Modified: ofbiz/trunk/framework/widget/src/org/ofbiz/widget/form/ModelFormField.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/widget/src/org/ofbiz/widget/form/ModelFormField.java?rev=1647936&r1=1647935&r2=1647936&view=diff ============================================================================== --- ofbiz/trunk/framework/widget/src/org/ofbiz/widget/form/ModelFormField.java (original) +++ ofbiz/trunk/framework/widget/src/org/ofbiz/widget/form/ModelFormField.java Fri Dec 26 06:47:13 2014 @@ -24,6 +24,7 @@ import java.sql.Timestamp; import java.text.DateFormat; import java.text.NumberFormat; import java.util.ArrayList; +import java.util.Collections; import java.util.Date; import java.util.HashMap; import java.util.LinkedList; @@ -58,14 +59,7 @@ import org.ofbiz.entity.GenericValue; import org.ofbiz.entity.condition.EntityCondition; import org.ofbiz.entity.finder.EntityFinderUtil; import org.ofbiz.entity.model.ModelEntity; -import org.ofbiz.entity.model.ModelField; -import org.ofbiz.entity.model.ModelReader; -import org.ofbiz.entity.util.EntityQuery; import org.ofbiz.entity.util.EntityUtil; -import org.ofbiz.service.DispatchContext; -import org.ofbiz.service.GenericServiceException; -import org.ofbiz.service.ModelParam; -import org.ofbiz.service.ModelService; import org.ofbiz.widget.ModelFieldVisitor; import org.ofbiz.widget.WidgetWorker; import org.ofbiz.widget.form.ModelForm.UpdateArea; @@ -75,534 +69,129 @@ import bsh.EvalError; import bsh.Interpreter; /** - * Widget Library - Form model class + * Models the <field> element. + * + * @see <code>widget-form.xsd</code> */ public class ModelFormField { - public static final String module = ModelFormField.class.getName(); - - protected ModelForm modelForm; - - protected String name; - protected FlexibleMapAccessor<Map<String, ? extends Object>> mapAcsr; - protected String entityName; - protected String serviceName; - protected FlexibleMapAccessor<Object> entryAcsr; - protected String parameterName; - protected String fieldName; - protected String attributeName; - protected FlexibleStringExpander title; - protected FlexibleStringExpander tooltip; - protected String titleAreaStyle; - protected String widgetAreaStyle; - protected String titleStyle; - protected String widgetStyle; - protected String tooltipStyle; - protected String requiredFieldStyle; - protected String sortFieldStyle; - protected String sortFieldAscStyle; - protected String sortFieldDescStyle; - protected Integer position = null; - protected String redWhen; - protected FlexibleStringExpander useWhen; - protected boolean encodeOutput = true; - protected String event; - protected FlexibleStringExpander action; - - protected FieldInfo fieldInfo = null; - protected String idName; - protected boolean separateColumn = false; - protected Boolean requiredField = null; - protected Boolean sortField = null; - protected String sortFieldHelpText = ""; - protected String headerLink; - protected String headerLinkStyle; - - /** On Change Event areas to be updated. */ - protected List<UpdateArea> onChangeUpdateAreas; - /** On Click Event areas to be updated. */ - protected List<UpdateArea> onClickUpdateAreas; - - // ===== CONSTRUCTORS ===== - /** Default Constructor */ - public ModelFormField(ModelForm modelForm) { - this.modelForm = modelForm; - } - - /** XML Constructor */ - public ModelFormField(Element fieldElement, ModelForm modelForm, ModelReader entityModelReader, - DispatchContext dispatchContext) { - this.modelForm = modelForm; - this.name = fieldElement.getAttribute("name"); - this.setMapName(fieldElement.getAttribute("map-name")); - this.entityName = fieldElement.getAttribute("entity-name"); - this.serviceName = fieldElement.getAttribute("service-name"); - this.setEntryName(UtilXml.checkEmpty(fieldElement.getAttribute("entry-name"), this.name)); - this.parameterName = UtilXml.checkEmpty(fieldElement.getAttribute("parameter-name"), this.name); - this.fieldName = UtilXml.checkEmpty(fieldElement.getAttribute("field-name"), this.name); - this.attributeName = UtilXml.checkEmpty(fieldElement.getAttribute("attribute-name"), this.name); - this.setTitle(fieldElement.hasAttribute("title") ? fieldElement.getAttribute("title") : null); - this.setTooltip(fieldElement.getAttribute("tooltip")); - this.titleAreaStyle = fieldElement.getAttribute("title-area-style"); - this.widgetAreaStyle = fieldElement.getAttribute("widget-area-style"); - this.titleStyle = fieldElement.getAttribute("title-style"); - this.widgetStyle = fieldElement.getAttribute("widget-style"); - this.tooltipStyle = fieldElement.getAttribute("tooltip-style"); - this.requiredFieldStyle = fieldElement.getAttribute("required-field-style"); - this.sortFieldStyle = fieldElement.getAttribute("sort-field-style"); - this.sortFieldAscStyle = fieldElement.getAttribute("sort-field-asc-style"); - this.sortFieldDescStyle = fieldElement.getAttribute("sort-field-desc-style"); - this.redWhen = fieldElement.getAttribute("red-when"); - this.setUseWhen(fieldElement.getAttribute("use-when")); - this.encodeOutput = !"false".equals(fieldElement.getAttribute("encode-output")); - this.event = fieldElement.getAttribute("event"); - this.setAction(fieldElement.hasAttribute("action") ? fieldElement.getAttribute("action") : null); - this.idName = fieldElement.getAttribute("id-name"); - this.separateColumn = "true".equals(fieldElement.getAttribute("separate-column")); - this.requiredField = fieldElement.hasAttribute("required-field") ? "true".equals(fieldElement - .getAttribute("required-field")) : null; - this.sortField = fieldElement.hasAttribute("sort-field") ? "true".equals(fieldElement.getAttribute("sort-field")) : null; - this.sortFieldHelpText = fieldElement.getAttribute("sort-field-help-text"); - this.headerLink = fieldElement.getAttribute("header-link"); - this.headerLinkStyle = fieldElement.getAttribute("header-link-style"); - - String positionStr = fieldElement.getAttribute("position"); - try { - if (UtilValidate.isNotEmpty(positionStr)) - position = Integer.valueOf(positionStr); - } catch (Exception e) { - Debug.logError(e, "Could not convert position attribute of the field element to an integer: [" + positionStr - + "], using the default of the form renderer", module); - } - - // get sub-element and set fieldInfo - List<? extends Element> subElements = UtilXml.childElementList(fieldElement); - for (Element subElement : subElements) { - String subElementName = subElement.getTagName(); - if (Debug.verboseOn()) - Debug.logVerbose("Processing field " + this.name + " with type info tag " + subElementName, module); - - if (UtilValidate.isEmpty(subElementName)) { - this.fieldInfo = null; - this.induceFieldInfo(null, entityModelReader, dispatchContext); //no defaultFieldType specified here, will default to edit - } else if ("display".equals(subElementName)) - this.fieldInfo = new DisplayField(subElement, this); - else if ("display-entity".equals(subElementName)) - this.fieldInfo = new DisplayEntityField(subElement, this); - else if ("hyperlink".equals(subElementName)) - this.fieldInfo = new HyperlinkField(subElement, this); - else if ("text".equals(subElementName)) - this.fieldInfo = new TextField(subElement, this); - else if ("textarea".equals(subElementName)) - this.fieldInfo = new TextareaField(subElement, this); - else if ("date-time".equals(subElementName)) - this.fieldInfo = new DateTimeField(subElement, this); - else if ("drop-down".equals(subElementName)) - this.fieldInfo = new DropDownField(subElement, this); - else if ("check".equals(subElementName)) - this.fieldInfo = new CheckField(subElement, this); - else if ("radio".equals(subElementName)) - this.fieldInfo = new RadioField(subElement, this); - else if ("submit".equals(subElementName)) - this.fieldInfo = new SubmitField(subElement, this); - else if ("reset".equals(subElementName)) - this.fieldInfo = new ResetField(subElement, this); - else if ("hidden".equals(subElementName)) - this.fieldInfo = new HiddenField(subElement, this); - else if ("ignored".equals(subElementName)) - this.fieldInfo = new IgnoredField(subElement, this); - else if ("text-find".equals(subElementName)) - this.fieldInfo = new TextFindField(subElement, this); - else if ("date-find".equals(subElementName)) - this.fieldInfo = new DateFindField(subElement, this); - else if ("range-find".equals(subElementName)) - this.fieldInfo = new RangeFindField(subElement, this); - else if ("lookup".equals(subElementName)) - this.fieldInfo = new LookupField(subElement, this); - else if ("file".equals(subElementName)) - this.fieldInfo = new FileField(subElement, this); - else if ("password".equals(subElementName)) - this.fieldInfo = new PasswordField(subElement, this); - else if ("image".equals(subElementName)) - this.fieldInfo = new ImageField(subElement, this); - else if ("container".equals(subElementName)) - this.fieldInfo = new ContainerField(subElement, this); - else if ("on-field-event-update-area".equals(subElementName)) - addOnEventUpdateArea(new UpdateArea(subElement)); - else - throw new IllegalArgumentException("The field sub-element with name " + subElementName + " is not supported"); - } - } - - private void addOnEventUpdateArea(UpdateArea updateArea) { - // Event types are sorted as a convenience for the rendering classes - Debug.logInfo(this.modelForm.getName() + ":" + this.name + " adding UpdateArea type " + updateArea.getEventType(), module); - if ("change".equals(updateArea.getEventType())) - addOnChangeUpdateArea(updateArea); - else if ("click".equals(updateArea.getEventType())) - addOnClickUpdateArea(updateArea); - } - - private void addOnChangeUpdateArea(UpdateArea updateArea) { - if (onChangeUpdateAreas == null) - onChangeUpdateAreas = new ArrayList<UpdateArea>(); - onChangeUpdateAreas.add(updateArea); - Debug.logInfo(this.modelForm.getName() + ":" + this.name + " onChangeUpdateAreas size = " + onChangeUpdateAreas.size(), - module); - } - - private void addOnClickUpdateArea(UpdateArea updateArea) { - if (onClickUpdateAreas == null) - onClickUpdateAreas = new ArrayList<UpdateArea>(); - onClickUpdateAreas.add(updateArea); - } - - public void mergeOverrideModelFormField(ModelFormField overrideFormField) { - if (overrideFormField == null) - return; - - // incorporate updates for values that are not empty in the overrideFormField - if (UtilValidate.isNotEmpty(overrideFormField.name)) - this.name = overrideFormField.name; - if (UtilValidate.isNotEmpty(overrideFormField.mapAcsr)) - this.mapAcsr = overrideFormField.mapAcsr; //Debug.logInfo("overriding mapAcsr, old=" + (this.mapAcsr==null?"null":this.mapAcsr.getOriginalName()) + ", new=" + overrideFormField.mapAcsr.getOriginalName(), module); - if (UtilValidate.isNotEmpty(overrideFormField.entityName)) - this.entityName = overrideFormField.entityName; - if (UtilValidate.isNotEmpty(overrideFormField.serviceName)) - this.serviceName = overrideFormField.serviceName; - if (UtilValidate.isNotEmpty(overrideFormField.entryAcsr)) - this.entryAcsr = overrideFormField.entryAcsr; - if (UtilValidate.isNotEmpty(overrideFormField.parameterName)) - this.parameterName = overrideFormField.parameterName; - if (UtilValidate.isNotEmpty(overrideFormField.fieldName)) - this.fieldName = overrideFormField.fieldName; - if (UtilValidate.isNotEmpty(overrideFormField.attributeName)) - this.attributeName = overrideFormField.attributeName; - if (UtilValidate.isNotEmpty(overrideFormField.title)) - this.title = overrideFormField.title; // title="" can be used to override the original value - if (UtilValidate.isNotEmpty(overrideFormField.tooltip)) - this.tooltip = overrideFormField.tooltip; - if (overrideFormField.requiredField != null) - this.requiredField = overrideFormField.requiredField; - if (overrideFormField.sortField != null) - this.sortField = overrideFormField.sortField; - if (UtilValidate.isNotEmpty(overrideFormField.sortFieldHelpText)) - this.sortFieldHelpText = overrideFormField.sortFieldHelpText; - if (UtilValidate.isNotEmpty(overrideFormField.titleAreaStyle)) - this.titleAreaStyle = overrideFormField.titleAreaStyle; - if (UtilValidate.isNotEmpty(overrideFormField.widgetAreaStyle)) - this.widgetAreaStyle = overrideFormField.widgetAreaStyle; - if (UtilValidate.isNotEmpty(overrideFormField.titleStyle)) - this.titleStyle = overrideFormField.titleStyle; - if (UtilValidate.isNotEmpty(overrideFormField.widgetStyle)) - this.widgetStyle = overrideFormField.widgetStyle; - if (overrideFormField.position != null) - this.position = overrideFormField.position; - if (UtilValidate.isNotEmpty(overrideFormField.redWhen)) - this.redWhen = overrideFormField.redWhen; - if (UtilValidate.isNotEmpty(overrideFormField.event)) - this.event = overrideFormField.event; - if (UtilValidate.isNotEmpty(overrideFormField.action)) - this.action = overrideFormField.action; - if (UtilValidate.isNotEmpty(overrideFormField.useWhen)) - this.useWhen = overrideFormField.useWhen; - if (overrideFormField.fieldInfo != null) - this.setFieldInfo(overrideFormField.fieldInfo); - if (overrideFormField.headerLink != null) - this.setHeaderLink(overrideFormField.headerLink); - if (UtilValidate.isNotEmpty(overrideFormField.idName)) - this.idName = overrideFormField.idName; - if (overrideFormField.onChangeUpdateAreas != null) - this.onChangeUpdateAreas = overrideFormField.onChangeUpdateAreas; - if (overrideFormField.onClickUpdateAreas != null) - this.onClickUpdateAreas = overrideFormField.onClickUpdateAreas; - this.encodeOutput = overrideFormField.encodeOutput; - } - - private boolean induceFieldInfo(String defaultFieldType, ModelReader entityModelReader, DispatchContext dispatchContext) { - if (this.induceFieldInfoFromEntityField(defaultFieldType, entityModelReader)) - return true; - if (this.induceFieldInfoFromServiceParam(defaultFieldType, entityModelReader, dispatchContext)) - return true; - return false; - } + /* + * ----------------------------------------------------------------------- * + * DEVELOPERS PLEASE READ + * ----------------------------------------------------------------------- * + * + * This model is intended to be a read-only data structure that represents + * an XML element. Outside of object construction, the class should not + * have any behaviors. All behavior should be contained in model visitors. + * + * Instances of this class will be shared by multiple threads - therefore + * it is immutable. DO NOT CHANGE THE OBJECT'S STATE AT RUN TIME! + * + */ - private boolean induceFieldInfoFromServiceParam(String defaultFieldType, ModelReader entityModelReader, - DispatchContext dispatchContext) { - if (UtilValidate.isEmpty(this.getServiceName()) || UtilValidate.isEmpty(this.getAttributeName())) - return false; - try { - ModelService modelService = dispatchContext.getModelService(this.getServiceName()); - if (modelService != null) { - ModelParam modelParam = modelService.getParam(this.getAttributeName()); - if (modelParam != null) { - if (UtilValidate.isNotEmpty(modelParam.entityName) && UtilValidate.isNotEmpty(modelParam.fieldName)) { - this.entityName = modelParam.entityName; - this.fieldName = modelParam.fieldName; - if (this.induceFieldInfoFromEntityField(defaultFieldType, entityModelReader)) { - return true; - } - } + public static final String module = ModelFormField.class.getName(); - this.induceFieldInfoFromServiceParam(modelService, modelParam, defaultFieldType); - return true; - } - } - } catch (GenericServiceException e) { - Debug.logError(e, - "error getting service parameter definition for auto-field with serviceName: " + this.getServiceName() - + ", and attributeName: " + this.getAttributeName(), module); - } - return false; + public static ModelFormField from(ModelFormFieldBuilder builder) { + return new ModelFormField(builder); } - public boolean induceFieldInfoFromServiceParam(ModelService modelService, ModelParam modelParam, String defaultFieldType) { - if (modelService == null || modelParam == null) - return false; - - this.serviceName = modelService.name; - this.attributeName = modelParam.name; - - if ("find".equals(defaultFieldType)) { - if (modelParam.type.indexOf("Double") != -1 || modelParam.type.indexOf("Float") != -1 - || modelParam.type.indexOf("Long") != -1 || modelParam.type.indexOf("Integer") != -1) { - ModelFormField.RangeFindField textField = new ModelFormField.RangeFindField(FieldInfo.SOURCE_AUTO_SERVICE, this); - textField.setSize(6); - this.setFieldInfo(textField); - } else if (modelParam.type.indexOf("Timestamp") != -1) { - ModelFormField.DateFindField dateTimeField = new ModelFormField.DateFindField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("timestamp"); - this.setFieldInfo(dateTimeField); - } else if (modelParam.type.indexOf("Date") != -1) { - ModelFormField.DateFindField dateTimeField = new ModelFormField.DateFindField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("date"); - this.setFieldInfo(dateTimeField); - } else if (modelParam.type.indexOf("Time") != -1) { - ModelFormField.DateFindField dateTimeField = new ModelFormField.DateFindField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("time"); - this.setFieldInfo(dateTimeField); - } else { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_SERVICE, this); - this.setFieldInfo(textField); - } - } else if ("display".equals(defaultFieldType)) { - ModelFormField.DisplayField displayField = new ModelFormField.DisplayField(FieldInfo.SOURCE_AUTO_SERVICE, this); - this.setFieldInfo(displayField); + private final FlexibleStringExpander action; + private final String attributeName; + private final boolean encodeOutput; + private final String entityName; + private final FlexibleMapAccessor<Object> entryAcsr; + private final String event; + private final FieldInfo fieldInfo; + private final String fieldName; + private final String headerLink; + private final String headerLinkStyle; + private final String idName; + private final FlexibleMapAccessor<Map<String, ? extends Object>> mapAcsr; + private final ModelForm modelForm; + private final String name; + private final List<UpdateArea> onChangeUpdateAreas; + private final List<UpdateArea> onClickUpdateAreas; + private final String parameterName; + private final Integer position; + private final String redWhen; + private final Boolean requiredField; + private final String requiredFieldStyle; + private final boolean separateColumn; + private final String serviceName; + private final Boolean sortField; + private final String sortFieldAscStyle; + private final String sortFieldDescStyle; + private final String sortFieldHelpText; + private final String sortFieldStyle; + private final FlexibleStringExpander title; + private final String titleAreaStyle; + private final String titleStyle; + private final FlexibleStringExpander tooltip; + private final String tooltipStyle; + private final FlexibleStringExpander useWhen; + private final String widgetAreaStyle; + private final String widgetStyle; + + private ModelFormField(ModelFormFieldBuilder builder) { + this.action = builder.getAction(); + this.attributeName = builder.getAttributeName(); + this.encodeOutput = builder.getEncodeOutput(); + this.entityName = builder.getEntityName(); + this.entryAcsr = builder.getEntryAcsr(); + this.event = builder.getEvent(); + if (builder.getFieldInfo() != null) { + this.fieldInfo = builder.getFieldInfo().copy(this); } else { - // default to "edit" - if (modelParam.type.indexOf("Double") != -1 || modelParam.type.indexOf("Float") != -1 - || modelParam.type.indexOf("Long") != -1 || modelParam.type.indexOf("Integer") != -1) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_SERVICE, this); - textField.setSize(6); - this.setFieldInfo(textField); - } else if (modelParam.type.indexOf("Timestamp") != -1) { - ModelFormField.DateTimeField dateTimeField = new ModelFormField.DateTimeField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("timestamp"); - this.setFieldInfo(dateTimeField); - } else if (modelParam.type.indexOf("Date") != -1) { - ModelFormField.DateTimeField dateTimeField = new ModelFormField.DateTimeField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("date"); - this.setFieldInfo(dateTimeField); - } else if (modelParam.type.indexOf("Time") != -1) { - ModelFormField.DateTimeField dateTimeField = new ModelFormField.DateTimeField(FieldInfo.SOURCE_AUTO_SERVICE, this); - dateTimeField.setType("time"); - this.setFieldInfo(dateTimeField); - } else { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_SERVICE, this); - this.setFieldInfo(textField); - } + this.fieldInfo = null; } - - return true; - } - - private boolean induceFieldInfoFromEntityField(String defaultFieldType, ModelReader entityModelReader) { - if (UtilValidate.isEmpty(this.getEntityName()) || UtilValidate.isEmpty(this.getFieldName())) - return false; - try { - ModelEntity modelEntity = entityModelReader.getModelEntity(this.getEntityName()); - if (modelEntity != null) { - ModelField modelField = modelEntity.getField(this.getFieldName()); - if (modelField != null) { - // okay, populate using the entity field info... - this.induceFieldInfoFromEntityField(modelEntity, modelField, defaultFieldType); - return true; - } - } - } catch (GenericEntityException e) { - Debug.logError(e, module); + this.fieldName = builder.getFieldName(); + this.headerLink = builder.getHeaderLink(); + this.headerLinkStyle = builder.getHeaderLinkStyle(); + this.idName = builder.getIdName(); + this.mapAcsr = builder.getMapAcsr(); + this.modelForm = builder.getModelForm(); + this.name = builder.getName(); + Debug.logInfo("name = " + name + ", fieldInfo = " + fieldInfo, module); + if (builder.getOnChangeUpdateAreas().isEmpty()) { + this.onChangeUpdateAreas = Collections.emptyList(); + } else { + this.onChangeUpdateAreas = Collections.unmodifiableList(new ArrayList<UpdateArea>(builder.getOnChangeUpdateAreas())); } - return false; - } - - public boolean induceFieldInfoFromEntityField(ModelEntity modelEntity, ModelField modelField, String defaultFieldType) { - if (modelEntity == null || modelField == null) - return false; - - this.entityName = modelEntity.getEntityName(); - this.fieldName = modelField.getName(); - - if ("find".equals(defaultFieldType)) { - if ("id".equals(modelField.getType()) || "id-ne".equals(modelField.getType())) { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(20); - textField.setMaxlength(Integer.valueOf(20)); - this.setFieldInfo(textField); - } else if ("id-long".equals(modelField.getType()) || "id-long-ne".equals(modelField.getType())) { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(40); - textField.setMaxlength(Integer.valueOf(60)); - this.setFieldInfo(textField); - } else if ("id-vlong".equals(modelField.getType()) || "id-vlong-ne".equals(modelField.getType())) { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(60); - textField.setMaxlength(Integer.valueOf(250)); - this.setFieldInfo(textField); - } else if ("very-short".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(6); - textField.setMaxlength(Integer.valueOf(10)); - this.setFieldInfo(textField); - } else if ("name".equals(modelField.getType()) || "short-varchar".equals(modelField.getType())) { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(40); - textField.setMaxlength(Integer.valueOf(60)); - this.setFieldInfo(textField); - } else if ("value".equals(modelField.getType()) || "comment".equals(modelField.getType()) - || "description".equals(modelField.getType()) || "long-varchar".equals(modelField.getType()) - || "url".equals(modelField.getType()) || "email".equals(modelField.getType())) { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(60); - textField.setMaxlength(Integer.valueOf(250)); - this.setFieldInfo(textField); - } else if ("floating-point".equals(modelField.getType()) || "currency-amount".equals(modelField.getType()) - || "numeric".equals(modelField.getType())) { - ModelFormField.RangeFindField textField = new ModelFormField.RangeFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(6); - this.setFieldInfo(textField); - } else if ("date-time".equals(modelField.getType()) || "date".equals(modelField.getType()) - || "time".equals(modelField.getType())) { - ModelFormField.DateFindField dateTimeField = new ModelFormField.DateFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - if ("date-time".equals(modelField.getType())) { - dateTimeField.setType("timestamp"); - } else if ("date".equals(modelField.getType())) { - dateTimeField.setType("date"); - } else if ("time".equals(modelField.getType())) { - dateTimeField.setType("time"); - } - this.setFieldInfo(dateTimeField); - } else { - ModelFormField.TextFindField textField = new ModelFormField.TextFindField(FieldInfo.SOURCE_AUTO_ENTITY, this); - this.setFieldInfo(textField); - } - } else if ("display".equals(defaultFieldType)) { - ModelFormField.DisplayField displayField = new ModelFormField.DisplayField(FieldInfo.SOURCE_AUTO_SERVICE, this); - this.setFieldInfo(displayField); - } else if ("hidden".equals(defaultFieldType)) { - ModelFormField.HiddenField hiddenField = new ModelFormField.HiddenField(FieldInfo.SOURCE_AUTO_SERVICE, this); - this.setFieldInfo(hiddenField); + if (builder.getOnClickUpdateAreas().isEmpty()) { + this.onClickUpdateAreas = Collections.emptyList(); } else { - if ("id".equals(modelField.getType()) || "id-ne".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(20); - textField.setMaxlength(Integer.valueOf(20)); - this.setFieldInfo(textField); - } else if ("id-long".equals(modelField.getType()) || "id-long-ne".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(40); - textField.setMaxlength(Integer.valueOf(60)); - this.setFieldInfo(textField); - } else if ("id-vlong".equals(modelField.getType()) || "id-vlong-ne".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(60); - textField.setMaxlength(Integer.valueOf(250)); - this.setFieldInfo(textField); - } else if ("indicator".equals(modelField.getType())) { - ModelFormField.DropDownField dropDownField = new ModelFormField.DropDownField(FieldInfo.SOURCE_AUTO_ENTITY, this); - dropDownField.setAllowEmpty(false); - dropDownField.addOptionSource(new ModelFormField.SingleOption("Y", null, dropDownField)); - dropDownField.addOptionSource(new ModelFormField.SingleOption("N", null, dropDownField)); - this.setFieldInfo(dropDownField); - //ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - //textField.setSize(1); - //textField.setMaxlength(Integer.valueOf(1)); - //this.setFieldInfo(textField); - } else if ("very-short".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(6); - textField.setMaxlength(Integer.valueOf(10)); - this.setFieldInfo(textField); - } else if ("very-long".equals(modelField.getType())) { - ModelFormField.TextareaField textareaField = new ModelFormField.TextareaField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textareaField.setCols(60); - textareaField.setRows(2); - this.setFieldInfo(textareaField); - } else if ("name".equals(modelField.getType()) || "short-varchar".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(40); - textField.setMaxlength(Integer.valueOf(60)); - this.setFieldInfo(textField); - } else if ("value".equals(modelField.getType()) || "comment".equals(modelField.getType()) - || "description".equals(modelField.getType()) || "long-varchar".equals(modelField.getType()) - || "url".equals(modelField.getType()) || "email".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(60); - textField.setMaxlength(Integer.valueOf(250)); - this.setFieldInfo(textField); - } else if ("floating-point".equals(modelField.getType()) || "currency-amount".equals(modelField.getType()) - || "numeric".equals(modelField.getType())) { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - textField.setSize(6); - this.setFieldInfo(textField); - } else if ("date-time".equals(modelField.getType()) || "date".equals(modelField.getType()) - || "time".equals(modelField.getType())) { - ModelFormField.DateTimeField dateTimeField = new ModelFormField.DateTimeField(FieldInfo.SOURCE_AUTO_ENTITY, this); - if ("date-time".equals(modelField.getType())) { - dateTimeField.setType("timestamp"); - } else if ("date".equals(modelField.getType())) { - dateTimeField.setType("date"); - } else if ("time".equals(modelField.getType())) { - dateTimeField.setType("time"); - } - this.setFieldInfo(dateTimeField); - } else { - ModelFormField.TextField textField = new ModelFormField.TextField(FieldInfo.SOURCE_AUTO_ENTITY, this); - this.setFieldInfo(textField); - } + this.onClickUpdateAreas = Collections.unmodifiableList(new ArrayList<UpdateArea>(builder.getOnClickUpdateAreas())); } - - return true; - } - - public void renderFieldString(Appendable writer, Map<String, Object> context, FormStringRenderer formStringRenderer) - throws IOException { - this.fieldInfo.renderFieldString(writer, context, formStringRenderer); - } - - public List<UpdateArea> getOnChangeUpdateAreas() { - return onChangeUpdateAreas; - } - - public List<UpdateArea> getOnClickUpdateAreas() { - return onClickUpdateAreas; - } - - public FieldInfo getFieldInfo() { - return fieldInfo; + this.parameterName = builder.getParameterName(); + this.position = builder.getPosition(); + this.redWhen = builder.getRedWhen(); + this.requiredField = builder.getRequiredField(); + this.requiredFieldStyle = builder.getRequiredFieldStyle(); + this.separateColumn = builder.getSeparateColumn(); + this.serviceName = builder.getServiceName(); + this.sortField = builder.getSortField(); + this.sortFieldAscStyle = builder.getSortFieldAscStyle(); + this.sortFieldDescStyle = builder.getSortFieldDescStyle(); + this.sortFieldHelpText = builder.getSortFieldHelpText(); + this.sortFieldStyle = builder.getSortFieldStyle(); + this.title = builder.getTitle(); + this.titleAreaStyle = builder.getTitleAreaStyle(); + this.titleStyle = builder.getTitleStyle(); + this.tooltip = builder.getTooltip(); + this.tooltipStyle = builder.getTooltipStyle(); + this.useWhen = builder.getUseWhen(); + this.widgetAreaStyle = builder.getWidgetAreaStyle(); + this.widgetStyle = builder.getWidgetStyle(); } - public ModelForm getModelForm() { - return modelForm; + public FlexibleStringExpander getAction() { + return action; } - /** - * @param fieldInfo - */ - public void setFieldInfo(FieldInfo fieldInfo) { - // field info is a little different, check source for priority - if (fieldInfo != null && (this.fieldInfo == null || (fieldInfo.getFieldSource() <= this.fieldInfo.getFieldSource()))) { - this.fieldInfo = fieldInfo.copy(this); - } + public String getAction(Map<String, ? extends Object> context) { + if (UtilValidate.isNotEmpty(this.action)) + return action.expandString(context); + return null; } /** @@ -618,22 +207,35 @@ public class ModelFormField { return this.name; } + public String getCurrentContainerId(Map<String, Object> context) { + ModelForm modelForm = this.getModelForm(); + String idName = FlexibleStringExpander.expandString(this.getIdName(), context); + + if (modelForm != null) { + Integer itemIndex = (Integer) context.get("itemIndex"); + if ("list".equals(modelForm.getType()) || "multi".equals(modelForm.getType())) { + if (itemIndex != null) { + return idName + modelForm.getItemIndexSeparator() + itemIndex.intValue(); + } + } + } + return idName; + } + + public boolean getEncodeOutput() { + return this.encodeOutput; + } + public String getEntityName() { if (UtilValidate.isNotEmpty(this.entityName)) return this.entityName; return this.modelForm.getDefaultEntityName(); } - public String getEntryName() { - if (UtilValidate.isNotEmpty(this.entryAcsr)) - return this.entryAcsr.getOriginalName(); - return this.name; - } - /** * Gets the entry from the context that corresponds to this field; if this * form is being rendered in an error condition (ie isError in the context - * is true) then the value will be retreived from the parameters Map in + * is true) then the value will be retrieved from the parameters Map in * the context. * * @param context the context @@ -749,6 +351,51 @@ public class ModelFormField { return returnValue; } + public FlexibleMapAccessor<Object> getEntryAcsr() { + return entryAcsr; + } + + public String getEntryName() { + if (UtilValidate.isNotEmpty(this.entryAcsr)) + return this.entryAcsr.getOriginalName(); + return this.name; + } + + public String getEvent() { + return event; + } + + public FieldInfo getFieldInfo() { + return fieldInfo; + } + + /** + * Gets the name of the Entity Field that corresponds + * with this field. This can be used to get additional information about the field. + * Use the getEntityName() method to get the Entity name that the field is in. + * + * @return return the name of the Entity Field that corresponds with this field + */ + public String getFieldName() { + if (UtilValidate.isNotEmpty(this.fieldName)) + return this.fieldName; + return this.name; + } + + public String getHeaderLink() { + return headerLink; + } + + public String getHeaderLinkStyle() { + return headerLinkStyle; + } + + public String getIdName() { + if (UtilValidate.isNotEmpty(idName)) + return idName; + return this.modelForm.getName() + "_" + this.getFieldName(); + } + public Map<String, ? extends Object> getMap(Map<String, ? extends Object> context) { if (UtilValidate.isEmpty(this.mapAcsr)) return this.modelForm.getDefaultMap(context); //Debug.logInfo("Getting Map from default of the form because of no mapAcsr for field " + this.getName(), module); @@ -766,17 +413,8 @@ public class ModelFormField { return result; } - /** - * Gets the name of the Entity Field that corresponds - * with this field. This can be used to get additional information about the field. - * Use the getEntityName() method to get the Entity name that the field is in. - * - * @return return the name of the Entity Field that corresponds with this field - */ - public String getFieldName() { - if (UtilValidate.isNotEmpty(this.fieldName)) - return this.fieldName; - return this.name; + public FlexibleMapAccessor<Map<String, ? extends Object>> getMapAcsr() { + return mapAcsr; } /** Get the name of the Map in the form context that contains the entry, @@ -793,10 +431,26 @@ public class ModelFormField { return this.modelForm.getDefaultMapName(); } + public ModelForm getModelForm() { + return modelForm; + } + public String getName() { return name; } + public List<UpdateArea> getOnChangeUpdateAreas() { + return onChangeUpdateAreas; + } + + public List<UpdateArea> getOnClickUpdateAreas() { + return onClickUpdateAreas; + } + + public String getParameterName() { + return parameterName; + } + /** * Get the name to use for the parameter for this field in the form interpreter. * For HTML forms this is the request parameter name. @@ -828,135 +482,66 @@ public class ModelFormField { return redWhen; } - public String getEvent() { - return event; + public boolean getRequiredField() { + return this.requiredField != null ? this.requiredField : false; } - public String getAction(Map<String, ? extends Object> context) { - if (UtilValidate.isNotEmpty(this.action)) - return action.expandString(context); - return null; + public String getRequiredFieldStyle() { + if (UtilValidate.isNotEmpty(this.requiredFieldStyle)) + return this.requiredFieldStyle; + return this.modelForm.getDefaultRequiredFieldStyle(); } - /** - * the widget/interaction part will be red if the date value is - * before-now (for ex. thruDate), after-now (for ex. fromDate), or by-name (if the - * field's name or entry-name or fromDate or thruDate the corresponding - * action will be done); only applicable when the field is a timestamp - * - * @param context the context - * @return true if the field should be read otherwise false - */ - public boolean shouldBeRed(Map<String, Object> context) { - // red-when (never | before-now | after-now | by-name) "by-name" - - String redCondition = this.redWhen; + public boolean getSeparateColumn() { + return this.separateColumn; + } - if ("never".equals(redCondition)) - return false; + public String getServiceName() { + if (UtilValidate.isNotEmpty(this.serviceName)) + return this.serviceName; + return this.modelForm.getDefaultServiceName(); + } - // for performance resaons we check this first, most fields will be eliminated here and the valueOfs will not be necessary - if (UtilValidate.isEmpty(redCondition) || "by-name".equals(redCondition)) { - if ("fromDate".equals(this.name) || (this.entryAcsr != null && "fromDate".equals(this.entryAcsr.getOriginalName()))) { - redCondition = "after-now"; - } else if ("thruDate".equals(this.name) - || (this.entryAcsr != null && "thruDate".equals(this.entryAcsr.getOriginalName()))) { - redCondition = "before-now"; - } else { - return false; - } - } + public Boolean getSortField() { + return sortField; + } - boolean isBeforeNow = false; - if ("before-now".equals(redCondition)) { - isBeforeNow = true; - } else if ("after-now".equals(redCondition)) { - isBeforeNow = false; - } else { - return false; - } + public String getSortFieldAscStyle() { + return sortFieldAscStyle; + } - java.sql.Date dateVal = null; - java.sql.Time timeVal = null; - java.sql.Timestamp timestampVal = null; + public String getSortFieldDescStyle() { + return sortFieldDescStyle; + } - //now before going on, check to see if the current entry is a valid date and/or time and get the value - String value = this.getEntry(context, null); - try { - timestampVal = java.sql.Timestamp.valueOf(value); - } catch (Exception e) { - // okay, not a timestamp... - } + public String getSortFieldHelpText() { + return sortFieldHelpText; + } - if (timestampVal == null) { - try { - dateVal = java.sql.Date.valueOf(value); - } catch (Exception e) { - // okay, not a date... - } - } + public String getSortFieldHelpText(Map<String, Object> context) { + return FlexibleStringExpander.expandString(this.sortFieldHelpText, context); + } - if (timestampVal == null && dateVal == null) { - try { - timeVal = java.sql.Time.valueOf(value); - } catch (Exception e) { - // okay, not a time... - } - } - - if (timestampVal == null && dateVal == null && timeVal == null) { - return false; - } + public String getSortFieldStyle() { + if (UtilValidate.isNotEmpty(this.sortFieldStyle)) + return this.sortFieldStyle; + return this.modelForm.getDefaultSortFieldStyle(); + } - long nowMillis = System.currentTimeMillis(); - if (timestampVal != null) { - java.sql.Timestamp nowStamp = new java.sql.Timestamp(nowMillis); - if (!timestampVal.equals(nowStamp)) { - if (isBeforeNow) { - if (timestampVal.before(nowStamp)) { - return true; - } - } else { - if (timestampVal.after(nowStamp)) { - return true; - } - } - } - } else if (dateVal != null) { - java.sql.Date nowDate = new java.sql.Date(nowMillis); - if (!dateVal.equals(nowDate)) { - if (isBeforeNow) { - if (dateVal.before(nowDate)) { - return true; - } - } else { - if (dateVal.after(nowDate)) { - return true; - } - } - } - } else if (timeVal != null) { - java.sql.Time nowTime = new java.sql.Time(nowMillis); - if (!timeVal.equals(nowTime)) { - if (isBeforeNow) { - if (timeVal.before(nowTime)) { - return true; - } - } else { - if (timeVal.after(nowTime)) { - return true; - } - } - } - } + public String getSortFieldStyleAsc() { + if (UtilValidate.isNotEmpty(this.sortFieldAscStyle)) + return this.sortFieldAscStyle; + return this.modelForm.getDefaultSortFieldAscStyle(); + } - return false; + public String getSortFieldStyleDesc() { + if (UtilValidate.isNotEmpty(this.sortFieldDescStyle)) + return this.sortFieldDescStyle; + return this.modelForm.getDefaultSortFieldDescStyle(); } - public String getServiceName() { - if (UtilValidate.isNotEmpty(this.serviceName)) - return this.serviceName; - return this.modelForm.getDefaultServiceName(); + public FlexibleStringExpander getTitle() { + return title; } public String getTitle(Map<String, Object> context) { @@ -1009,28 +594,8 @@ public class ModelFormField { return this.modelForm.getDefaultTitleStyle(); } - public String getRequiredFieldStyle() { - if (UtilValidate.isNotEmpty(this.requiredFieldStyle)) - return this.requiredFieldStyle; - return this.modelForm.getDefaultRequiredFieldStyle(); - } - - public String getSortFieldStyle() { - if (UtilValidate.isNotEmpty(this.sortFieldStyle)) - return this.sortFieldStyle; - return this.modelForm.getDefaultSortFieldStyle(); - } - - public String getSortFieldStyleAsc() { - if (UtilValidate.isNotEmpty(this.sortFieldAscStyle)) - return this.sortFieldAscStyle; - return this.modelForm.getDefaultSortFieldAscStyle(); - } - - public String getSortFieldStyleDesc() { - if (UtilValidate.isNotEmpty(this.sortFieldDescStyle)) - return this.sortFieldDescStyle; - return this.modelForm.getDefaultSortFieldDescStyle(); + public FlexibleStringExpander getTooltip() { + return tooltip; } public String getTooltip(Map<String, Object> context) { @@ -1045,87 +610,32 @@ public class ModelFormField { return tooltipString; } - public String getUseWhen(Map<String, Object> context) { - if (UtilValidate.isNotEmpty(this.useWhen)) - return this.useWhen.expandString(context); - return ""; - } - - public boolean getEncodeOutput() { - return this.encodeOutput; - } - - public String getIdName() { - if (UtilValidate.isNotEmpty(idName)) - return idName; - return this.modelForm.getName() + "_" + this.getFieldName(); - } - - public String getCurrentContainerId(Map<String, Object> context) { - ModelForm modelForm = this.getModelForm(); - String idName = FlexibleStringExpander.expandString(this.getIdName(), context); - - if (modelForm != null) { - Integer itemIndex = (Integer) context.get("itemIndex"); - if ("list".equals(modelForm.getType()) || "multi".equals(modelForm.getType())) { - if (itemIndex != null) { - return idName + modelForm.getItemIndexSeparator() + itemIndex.intValue(); - } - } - } - return idName; - } - - public String getHeaderLink() { - return headerLink; + public String getTooltipStyle() { + if (UtilValidate.isNotEmpty(this.tooltipStyle)) + return this.tooltipStyle; + return this.modelForm.getDefaultTooltipStyle(); } - public String getHeaderLinkStyle() { - return headerLinkStyle; + public FlexibleStringExpander getUseWhen() { + return useWhen; } - /** - * @param string - */ - public void setIdName(String string) { - idName = string; + public String getUseWhen(Map<String, Object> context) { + if (UtilValidate.isNotEmpty(this.useWhen)) + return this.useWhen.expandString(context); + return ""; } - public boolean isUseWhenEmpty() { - if (this.useWhen == null) { - return true; - } - - return this.useWhen.isEmpty(); + public String getWidgetAreaStyle() { + if (UtilValidate.isNotEmpty(this.widgetAreaStyle)) + return this.widgetAreaStyle; + return this.modelForm.getDefaultWidgetAreaStyle(); } - public boolean shouldUse(Map<String, Object> context) { - String useWhenStr = this.getUseWhen(context); - if (UtilValidate.isEmpty(useWhenStr)) - return true; - - try { - Interpreter bsh = this.modelForm.getBshInterpreter(context); - Object retVal = bsh.eval(StringUtil.convertOperatorSubstitutions(useWhenStr)); - boolean condTrue = false; - // retVal should be a Boolean, if not something weird is up... - if (retVal instanceof Boolean) { - Boolean boolVal = (Boolean) retVal; - condTrue = boolVal.booleanValue(); - } else { - throw new IllegalArgumentException("Return value from use-when condition eval was not a Boolean: " - + (retVal != null ? retVal.getClass().getName() : "null") + " [" + retVal + "] on the field " + this.name - + " of form " + this.modelForm.getName()); - } - - return condTrue; - } catch (EvalError e) { - String errMsg = "Error evaluating BeanShell use-when condition [" + useWhenStr + "] on the field " + this.name - + " of form " + this.modelForm.getName() + ": " + e.toString(); - Debug.logError(e, errMsg, module); - //Debug.logError("For use-when eval error context is: " + context, module); - throw new IllegalArgumentException(errMsg); - } + public String getWidgetStyle() { + if (UtilValidate.isNotEmpty(this.widgetStyle)) + return this.widgetStyle; + return this.modelForm.getDefaultWidgetStyle(); } /** @@ -1141,862 +651,754 @@ public class ModelFormField { return true; } - public String getWidgetAreaStyle() { - if (UtilValidate.isNotEmpty(this.widgetAreaStyle)) - return this.widgetAreaStyle; - return this.modelForm.getDefaultWidgetAreaStyle(); + public boolean isSortField() { + return this.sortField != null && this.sortField.booleanValue(); } - public String getWidgetStyle() { - if (UtilValidate.isNotEmpty(this.widgetStyle)) - return this.widgetStyle; - return this.modelForm.getDefaultWidgetStyle(); - } + public boolean isUseWhenEmpty() { + if (this.useWhen == null) { + return true; + } - public String getTooltipStyle() { - if (UtilValidate.isNotEmpty(this.tooltipStyle)) - return this.tooltipStyle; - return this.modelForm.getDefaultTooltipStyle(); + return this.useWhen.isEmpty(); } - /** - * @param string - */ - public void setAttributeName(String string) { - attributeName = string; + public void renderFieldString(Appendable writer, Map<String, Object> context, FormStringRenderer formStringRenderer) + throws IOException { + this.fieldInfo.renderFieldString(writer, context, formStringRenderer); } /** - * @param string + * the widget/interaction part will be red if the date value is + * before-now (for ex. thruDate), after-now (for ex. fromDate), or by-name (if the + * field's name or entry-name or fromDate or thruDate the corresponding + * action will be done); only applicable when the field is a timestamp + * + * @param context the context + * @return true if the field should be read otherwise false */ - public void setEntityName(String string) { - entityName = string; - } + public boolean shouldBeRed(Map<String, Object> context) { + // red-when (never | before-now | after-now | by-name) "by-name" - /** - * @param string - */ - public void setEntryName(String string) { - entryAcsr = FlexibleMapAccessor.getInstance(string); - } + String redCondition = this.redWhen; - /** - * @param string - */ - public void setFieldName(String string) { - fieldName = string; - } + if ("never".equals(redCondition)) + return false; - /** - * @param string - */ - public void setMapName(String string) { - this.mapAcsr = FlexibleMapAccessor.getInstance(string); - } + // for performance resaons we check this first, most fields will be eliminated here and the valueOfs will not be necessary + if (UtilValidate.isEmpty(redCondition) || "by-name".equals(redCondition)) { + if ("fromDate".equals(this.name) || (this.entryAcsr != null && "fromDate".equals(this.entryAcsr.getOriginalName()))) { + redCondition = "after-now"; + } else if ("thruDate".equals(this.name) + || (this.entryAcsr != null && "thruDate".equals(this.entryAcsr.getOriginalName()))) { + redCondition = "before-now"; + } else { + return false; + } + } - /** - * @param string - */ - public void setName(String string) { - name = string; - } + boolean isBeforeNow = false; + if ("before-now".equals(redCondition)) { + isBeforeNow = true; + } else if ("after-now".equals(redCondition)) { + isBeforeNow = false; + } else { + return false; + } - /** - * @param string - */ - public void setParameterName(String string) { - parameterName = string; - } + java.sql.Date dateVal = null; + java.sql.Time timeVal = null; + java.sql.Timestamp timestampVal = null; - /** - * @param i - */ - public void setPosition(int i) { - position = Integer.valueOf(i); - } - - /** - * @param string - */ - public void setRedWhen(String string) { - redWhen = string; - } - - /** - * @param string - */ - public void setEvent(String string) { - event = string; - } - - /** - * @param string - */ - public void setAction(String string) { - this.action = FlexibleStringExpander.getInstance(string); - } - - /** - * @param string - */ - public void setServiceName(String string) { - serviceName = string; - } - - /** - * @param string - */ - public void setTitle(String string) { - this.title = FlexibleStringExpander.getInstance(string); - } - - /** - * @param string - */ - public void setTitleAreaStyle(String string) { - this.titleAreaStyle = string; - } - - /** - * @param string - */ - public void setTitleStyle(String string) { - this.titleStyle = string; - } - - /** - * @param string - */ - public void setTooltip(String string) { - this.tooltip = FlexibleStringExpander.getInstance(string); - } - - /** - * @param string - */ - public void setUseWhen(String string) { - this.useWhen = FlexibleStringExpander.getInstance(string); - } - - public void setEncodeOutput(boolean encodeOutput) { - this.encodeOutput = encodeOutput; - } - - /** - * @param string - */ - public void setWidgetAreaStyle(String string) { - this.widgetAreaStyle = string; - } - - /** - * @param string - */ - public void setWidgetStyle(String string) { - this.widgetStyle = string; - } - - /** - * @param string - */ - public void setTooltipStyle(String string) { - this.tooltipStyle = string; - } - - public boolean getSeparateColumn() { - return this.separateColumn; - } - - /** - * @param string - */ - public void setHeaderLink(String string) { - this.headerLink = string; - } - - /** - * @param string - */ - public void setHeaderLinkStyle(String string) { - this.headerLinkStyle = string; - } - - public boolean getRequiredField() { - return this.requiredField != null ? this.requiredField : false; - } - - /** - * @param required the field is required - */ - public void setRequiredField(boolean required) { - this.requiredField = required; - } - - public String getSortFieldHelpText(Map<String, Object> context) { - return FlexibleStringExpander.expandString(this.sortFieldHelpText, context); - } - - public boolean isSortField() { - return this.sortField != null && this.sortField.booleanValue(); - } - - /** - * @param sort set as sort field - */ - public void setSortField(boolean sort) { - this.sortField = Boolean.valueOf(sort); - } - - /** - * @param modelForm the model form - */ - public void setModelForm(ModelForm modelForm) { - this.modelForm = modelForm; - } - - public static abstract class FieldInfoWithOptions extends FieldInfo { - - protected FlexibleStringExpander noCurrentSelectedKey = null; - protected List<OptionSource> optionSources = new LinkedList<OptionSource>(); - - public FieldInfoWithOptions(int fieldSource, int fieldType, ModelFormField modelFormField) { - super(fieldSource, fieldType, modelFormField); + //now before going on, check to see if the current entry is a valid date and/or time and get the value + String value = this.getEntry(context, null); + try { + timestampVal = java.sql.Timestamp.valueOf(value); + } catch (Exception e) { + // okay, not a timestamp... } - // Copy constructor. - protected FieldInfoWithOptions(FieldInfoWithOptions original, ModelFormField modelFormField) { - super(original.getFieldSource(), original.getFieldType(), modelFormField); - this.noCurrentSelectedKey = original.noCurrentSelectedKey; - this.optionSources.addAll(original.optionSources); + if (timestampVal == null) { + try { + dateVal = java.sql.Date.valueOf(value); + } catch (Exception e) { + // okay, not a date... + } } - public FieldInfoWithOptions(Element element, ModelFormField modelFormField) { - super(element, modelFormField); - - noCurrentSelectedKey = FlexibleStringExpander.getInstance(element.getAttribute("no-current-selected-key")); - - // read all option and entity-options sub-elements, maintaining order - List<? extends Element> childElements = UtilXml.childElementList(element); - if (childElements.size() > 0) { - for (Element childElement : childElements) { - if ("option".equals(childElement.getTagName())) { - this.addOptionSource(new SingleOption(childElement, this)); - } else if ("list-options".equals(childElement.getTagName())) { - this.addOptionSource(new ListOptions(childElement, this)); - } else if ("entity-options".equals(childElement.getTagName())) { - this.addOptionSource(new EntityOptions(childElement, this)); - } - } - } else { - // this must be added or the multi-form select box options would not show up - this.addOptionSource(new SingleOption("Y", " ", this)); + if (timestampVal == null && dateVal == null) { + try { + timeVal = java.sql.Time.valueOf(value); + } catch (Exception e) { + // okay, not a time... } } - public List<OptionSource> getOptionSources() { - return optionSources; + if (timestampVal == null && dateVal == null && timeVal == null) { + return false; } - public List<OptionValue> getAllOptionValues(Map<String, Object> context, Delegator delegator) { - List<OptionValue> optionValues = new LinkedList<OptionValue>(); - for (OptionSource optionSource : this.optionSources) { - optionSource.addOptionValues(optionValues, context, delegator); + long nowMillis = System.currentTimeMillis(); + if (timestampVal != null) { + java.sql.Timestamp nowStamp = new java.sql.Timestamp(nowMillis); + if (!timestampVal.equals(nowStamp)) { + if (isBeforeNow) { + if (timestampVal.before(nowStamp)) { + return true; + } + } else { + if (timestampVal.after(nowStamp)) { + return true; + } + } } - return optionValues; - } - - public static String getDescriptionForOptionKey(String key, List<OptionValue> allOptionValues) { - if (UtilValidate.isEmpty(key)) - return ""; - - if (UtilValidate.isEmpty(allOptionValues)) - return key; - - for (OptionValue optionValue : allOptionValues) { - if (key.equals(optionValue.getKey())) { - return optionValue.getDescription(); + } else if (dateVal != null) { + java.sql.Date nowDate = new java.sql.Date(nowMillis); + if (!dateVal.equals(nowDate)) { + if (isBeforeNow) { + if (dateVal.before(nowDate)) { + return true; + } + } else { + if (dateVal.after(nowDate)) { + return true; + } } } - - // if we get here we didn't find a match, just return the key - return key; - } - - public String getNoCurrentSelectedKey(Map<String, Object> context) { - if (this.noCurrentSelectedKey == null) { - return null; + } else if (timeVal != null) { + java.sql.Time nowTime = new java.sql.Time(nowMillis); + if (!timeVal.equals(nowTime)) { + if (isBeforeNow) { + if (timeVal.before(nowTime)) { + return true; + } + } else { + if (timeVal.after(nowTime)) { + return true; + } + } } - return this.noCurrentSelectedKey.expandString(context); - } - - public void setNoCurrentSelectedKey(String string) { - this.noCurrentSelectedKey = FlexibleStringExpander.getInstance(string); - } - - public void addOptionSource(OptionSource optionSource) { - this.optionSources.add(optionSource); } - } - - public static class OptionValue { - protected String key; - protected String description; - public OptionValue(String key, String description) { - this.key = key; - this.description = description; - } - - public String getKey() { - return key; - } - - public String getDescription() { - return description; - } - } - - public static abstract class OptionSource { - protected FieldInfo fieldInfo; - - public abstract void addOptionValues(List<OptionValue> optionValues, Map<String, Object> context, Delegator delegator); + return false; } - public static class SingleOption extends OptionSource { - protected FlexibleStringExpander key; - protected FlexibleStringExpander description; - - public SingleOption(String key, String description, FieldInfo fieldInfo) { - this.key = FlexibleStringExpander.getInstance(key); - this.description = FlexibleStringExpander.getInstance(UtilXml.checkEmpty(description, key)); - this.fieldInfo = fieldInfo; - } + public boolean shouldUse(Map<String, Object> context) { + String useWhenStr = this.getUseWhen(context); + if (UtilValidate.isEmpty(useWhenStr)) + return true; - public SingleOption(Element optionElement, FieldInfo fieldInfo) { - this.key = FlexibleStringExpander.getInstance(optionElement.getAttribute("key")); - this.description = FlexibleStringExpander.getInstance(UtilXml.checkEmpty(optionElement.getAttribute("description"), - optionElement.getAttribute("key"))); - this.fieldInfo = fieldInfo; - } + try { + Interpreter bsh = this.modelForm.getBshInterpreter(context); + Object retVal = bsh.eval(StringUtil.convertOperatorSubstitutions(useWhenStr)); + boolean condTrue = false; + // retVal should be a Boolean, if not something weird is up... + if (retVal instanceof Boolean) { + Boolean boolVal = (Boolean) retVal; + condTrue = boolVal.booleanValue(); + } else { + throw new IllegalArgumentException("Return value from use-when condition eval was not a Boolean: " + + (retVal != null ? retVal.getClass().getName() : "null") + " [" + retVal + "] on the field " + this.name + + " of form " + this.modelForm.getName()); + } - @Override - public void addOptionValues(List<OptionValue> optionValues, Map<String, Object> context, Delegator delegator) { - optionValues.add(new OptionValue(key.expandString(context), description.expandString(context))); + return condTrue; + } catch (EvalError e) { + String errMsg = "Error evaluating BeanShell use-when condition [" + useWhenStr + "] on the field " + this.name + + " of form " + this.modelForm.getName() + ": " + e.toString(); + Debug.logError(e, errMsg, module); + //Debug.logError("For use-when eval error context is: " + context, module); + throw new IllegalArgumentException(errMsg); } } - public static class ListOptions extends OptionSource { - protected FlexibleMapAccessor<List<? extends Object>> listAcsr; - protected String listEntryName; - protected FlexibleMapAccessor<Object> keyAcsr; - protected FlexibleStringExpander description; - - public ListOptions(String listName, String listEntryName, String keyName, String description, FieldInfo fieldInfo) { - this.listAcsr = FlexibleMapAccessor.getInstance(listName); - this.listEntryName = listEntryName; - this.keyAcsr = FlexibleMapAccessor.getInstance(keyName); - this.description = FlexibleStringExpander.getInstance(description); - this.fieldInfo = fieldInfo; - } + /** + * Models the <auto-complete> element. + * + * @see <code>widget-form.xsd</code> + */ + public static class AutoComplete { + private final String autoSelect; + private final String choices; + private final String frequency; + private final String fullSearch; + private final String ignoreCase; + private final String minChars; + private final String partialChars; + private final String partialSearch; - public ListOptions(Element optionElement, FieldInfo fieldInfo) { - this.listEntryName = optionElement.getAttribute("list-entry-name"); - this.keyAcsr = FlexibleMapAccessor.getInstance(optionElement.getAttribute("key-name")); - this.listAcsr = FlexibleMapAccessor.getInstance(optionElement.getAttribute("list-name")); - this.listEntryName = optionElement.getAttribute("list-entry-name"); - this.description = FlexibleStringExpander.getInstance(optionElement.getAttribute("description")); - this.fieldInfo = fieldInfo; + public AutoComplete(Element element) { + this.autoSelect = element.getAttribute("auto-select"); + this.frequency = element.getAttribute("frequency"); + this.minChars = element.getAttribute("min-chars"); + this.choices = element.getAttribute("choices"); + this.partialSearch = element.getAttribute("partial-search"); + this.partialChars = element.getAttribute("partial-chars"); + this.ignoreCase = element.getAttribute("ignore-case"); + this.fullSearch = element.getAttribute("full-search"); } - @Override - public void addOptionValues(List<OptionValue> optionValues, Map<String, Object> context, Delegator delegator) { - List<? extends Object> dataList = UtilGenerics.checkList(this.listAcsr.get(context)); - if (dataList != null && dataList.size() != 0) { - for (Object data : dataList) { - Map<String, Object> localContext = new HashMap<String, Object>(); - localContext.putAll(context); - if (UtilValidate.isNotEmpty(this.listEntryName)) { - localContext.put(this.listEntryName, data); - } else { - Map<String, Object> dataMap = UtilGenerics.checkMap(data); - localContext.putAll(dataMap); - } - Object keyObj = keyAcsr.get(localContext); - String key = null; - if (keyObj instanceof String) { - key = (String) keyObj; - } else { - try { - key = (String) ObjectType.simpleTypeConvert(keyObj, "String", null, null); - } catch (GeneralException e) { - String errMsg = "Could not convert field value for the field: [" + this.keyAcsr.toString() - + "] to String for the value [" + keyObj + "]: " + e.toString(); - Debug.logError(e, errMsg, module); - } - } - optionValues.add(new OptionValue(key, description.expandString(localContext))); - } - } + public String getAutoSelect() { + return this.autoSelect; } - } - - public static class EntityOptions extends OptionSource { - protected String entityName; - protected String keyFieldName; - protected FlexibleStringExpander description; - protected boolean cache = true; - protected String filterByDate; - protected List<EntityFinderUtil.ConditionExpr> constraintList = null; - protected List<String> orderByList = null; - - public EntityOptions(FieldInfo fieldInfo) { - this.fieldInfo = fieldInfo; + public String getChoices() { + return this.choices; } - public EntityOptions(Element entityOptionsElement, FieldInfo fieldInfo) { - this.entityName = entityOptionsElement.getAttribute("entity-name"); - this.keyFieldName = entityOptionsElement.getAttribute("key-field-name"); - this.description = FlexibleStringExpander.getInstance(entityOptionsElement.getAttribute("description")); - this.cache = !"false".equals(entityOptionsElement.getAttribute("cache")); - this.filterByDate = entityOptionsElement.getAttribute("filter-by-date"); - - List<? extends Element> constraintElements = UtilXml.childElementList(entityOptionsElement, "entity-constraint"); - if (UtilValidate.isNotEmpty(constraintElements)) { - this.constraintList = new LinkedList<EntityFinderUtil.ConditionExpr>(); - for (Element constraintElement : constraintElements) { - constraintList.add(new EntityFinderUtil.ConditionExpr(constraintElement)); - } - } - - List<? extends Element> orderByElements = UtilXml.childElementList(entityOptionsElement, "entity-order-by"); - if (UtilValidate.isNotEmpty(orderByElements)) { - this.orderByList = new LinkedList<String>(); - for (Element orderByElement : orderByElements) { - orderByList.add(orderByElement.getAttribute("field-name")); - } - } - - this.fieldInfo = fieldInfo; + public String getFrequency() { + return this.frequency; } - public String getEntityName() { - return entityName; + public String getFullSearch() { + return this.fullSearch; } - public String getKeyFieldName() { - if (UtilValidate.isNotEmpty(this.keyFieldName)) - return this.keyFieldName; - return this.fieldInfo.getModelFormField().getFieldName(); // get the modelFormField fieldName + public String getIgnoreCase() { + return this.ignoreCase; } - @Override - public void addOptionValues(List<OptionValue> optionValues, Map<String, Object> context, Delegator delegator) { - // first expand any conditions that need expanding based on the current context - EntityCondition findCondition = null; - if (UtilValidate.isNotEmpty(this.constraintList)) { - List<EntityCondition> expandedConditionList = new LinkedList<EntityCondition>(); - for (EntityFinderUtil.Condition condition : constraintList) { - ModelEntity modelEntity = delegator.getModelEntity(this.entityName); - if (modelEntity == null) { - throw new IllegalArgumentException("Error in entity-options: could not find entity [" + this.entityName - + "]"); - } - EntityCondition createdCondition = condition.createCondition(context, modelEntity, - delegator.getModelFieldTypeReader(modelEntity)); - if (createdCondition != null) { - expandedConditionList.add(createdCondition); - } - } - findCondition = EntityCondition.makeCondition(expandedConditionList); - } - - try { - Locale locale = UtilMisc.ensureLocale(context.get("locale")); - - List<GenericValue> values = null; - values = EntityQuery.use(delegator).from(this.entityName).where(findCondition).orderBy(this.orderByList).cache(this.cache).queryList(); - // filter-by-date if requested - if ("true".equals(this.filterByDate)) { - values = EntityUtil.filterByDate(values, true); - } else if (!"false".equals(this.filterByDate)) { - // not explicitly true or false, check to see if has fromDate and thruDate, if so do the filter - ModelEntity modelEntity = delegator.getModelEntity(this.entityName); - if (modelEntity != null && modelEntity.isField("fromDate") && modelEntity.isField("thruDate")) { - values = EntityUtil.filterByDate(values, true); - } - } - - for (GenericValue value : values) { - // add key and description with string expansion, ie expanding ${} stuff, passing locale explicitly to expand value string because it won't be found in the Entity - MapStack<String> localContext = MapStack.create(context); - // Rendering code might try to modify the GenericEntity instance, - // so we make a copy of it. - Map<String, Object> genericEntityClone = UtilGenerics.cast(value.clone()); - localContext.push(genericEntityClone); - - // expand with the new localContext, which is locale aware - String optionDesc = this.description.expandString(localContext, locale); - - Object keyFieldObject = value.get(this.getKeyFieldName()); - if (keyFieldObject == null) { - throw new IllegalArgumentException( - "The entity-options identifier (from key-name attribute, or default to the field name) [" - + this.getKeyFieldName() + "], may not be a valid key field name for the entity [" - + this.entityName + "]."); - } - String keyFieldValue = keyFieldObject.toString(); - optionValues.add(new OptionValue(keyFieldValue, optionDesc)); - } - } catch (GenericEntityException e) { - Debug.logError(e, "Error getting entity options in form", module); - } + public String getMinChars() { + return this.minChars; } - } - - public static class InPlaceEditor { - protected FlexibleStringExpander url; - protected String cancelControl; - protected String cancelText; - protected String clickToEditText; - protected String fieldPostCreation; - protected String formClassName; - protected String highlightColor; - protected String highlightEndColor; - protected String hoverClassName; - protected String htmlResponse; - protected String loadingClassName; - protected String loadingText; - protected String okControl; - protected String okText; - protected String paramName; - protected String savingClassName; - protected String savingText; - protected String submitOnBlur; - protected String textBeforeControls; - protected String textAfterControls; - protected String textBetweenControls; - protected String updateAfterRequestCall; - protected String rows; - protected String cols; - protected Map<FlexibleMapAccessor<Object>, Object> fieldMap; - public InPlaceEditor(Element element) { - this.setUrl(element.getAttribute("url")); - this.cancelControl = element.getAttribute("cancel-control"); - this.cancelText = element.getAttribute("cancel-text"); - this.clickToEditText = element.getAttribute("click-to-edit-text"); - this.fieldPostCreation = element.getAttribute("field-post-creation"); - this.formClassName = element.getAttribute("form-class-name"); - this.highlightColor = element.getAttribute("highlight-color"); - this.highlightEndColor = element.getAttribute("highlight-end-color"); - this.hoverClassName = element.getAttribute("hover-class-name"); - this.htmlResponse = element.getAttribute("html-response"); - this.loadingClassName = element.getAttribute("loading-class-name"); - this.loadingText = element.getAttribute("loading-text"); - this.okControl = element.getAttribute("ok-control"); - this.okText = element.getAttribute("ok-text"); - this.paramName = element.getAttribute("param-name"); - this.savingClassName = element.getAttribute("saving-class-name"); - this.savingText = element.getAttribute("saving-text"); - this.submitOnBlur = element.getAttribute("submit-on-blur"); - this.textBeforeControls = element.getAttribute("text-before-controls"); - this.textAfterControls = element.getAttribute("text-after-controls"); - this.textBetweenControls = element.getAttribute("text-between-controls"); - this.updateAfterRequestCall = element.getAttribute("update-after-request-call"); + public String getPartialChars() { + return this.partialChars; + } - Element simpleElement = UtilXml.firstChildElement(element, "simple-editor"); - this.rows = simpleElement.getAttribute("rows"); - this.cols = simpleElement.getAttribute("cols"); + public String getPartialSearch() { + return this.partialSearch; + } + } - this.fieldMap = EntityFinderUtil.makeFieldMap(element); + /** + * Models the <check> element. + * + * @see <code>widget-form.xsd</code> + */ + public static class CheckField extends FieldInfoWithOptions { + public final static String ROW_SUBMIT_FIELD_NAME = "_rowSubmit"; + private final FlexibleStringExpander allChecked; + + private CheckField(CheckField original, ModelFormField modelFormField) { + super(original, modelFormField); + this.allChecked = original.allChecked; } - public String getUrl(Map<String, Object> context) { - if (this.url != null) { - return this.url.expandString(context); - } else { - return ""; - } + public CheckField(Element element, ModelFormField modelFormField) { + super(element, modelFormField); + allChecked = FlexibleStringExpander.getInstance(element.getAttribute("all-checked")); } - public String getCancelControl() { - return this.cancelControl; + public CheckField(int fieldSource, ModelFormField modelFormField) { + super(fieldSource, FieldInfo.CHECK, modelFormField); + this.allChecked = FlexibleStringExpander.getInstance(""); } - public String getCancelText() { - return this.cancelText; + public CheckField(ModelFormField modelFormField) { + super(FieldInfo.SOURCE_EXPLICIT, FieldInfo.CHECK, modelFormField); + this.allChecked = FlexibleStringExpander.getInstance(""); } - public String getClickToEditText() { - return this.clickToEditText; + @Override + public void accept(ModelFieldVisitor visitor) { + visitor.visit(this); } - public String getFieldPostCreation() { - return this.fieldPostCreation; + @Override + public FieldInfo copy(ModelFormField modelFormField) { + return new CheckField(this, modelFormField); } - public String getFormClassName() { - return this.formClassName; + public FlexibleStringExpander getAllChecked() { + return allChecked; } - public String getHighlightColor() { - return this.highlightColor; + public Boolean isAllChecked(Map<String, Object> context) { + String allCheckedStr = this.allChecked.expandString(context); + if (!allCheckedStr.isEmpty()) + return Boolean.valueOf("true".equals(allCheckedStr)); + else + return null; } - public String getHighlightEndColor() { - return this.highlightEndColor; + @Override + public void renderFieldString(Appendable writer, Map<String, Object> context, FormStringRenderer formStringRenderer) + throws IOException { + formStringRenderer.renderCheckField(writer, context, this); } + } - public String getHoverClassName() { - return this.hoverClassName; + /** + * Models the <container> element. + * + * @see <code>widget-form.xsd</code> + */ + public static class ContainerField extends FieldInfo { + + private ContainerField(ContainerField original, ModelFormField modelFormField) { + super(original.getFieldSource(), original.getFieldType(), modelFormField); } - public String getHtmlResponse() { - return this.htmlResponse; + public ContainerField(Element element, ModelFormField modelFormField) { + super(element, modelFormField); } - public String getLoadingClassName() { - return this.loadingClassName; + public ContainerField(int fieldSource, int fieldType, ModelFormField modelFormField) { + super(fieldSource, fieldType, modelFormField); } - public String getLoadingText() { - return this.loadingText; + @Override + public void accept(ModelFieldVisitor visitor) { + visitor.visit(this); } - public String getOkControl() { - return this.okControl; + @Override + public FieldInfo copy(ModelFormField modelFormField) { + return new ContainerField(this, modelFormField); } - public String getOkText() { - return this.okText; + @Override + public void renderFieldString(Appendable writer, Map<String, Object> context, FormStringRenderer formStringRenderer) + throws IOException { + formStringRenderer.renderContainerFindField(writer, context, this); } + } - public String getParamName() { - return this.paramName; + /** + * Models the <date-find> element. + * + * @see <code>widget-form.xsd</code> + */ + public static class DateFindField extends DateTimeField { + private final String defaultOptionFrom; + private final String defaultOptionThru; + + private DateFindField(DateFindField original, ModelFormField modelFormField) { + super(original, modelFormField);
[... 4377 lines stripped ...]