Sunday, 23 November 2014

Export to Excel with user customization (Style Class)

This blog we will see how to export excel sheet using default component and user customization using oracle ADF.

Export to excel using ADF component:

Export to excel using ADF component:Export to excel from any table using af:exportCollectionActionListener component.

<af:commandImageLink text="Export to Excel"
                                           icon="/images/export-to.png">
          <af:exportCollectionActionListener exportedId="tab1"
                                                                       type="excelHTML"
                                                                       title="ExportToExcel"
                                                                       filename="TestTable.xls"/>
 </af:commandImageLink>

But this type of functionality is not enough for user. Through this we can’t achieve the export to excel as per the user expectation.

Export to excel using style class:
 
The below code is required export to excel using style class.
The jsff/jspx you can add the below code:

<af:commandImageLink text="Export to Excel"
                                           icon="/images/export-to.png">
    <af:setActionListener from="tab1" to="#{viewScope['exportId']}"/>
    <af:setActionListener from="border:1px solid black" to="#{viewScope['tableHeaderStyle']}"/>
    <af:setActionListener from="border:1px solid black" to="#{viewScope['tableDataStyle']}"/>
    <af:fileDownloadActionListener filename="TestTable.xls"
                                                           contentType="excelHTML;chatset=UTF-8"
                                                           method="#{testBean.exportToExcel}"/>
 </af:commandImageLink>

The below code needs to add your backing/managed bean:

public void exportToExcel(FacesContext facesContext, OutputStream os)
  throws IOException, NoSuchMethodException, InvocationTargetException, IllegalAccessException
{
  Map<String, Object> varDetails = ADFContext.getCurrent().getViewScope();
  String expId = (String)varDetails.get("exportId"); // export table id
  String thStyle = (String)varDetails.get("tableHeaderStyle"); // style class for <th>
  String tdStyle = (String)varDetails.get("tableDataStyle"); // style class for  <td>
  boolean showHiddenCols = "true".equals(varDetails.get("exporter.showHiddenColumns")); // define if hidden columns should be shown
  boolean forceColWidth = "true".equals(varDetails.get("exporter.forceColumnWidth")); // force width of columns

  // get the table from absoulte path
  UIViewRoot vr = facesContext.getViewRoot();
  RichTable table = (RichTable)vr.findComponent(expId);

  // get columns of table
  List<RichColumn> cols = new ArrayList<RichColumn>();
  for (UIComponent co : table.getChildren())
  {
    if (co instanceof RichColumn)
    {
      RichColumn col = (RichColumn)co;
      // if showHiddenCols is true shows all columns, otherwise shows only rendered and visible columns
      if (showHiddenCols || (col.isRendered() && col.isVisible()))
        cols.add(col);
    }
  }

  OutputStreamWriter expData = new OutputStreamWriter(os);
  expData.append("<table>");
  expData.append("<tr>");
  for (RichColumn col : cols)
  {
    // render <th> with style, align, width and nowrap attributes
    expData.append("<th");
    if (StringUtils.isNotEmpty(thStyle))
      expData.append(String.format(" style='%s'", thStyle));
    expData.append(String.format(" align='%s'", StringUtils.defaultString(col.getAlign(), "left")));
    if (forceColWidth && StringUtils.isNotEmpty(col.getWidth()))
      expData.append(String.format(" width='%s'", col.getWidth()));
    if (col.isHeaderNoWrap())
      expData.append(" nowrap");
    expData.append(">");
    expData.append(StringUtils.defaultString(col.getHeaderText()));
    expData.append("</th>");
  }
  expData.append("</tr>");

  ELContext elContext = facesContext.getELContext();
  ExpressionFactory expressionFactory = facesContext.getApplication().getExpressionFactory();
  if (StringUtils.isNotEmpty(table.getVarStatus()))
  {
    // create varStatusMap
    Method m = UIXIterator.class.getDeclaredMethod("createVarStatusMap", new Class[0]);
    m.setAccessible(true);
    Object varStatus = m.invoke(table, new Object[0]);
    String el = String.format("#{%s}", table.getVarStatus());
    ValueExpression exp = expressionFactory.createValueExpression(elContext, el, Object.class);
    exp.setValue(elContext, varStatus);
  }

  CollectionModel model = (CollectionModel)table.getValue();
  int rowcount = model.getRowCount();
  for (int i = 0; i < rowcount; i++)
  {
    model.setRowIndex(i);
    JUCtrlHierNodeBinding row = (JUCtrlHierNodeBinding)model.getRowData();
    if (StringUtils.isNotEmpty(table.getVar()))
    {
      String el = String.format("#{%s}", table.getVar());
      ValueExpression exp = expressionFactory.createValueExpression(elContext, el, Object.class);
      exp.setValue(elContext, row);
    }

    expData.append("<tr>");
    for (RichColumn col : cols)
    {
      // get value from some column attributes
      ValueExpression inlineStyleVE = col.getValueExpression("inlineStyle");
      ValueExpression alignVE = col.getValueExpression("align");
      String style = inlineStyleVE == null ? "" : (String)inlineStyleVE.getValue(facesContext.getELContext());
      String align = alignVE == null ? "" : (String)alignVE.getValue(facesContext.getELContext());

      // render <td> with style, align, width and nowrap attributes
      expData.append("<td");
      if (StringUtils.isNotEmpty(tdStyle) || StringUtils.isNotEmpty(style))
        expData.append(String.format(" style='%s;%s'", StringUtils.defaultString(tdStyle), StringUtils.defaultString(style)));
      if (StringUtils.isNotEmpty(align))
        expData.append(String.format(" align='%s'", align));
      if (forceColWidth && StringUtils.isNotEmpty(col.getWidth()))
        expData.append(String.format(" width='%s'", col.getWidth()));
      if (col.isNoWrap())
        expData.append(" nowrap");
      expData.append(">");

      // render the content of <td> using the value or text of its children (depending on the type of component)
      // note that you can add other UIComponent types and render using different criteria, and also you can convert value (Date, Double, etc)
      for (UIComponent co : col.getChildren())
      {
        if (co instanceof UIXValue)
        {
          UIXValue uixValue = (UIXValue)co;
          if (uixValue.getValue() != null)
            expData.append(uixValue.getValue().toString());
        }
        else if (co instanceof RichCommandLink)
        {
          RichCommandLink commandLink = (RichCommandLink)co;
          if (commandLink.getText() != null)
            expData.append(commandLink.getText());
        }
        else if (co instanceof RichGoLink)
        {
          RichGoLink goLink = (RichGoLink)co;
          if (goLink.getText() != null)
            expData.append(String.format("<a href='%s'>%s</a>", goLink.getDestination(), goLink.getText()));
        }
      }
      expData.append("</td>");
    }
    expData.append("</tr>");
  }
  expData.append("</table>");
  expData.close();
}

Thanks...

No comments:

Post a Comment