EMPIREDB-355
render SelectOneListbox instead of SelectOneMenu if format attribute size ist greater than one
diff --git a/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/components/SelectTag.java b/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/components/SelectTag.java
index 412e5d6..95acf1f 100644
--- a/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/components/SelectTag.java
+++ b/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/components/SelectTag.java
@@ -25,6 +25,8 @@
import javax.el.ValueExpression;
import javax.faces.component.NamingContainer;
import javax.faces.component.UIInput;
+import javax.faces.component.UISelectOne;
+import javax.faces.component.html.HtmlSelectOneListbox;
import javax.faces.component.html.HtmlSelectOneMenu;
import javax.faces.component.visit.VisitCallback;
import javax.faces.component.visit.VisitContext;
@@ -246,15 +248,14 @@
if (getChildCount() > 0)
{
inputComponent = getInputComponent();
- if (inputComponent instanceof HtmlSelectOneMenu)
+ if (inputComponent instanceof UISelectOne)
{
this.control = (SelectInputControl) InputControlManager.getControl(SelectInputControl.NAME);
// disabled
- boolean disabled = isDisabled();
- ((HtmlSelectOneMenu) inputComponent).setDisabled(disabled);
+ setInputDisabled((UISelectOne)inputComponent, isDisabled());
// Options (sync)
- control.syncOptions((HtmlSelectOneMenu) inputComponent, textResolver, selectInputInfo);
- setInputValue((HtmlSelectOneMenu) inputComponent);
+ control.syncOptions((UISelectOne) inputComponent, textResolver, selectInputInfo);
+ setInputValue((UISelectOne) inputComponent);
}
else
{ // Something's wrong here?
@@ -366,19 +367,14 @@
throw new InvalidPropertyException("inputControl", getInputControl());
// create component
this.control = (SelectInputControl)inputControl;
- HtmlSelectOneMenu input = control.createMenuComponent(this);
- // css style
- String userStyle = StringUtils.toString(getAttributes().get("styleClass"));
- String cssStyle = TagEncodingHelper.assembleStyleClassString("eSelect", null, null, userStyle);
- input.setStyleClass(cssStyle);
+ Object size = getAttributes().get("size");
+ UISelectOne input = control.createSelectComponent(this, FacesContext.getCurrentInstance(), size);
// other attributes
copyAttributes(input);
- input.setId(SELECT_COMPONENT_ID);
// Options
control.initOptions(input, textResolver, selectInputInfo);
// disabled
- boolean disabled = isDisabled();
- input.setDisabled(disabled);
+ boolean disabled = setInputDisabled(input, isDisabled());
control.addRemoveDisabledStyle(input, disabled);
// input.setLabel(getLabelString());
// input.setRequired(col.isRequired() && !col.isAutoGenerated());
@@ -387,7 +383,7 @@
return input;
}
- protected void setInputValue(HtmlSelectOneMenu input)
+ protected void setInputValue(UISelectOne input)
{
Object value = getValue();
if (value != null)
@@ -400,11 +396,11 @@
input.setValue(value);
}
- protected void copyAttributes(HtmlSelectOneMenu input)
+ protected void copyAttributes(UISelectOne input)
{
// set id
String inputId = this.getId();
- if (StringUtils.isNotEmpty(inputId))
+ if (StringUtils.isNotEmpty(inputId) && !inputId.startsWith("j_"))
{ // remove trailing underscore (workaround since parent and child may not have the same name)
if (inputId.endsWith("_"))
{
@@ -412,21 +408,21 @@
}
input.setId(inputId);
}
-
- Map<String, Object> attr = getAttributes();
- Object value;
- if ((value = attr.get("style")) != null)
- {
- input.setStyle(StringUtils.toString(value));
+ else
+ { // always set to CompoentID
+ input.setId(SELECT_COMPONENT_ID);
}
- if ((value = attr.get("tabindex")) != null)
- {
- input.setTabindex(StringUtils.toString(value));
- }
- if ((value = attr.get("onchange")) != null)
- {
- input.setOnchange(StringUtils.toString(value));
- }
+
+ Map<String, Object> tagMap = getAttributes();
+ Map<String, Object> inputMap = input.getAttributes();
+ // css style
+ String userStyle = StringUtils.toString(tagMap.get("styleClass"));
+ String cssStyle = TagEncodingHelper.assembleStyleClassString("eSelect", null, null, userStyle);
+ inputMap.put("styleClass", cssStyle);
+ // other
+ copyAttribute(inputMap, tagMap, "style");
+ copyAttribute(inputMap, tagMap, "tabindex");
+ copyAttribute(inputMap, tagMap, "onchange");
}
protected void addAttachedObjects(FacesContext context, UIInput inputComponent)
@@ -442,4 +438,25 @@
if (aoh!=null)
aoh.updateAttachedObjects(this, context, null, inputComponent);
}
+
+ protected boolean setInputDisabled(UISelectOne input, boolean disabled)
+ {
+ if (input instanceof HtmlSelectOneMenu)
+ ((HtmlSelectOneMenu)input).setDisabled(disabled);
+ else if (input instanceof HtmlSelectOneListbox)
+ ((HtmlSelectOneListbox)input).setDisabled(disabled);
+ else
+ log.warn("Unable to set disabled attribute!");
+ return disabled;
+ }
+
+ protected void copyAttribute(Map<String, Object> inputMap, Map<String, Object> tagMap, String name)
+ {
+ Object value = tagMap.get(name);
+ if (value==null) // Empty String must be allowed!
+ return;
+ // set
+ inputMap.put(name, String.valueOf(value));
+ }
+
}
diff --git a/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/controls/SelectInputControl.java b/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/controls/SelectInputControl.java
index be78fed0..619cf5e 100644
--- a/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/controls/SelectInputControl.java
+++ b/empire-db-jsf2/src/main/java/org/apache/empire/jsf2/controls/SelectInputControl.java
@@ -24,6 +24,8 @@
import javax.el.ValueExpression;
import javax.faces.component.UIComponent;
import javax.faces.component.UISelectItem;
+import javax.faces.component.UISelectOne;
+import javax.faces.component.html.HtmlSelectOneListbox;
import javax.faces.component.html.HtmlSelectOneMenu;
import javax.faces.context.FacesContext;
import javax.faces.event.PhaseId;
@@ -47,25 +49,44 @@
public static final String VALUE_EXPRESSION_FLAG = "VALUE_EXPRESSION_FLAG";
+ public static final String FORMAT_SIZE = "size:";
+
+ public static final String FORMAT_SIZE_ATTR = "format:size";
+
public static final String NAME = "select";
- private final Class<? extends HtmlSelectOneMenu> inputComponentClass;
+ private final Class<? extends HtmlSelectOneMenu> menuComponentClass;
+
+ private final Class<? extends HtmlSelectOneListbox> listComponentClass;
- public SelectInputControl(String name, Class<? extends HtmlSelectOneMenu> inputComponentClass)
+ public SelectInputControl(String name, Class<? extends HtmlSelectOneMenu> menuComponentClass, Class<? extends HtmlSelectOneListbox> listComponentClass)
{
super(name);
- this.inputComponentClass = inputComponentClass;
+ this.menuComponentClass = menuComponentClass;
+ this.listComponentClass = listComponentClass;
}
public SelectInputControl()
{
- this(SelectInputControl.NAME, HtmlSelectOneMenu.class);
+ this(SelectInputControl.NAME, HtmlSelectOneMenu.class, HtmlSelectOneListbox.class);
}
/* for SelectTag (when no column is available) */
- public HtmlSelectOneMenu createMenuComponent(UIComponent parent)
+ public UISelectOne createSelectComponent(UIComponent parent, FacesContext context, Object formatSize)
{
- return InputControlManager.createComponent(FacesContext.getCurrentInstance(), this.inputComponentClass);
+ Class<? extends UISelectOne> selectOneClass;
+ int listSize = ObjectUtils.getInteger(formatSize, 1);
+ if (listSize==-1 || listSize>1)
+ selectOneClass = this.listComponentClass;
+ else
+ selectOneClass = this.menuComponentClass;
+ // create now
+ UISelectOne selectOne = InputControlManager.createComponent(context, selectOneClass);
+ // set list size
+ if ((selectOne instanceof HtmlSelectOneListbox) && listSize>1)
+ ((HtmlSelectOneListbox)selectOne).setSize(listSize);
+ // done
+ return selectOne;
}
@Override
@@ -74,16 +95,16 @@
// check params
if (!compList.isEmpty())
throw new InvalidArgumentException("compList", compList);
- // create
- HtmlSelectOneMenu input = InputControlManager.createComponent(context, this.inputComponentClass);
+ // create list or menu
+ Object formatSize = getFormatOption(ii, FORMAT_SIZE, FORMAT_SIZE_ATTR);
+ UISelectOne input = createSelectComponent(parent, context, formatSize);
// setValueExpressionFlag
Object value = ii.getValue(false);
input.getAttributes().put(SelectInputControl.VALUE_EXPRESSION_FLAG, (value instanceof ValueExpression));
// copy Attributes
copyAttributes(parent, ii, input);
// disabled
- boolean disabled = ii.isDisabled();
- input.setDisabled(disabled);
+ boolean disabled = setDisabled(input, ii);
// Options
initOptions(input, ii.getTextResolver(), ii);
// add
@@ -99,16 +120,15 @@
protected void updateInputState(List<UIComponent> compList, InputInfo ii, FacesContext context, PhaseId phaseId)
{
UIComponent comp = compList.get(0);
- if (!(comp instanceof HtmlSelectOneMenu))
+ if (!(comp instanceof UISelectOne))
{
throw new UnexpectedReturnValueException(comp.getClass().getName(), "parent.getChildren()");
}
- HtmlSelectOneMenu input = (HtmlSelectOneMenu)comp;
+ UISelectOne input = (UISelectOne)comp;
// required
addRemoveStyle(input, InputControl.STYLECLASS_REQUIRED, ii.isRequired());
// disabled
- boolean disabled = ii.isDisabled();
- input.setDisabled(disabled);
+ boolean disabled = setDisabled(input, ii);
// check phase
if (phaseId!=PhaseId.APPLY_REQUEST_VALUES)
{ // Options (sync)
@@ -122,9 +142,23 @@
setInputValue(input, ii);
}
}
-
- protected boolean isEmptyEntryRequired(Options options, InputInfo ii, Object currentValue)
+
+ protected boolean setDisabled(UISelectOne input, InputInfo ii)
{
+ boolean disabled = ii.isDisabled();
+ if (input instanceof HtmlSelectOneMenu)
+ ((HtmlSelectOneMenu)input).setDisabled(disabled);
+ else if (input instanceof HtmlSelectOneListbox)
+ ((HtmlSelectOneListbox)input).setDisabled(disabled);
+ else
+ log.warn("Unable to set disabled attribute!");
+ return disabled;
+ }
+
+ protected boolean isEmptyEntryRequired(UISelectOne input, Options options, InputInfo ii, Object currentValue)
+ {
+ if (input instanceof HtmlSelectOneListbox)
+ return false; // not for listbox
if (options!=null && options.containsNull())
{ // already has an empty option
return false;
@@ -147,7 +181,7 @@
return ObjectUtils.isEmpty(currentValue);
}
- public void initOptions(HtmlSelectOneMenu input, TextResolver textResolver, InputInfo ii)
+ public void initOptions(UISelectOne input, TextResolver textResolver, InputInfo ii)
{
// get the options
Options options = ii.getOptions();
@@ -161,7 +195,7 @@
}
// current
Object currentValue = ii.getValue(true);
- if (isEmptyEntryRequired(options, ii, currentValue))
+ if (isEmptyEntryRequired(input, options, ii, currentValue))
{ // Empty entry
addSelectItem(input, textResolver, new OptionEntry(null, getNullText(ii)));
}
@@ -181,7 +215,7 @@
}
}
- public void syncOptions(HtmlSelectOneMenu input, TextResolver textResolver, InputInfo ii)
+ public void syncOptions(UISelectOne input, TextResolver textResolver, InputInfo ii)
{
// get the options
Options options = ii.getOptions();
@@ -194,7 +228,7 @@
return;
}
Object currentValue = ii.getValue(true);
- boolean hasEmpty = isEmptyEntryRequired(options, ii, currentValue);
+ boolean hasEmpty = isEmptyEntryRequired(input, options, ii, currentValue);
// boolean isInsideUIData = ii.isInsideUIData();
// Compare child-items with options
Iterator<OptionEntry> ioe = options.iterator();