richfaces:combobox this week's mystery.
karlkras Jul 2, 2010 9:12 PMHello, (Sorry for the length, but I got going and this is what I came up with)
So instead of a standard selectone JSF control, I'm looking at using the combobox richfaces control.
Now I'm about to throw my PC out of the window after 2+ hours trying to get it working.
The objects I'm trying to select from (one only in this case) are n number of users. The names of which can be duplicates, e.g., Smith, John but they have to have unique number ids, so in psudo code the object may look like this...
class MyClient() {
private String first;
private String last;
private int ID;
public String toString() {
return last + ", ' + first;
}
public MyClient(int ID, String first, String last) {
this.ID = ID;
this.first = first;
this.last = last;
}
public String getFirst() {
return first;
}
public String getLast() {
return last;
}
public Integer getID() {
return ID;
}
}
again, ID is the unique item for a myClient, but I need to list them in the selection control via their name.
so my attempt at a converter goes something like this:
public class ClientConverter implements javax.faces.convert.Converter {
private static final Logger LOG = LogManager.getLogger(ClientConverter.class);
@SuppressWarnings("unchecked")
@Override
public Object getAsObject(FacesContext context, UIComponent component, String value) {
List<SelectItem> selectItems = (List<SelectItem>) component.getAttributes().get("selectItems");
if (selectItems != null) {
LOG.info("Doing the select thing...");
Iterator<SelectItem> iterator = selectItems.iterator();
while (iterator.hasNext()) {
SelectItem selItem = iterator.next();
return (MyClient) selItem.getValue();
}
} else {
LOG.info("Select was null");
}
return null;
}
public String getAsString(FacesContext context, UIComponent component, Object value) {
if (value == null || !(value instanceof MyClient)) {
return "";
}
LOG.info("returning a MyClient object. " + ((MyClient) value).toString() );
return ((MyClient) value).toString();
}
}
#1, the getAsString method works fine but the getAsObject method is hosed. Since the value parameter is nothing more then the last, first name of the item that was set as the value in the list, and it can be a duplicate of another name pair in the list I can't use this as an index into the array of MyClient objects (which is what the List<SelectItem> selectItems = (List<SelectItem>) component.getAttributes().get("selectItems"); call returns) so I'm right back where I started, I can't fully identify the choice that was made. Since the combobox only supports the the value attribute I'm at a loss on how to fix this.
Oh, and another problem, but I don't really care about this as much now since I ran into this gem, my handlers aren't getting called when a change is issued in the combo control. The list is rendered just fine but when a selection is made in the related f:selectItems control the value setter in the bean is never fired, and of course, neither is the getAsObject entry point in the conveter...
oh... here's the JSP stuff:
<h:outputText value="Requestor:" styleClass="required"/>
<rich:comboBox id="client" value="#{projectbean.salesRepID}" listStyle="text-align: left;" defaultLabel="-- Select One --">
<f:attribute name="selectItems" value="#{projectbean.salesRepsItems}"/>
<f:selectItems value="#{projectbean.salesRepsItems}" />
<!-- <a4j:support ajaxSingle="true" event="onchange" reRender="nextbutton" /> -->
</rich:comboBox>
<h:outputText value="Sponsor:" styleClass="required"/>
<h:selectOneMenu id="salesrep" value="#{projectbean.salesRepID}">
<f:attribute name="selectItems" value="#{projectbean.salesRepsItems}"/>
<f:selectItems value="#{projectbean.salesRepsItems}"/>
<!-- <a4j:support ajaxSingle="true" event="onchange" reRender="nextbutton" /> -->
</h:selectOneMenu>
The selectOneMenu works sortof, the proper events are called anyway, but as stated the setter for projectbean.salesRepID is never called (I purposedly had both of these controls use the same arrrays and values to eliminate any difference these might have had otherwise.
There, now another hour of having to write this... any ideas on what I can do here?