/* * All rights reserved. This program and the accompanying materials * are made available under the terms of the GNU Lesser General Public License * (LGPL) version 2.1 which accompanies this distribution, and is available at * http://www.gnu.org/licenses/lgpl.html * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * Contributors: * Original file from org.jboss.seam.excel.ui.UIColumn.java in jboss-seam-excel * Anahide Tchertchian */ package org.nuxeo.ecm.platform.ui.web.component.seam; import java.io.IOException; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import javax.faces.component.UIComponent; import javax.faces.context.FacesContext; import org.jboss.seam.excel.ExcelWorkbook; import org.jboss.seam.excel.ExcelWorkbookException; import org.jboss.seam.excel.WorksheetItem; import org.jboss.seam.excel.ui.UIWorksheet; import org.jboss.seam.excel.ui.command.Command; /** * Overrides default column for better introspection of children. * <p> * If e:column tags are not direct children, the work sheet will not find them. * As layout templating adds additional JSF components, the children tree has * to be introspected further on, and other children components need to be * processed (UIAliasHolder components used in layout rendering for instance). * * @since 5.4.2 */ public class UIColumn extends org.jboss.seam.excel.ui.UIColumn { public static final String COMPONENT_TYPE = UIColumn.class.getName(); public static final String FOOTER_FACET_NAME = "footer"; @Override public void encodeBegin(FacesContext facesContext) throws IOException { // Get workbook and worksheet ExcelWorkbook excelWorkbook = getWorkbook(getParent()); if (excelWorkbook == null) { throw new ExcelWorkbookException("Could not find excel workbook"); } // Column width etc. excelWorkbook.applyColumnSettings(this); UIWorksheet sheet = (UIWorksheet) getParentByClass(getParent(), UIWorksheet.class); if (sheet == null) { throw new ExcelWorkbookException("Could not find worksheet"); } // Add header items (if any) WorksheetItem headerItem = (WorksheetItem) getFacet(HEADER_FACET_NAME); if (headerItem != null) { excelWorkbook.addItem(headerItem); } // Execute commands (if any) List<Command> commands = getCommands(getChildren()); for (Command command : commands) { excelWorkbook.executeCommand(command); } // Get UiCell template this column's data cells and iterate over sheet // data // XXX: process all components instead of just UICell ones. for (UIComponent child : getChildren()) { Object oldValue = null; Iterator iterator = null; // Store away the old value for the sheet binding var (if there is // one) if (sheet.getVar() != null) { oldValue = FacesContext.getCurrentInstance().getExternalContext().getRequestMap().get( sheet.getVar()); iterator = sheet.getDataIterator(); } else { // No var, no iteration... iterator = new ArrayList().iterator(); } while (iterator.hasNext()) { // Store the bound data in the request map and add the cell FacesContext.getCurrentInstance().getExternalContext().getRequestMap().put( sheet.getVar(), iterator.next()); encodeChild(facesContext, sheet, excelWorkbook, child); } // No iteration, nothing to restore if (sheet.getVar() == null) { return; } // Restore the previously modified request map (if there was a var) if (oldValue == null) { FacesContext.getCurrentInstance().getExternalContext().getRequestMap().remove( sheet.getVar()); } else { FacesContext.getCurrentInstance().getExternalContext().getRequestMap().put( sheet.getVar(), oldValue); } } // Add footer items (if any) WorksheetItem footerItem = (WorksheetItem) getFacet(FOOTER_FACET_NAME); if (footerItem != null) { excelWorkbook.addItem(footerItem); } // Move column pointer to next column excelWorkbook.nextColumn(); } @SuppressWarnings("rawtypes") protected void encodeChild(FacesContext facesContext, UIWorksheet sheet, ExcelWorkbook excelWorkbook, UIComponent child) throws IOException { // XXX make sure other components are processed if (child instanceof WorksheetItem) { excelWorkbook.addItem((WorksheetItem) child); } else { if (child.isRendered()) { child.encodeBegin(facesContext); // do not let component handling render of its children List subChildren = child.getChildren(); for (int j = 0, size = child.getChildCount(); j < size; j++) { UIComponent subChild = (UIComponent) subChildren.get(j); encodeChild(facesContext, sheet, excelWorkbook, subChild); } child.encodeEnd(facesContext); } } } @SuppressWarnings("unchecked") public static <T> List<T> getAllChildrenOfType(List<UIComponent> children, Class<T> childType) { List<T> matches = new ArrayList<T>(); for (UIComponent child : children) { if (childType.isAssignableFrom(child.getClass())) { matches.add((T) child); } else { // XXX introspect children List<T> subChildren = getAllChildrenOfType(child.getChildren(), childType); if (subChildren != null && !subChildren.isEmpty()) { matches.addAll(subChildren); } } } return matches; } /** * Returns all commands from a child list * * @param children The list to search * @return The commands */ protected static List<Command> getCommands(List<UIComponent> children) { return getAllChildrenOfType(children, Command.class); } }