001/* 002 * (C) Copyright 2011 Nuxeo SA (http://nuxeo.com/) and contributors. 003 * 004 * All rights reserved. This program and the accompanying materials 005 * are made available under the terms of the GNU Lesser General Public License 006 * (LGPL) version 2.1 which accompanies this distribution, and is available at 007 * http://www.gnu.org/licenses/lgpl.html 008 * 009 * This library is distributed in the hope that it will be useful, 010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 012 * Lesser General Public License for more details. 013 * 014 * Contributors: 015 * Anahide Tchertchian 016 */ 017package org.nuxeo.ecm.platform.forms.layout.functions; 018 019import java.io.Serializable; 020import java.util.ArrayList; 021import java.util.Collections; 022import java.util.Comparator; 023import java.util.List; 024import java.util.Map; 025 026import org.nuxeo.ecm.platform.forms.layout.api.FieldDefinition; 027import org.nuxeo.ecm.platform.forms.layout.api.Layout; 028import org.nuxeo.ecm.platform.forms.layout.api.LayoutDefinition; 029import org.nuxeo.ecm.platform.forms.layout.api.LayoutRow; 030import org.nuxeo.ecm.platform.forms.layout.api.LayoutRowDefinition; 031import org.nuxeo.ecm.platform.forms.layout.api.WidgetDefinition; 032import org.nuxeo.ecm.platform.forms.layout.api.WidgetReference; 033import org.nuxeo.ecm.platform.forms.layout.api.WidgetSelectOption; 034import org.nuxeo.ecm.platform.forms.layout.api.WidgetTypeDefinition; 035import org.nuxeo.ecm.platform.forms.layout.api.service.LayoutStore; 036import org.nuxeo.runtime.api.Framework; 037 038/** 039 * Provides helper methods, declared as static, to be used by the rendering framework. 040 * 041 * @since 5.5 042 */ 043public class LayoutFunctions { 044 045 public static WidgetTypeDefinition getWidgetTypeDefinition(String category, String typeName) { 046 LayoutStore layoutService = Framework.getService(LayoutStore.class); 047 return layoutService.getWidgetTypeDefinition(category, typeName); 048 } 049 050 /** 051 * Returns a String representing each of the field definitions property name, separated by a space. 052 */ 053 public static String getFieldDefinitionsAsString(FieldDefinition[] defs) { 054 StringBuilder buff = new StringBuilder(); 055 if (defs != null) { 056 for (FieldDefinition def : defs) { 057 buff.append(def.getPropertyName()).append(" "); 058 } 059 } 060 return buff.toString().trim(); 061 } 062 063 public static List<LayoutRow> getSelectedRows(Layout layout, List<String> selectedRowNames, 064 boolean showAlwaysSelected) { 065 LayoutRow[] rows = layout.getRows(); 066 List<LayoutRow> selectedRows = new ArrayList<LayoutRow>(); 067 if (rows != null) { 068 for (LayoutRow row : rows) { 069 if (row.isAlwaysSelected() && showAlwaysSelected) { 070 selectedRows.add(row); 071 } else if (selectedRowNames == null && row.isSelectedByDefault() && !row.isAlwaysSelected()) { 072 selectedRows.add(row); 073 } else if (selectedRowNames != null && selectedRowNames.contains(row.getName())) { 074 selectedRows.add(row); 075 } 076 } 077 } 078 // preserve selected rows order 079 Collections.sort(selectedRows, new LayoutRowsSorter(selectedRowNames)); 080 return selectedRows; 081 } 082 083 public static List<LayoutRow> getNotSelectedRows(Layout layout, List<String> selectedRowNames) { 084 LayoutRow[] rows = layout.getRows(); 085 List<LayoutRow> notSelectedRows = new ArrayList<LayoutRow>(); 086 if (rows != null) { 087 for (LayoutRow row : rows) { 088 if (selectedRowNames == null && !row.isSelectedByDefault() && !row.isAlwaysSelected()) { 089 notSelectedRows.add(row); 090 } else if (selectedRowNames != null && !row.isAlwaysSelected() 091 && !selectedRowNames.contains(row.getName())) { 092 notSelectedRows.add(row); 093 } 094 } 095 } 096 return notSelectedRows; 097 } 098 099 public static List<String> getDefaultSelectedRowNames(Layout layout, boolean showAlwaysSelected) { 100 List<LayoutRow> selectedRows = getSelectedRows(layout, null, showAlwaysSelected); 101 List<String> selectedRowNames = null; 102 if (selectedRows != null && !selectedRows.isEmpty()) { 103 selectedRowNames = new ArrayList<String>(); 104 for (LayoutRow row : selectedRows) { 105 selectedRowNames.add(row.getName()); 106 } 107 } 108 return selectedRowNames; 109 } 110 111 /** 112 * Returns an identifier computed from this definition so that an identical definition will have the same id. 113 * 114 * @since 5.5 115 */ 116 public static String computeLayoutDefinitionId(LayoutDefinition layoutDef) { 117 StringBuilder builder = new StringBuilder(); 118 builder.append(layoutDef.getName()).append(";"); 119 Map<String, String> templates = layoutDef.getTemplates(); 120 if (templates != null) { 121 builder.append(templates.toString()); 122 } 123 builder.append(";"); 124 LayoutRowDefinition[] rows = layoutDef.getRows(); 125 if (rows != null) { 126 for (LayoutRowDefinition row : rows) { 127 if (row != null) { 128 builder.append(computeLayoutRowDefinitionId(row)).append(","); 129 } 130 } 131 } 132 builder.append(";"); 133 Map<String, Map<String, Serializable>> properties = layoutDef.getProperties(); 134 if (properties != null) { 135 builder.append(properties.toString()); 136 } 137 builder.append(";"); 138 139 Integer intValue = new Integer(builder.toString().hashCode()); 140 return intValue.toString(); 141 } 142 143 /** 144 * Returns an identifier computed from this definition so that an identical definition will have the same id. 145 * 146 * @since 5.5 147 */ 148 public static String computeLayoutRowDefinitionId(LayoutRowDefinition layoutRowDef) { 149 StringBuffer builder = new StringBuffer(); 150 builder.append(layoutRowDef.getName()).append(";"); 151 builder.append(layoutRowDef.isSelectedByDefault()).append(";"); 152 builder.append(layoutRowDef.isAlwaysSelected()).append(";"); 153 WidgetReference[] widgets = layoutRowDef.getWidgetReferences(); 154 if (widgets != null) { 155 for (WidgetReference widget : widgets) { 156 if (widget != null) { 157 builder.append(widget.getName() + "(" + widget.getCategory() + ")").append(","); 158 } 159 } 160 } 161 builder.append(";"); 162 163 Map<String, Map<String, Serializable>> properties = layoutRowDef.getProperties(); 164 if (properties != null) { 165 builder.append(properties.toString()); 166 } 167 builder.append(";"); 168 169 Integer intValue = new Integer(builder.toString().hashCode()); 170 return intValue.toString(); 171 172 } 173 174 /** 175 * Returns an identifier computed from this definition so that an identical definition will have the same id. 176 * 177 * @since 5.5 178 */ 179 public static String computeWidgetDefinitionId(WidgetDefinition widgetDef) { 180 StringBuffer builder = new StringBuffer(); 181 builder.append(widgetDef.getName()).append(";"); 182 builder.append(widgetDef.getType()).append(";"); 183 builder.append(widgetDef.getTypeCategory()).append(";"); 184 185 FieldDefinition[] fieldDefinitions = widgetDef.getFieldDefinitions(); 186 if (fieldDefinitions != null) { 187 for (FieldDefinition fieldDef : fieldDefinitions) { 188 builder.append(fieldDef.getPropertyName() + ","); 189 } 190 } 191 builder.append(";"); 192 193 Map<String, String> labels = widgetDef.getLabels(); 194 if (labels != null) { 195 builder.append(labels.toString()); 196 } 197 builder.append(";"); 198 Map<String, String> helpLabels = widgetDef.getHelpLabels(); 199 if (helpLabels != null) { 200 builder.append(helpLabels.toString()); 201 } 202 builder.append(";"); 203 204 WidgetDefinition[] subWidgets = widgetDef.getSubWidgetDefinitions(); 205 if (subWidgets != null) { 206 for (WidgetDefinition widget : subWidgets) { 207 if (widget != null) { 208 builder.append(computeWidgetDefinitionId(widget)).append(","); 209 } 210 } 211 } 212 builder.append(";"); 213 214 WidgetReference[] subWidgetRefs = widgetDef.getSubWidgetReferences(); 215 if (subWidgetRefs != null) { 216 for (WidgetReference widget : subWidgetRefs) { 217 if (widget != null) { 218 builder.append(widget.getName() + "(" + widget.getCategory() + ")").append(","); 219 } 220 } 221 } 222 builder.append(";"); 223 224 Map<String, Map<String, Serializable>> properties = widgetDef.getProperties(); 225 if (properties != null) { 226 builder.append(properties.toString()); 227 } 228 builder.append(";"); 229 Map<String, Map<String, Serializable>> widgetModeProperties = widgetDef.getWidgetModeProperties(); 230 if (widgetModeProperties != null) { 231 builder.append(widgetModeProperties.toString()); 232 } 233 builder.append(";"); 234 235 builder.append(widgetDef.isTranslated()).append(";"); 236 builder.append(widgetDef.isHandlingLabels()).append(";"); 237 238 Map<String, String> modes = widgetDef.getModes(); 239 if (modes != null) { 240 builder.append(modes.toString()); 241 } 242 builder.append(";"); 243 244 WidgetSelectOption[] selectOptions = widgetDef.getSelectOptions(); 245 if (selectOptions != null) { 246 for (WidgetSelectOption option : selectOptions) { 247 if (option != null) { 248 builder.append(option.getTagConfigId()).append(","); 249 } 250 } 251 } 252 builder.append(";"); 253 254 Map<String, Map<String, Serializable>> controls = widgetDef.getControls(); 255 if (controls != null) { 256 builder.append(controls.toString()); 257 } 258 builder.append(";"); 259 260 Integer intValue = new Integer(builder.toString().hashCode()); 261 return intValue.toString(); 262 } 263 264 /** 265 * Sorter that re-arranges rows according to the row names order. 266 * 267 * @since 5.6 268 */ 269 public static class LayoutRowsSorter implements Comparator<LayoutRow> { 270 271 protected List<String> orderedRowNames; 272 273 private LayoutRowsSorter(List<String> orderedRowNames) { 274 super(); 275 this.orderedRowNames = orderedRowNames; 276 } 277 278 @Override 279 public int compare(LayoutRow o1, LayoutRow o2) { 280 if (orderedRowNames == null || orderedRowNames.size() == 0) { 281 return 0; 282 } 283 if (o1 == null && o2 == null) { 284 return 0; 285 } 286 if (o1 == null) { 287 return -1; 288 } 289 if (o2 == null) { 290 return 1; 291 } 292 String id1 = o1.getName(); 293 String id2 = o2.getName(); 294 if (id1 == null && id2 == null) { 295 return 0; 296 } 297 if (id1 == null) { 298 return -1; 299 } 300 if (id2 == null) { 301 return 1; 302 } 303 if (orderedRowNames.indexOf(id1) <= orderedRowNames.indexOf(id2)) { 304 return -1; 305 } else { 306 return 1; 307 } 308 } 309 310 } 311 312}