You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@myfaces.apache.org by Mike Quentel <mq...@4dm-inc.com> on 2009/05/22 17:09:08 UTC
synchronising selectOneChoice and table
Using JSF 1.2 and Trinidad...
Having issues syncing selectOneChoice and table values; I would like to have
the user's selection from the selectOneChoice to dynamically update the data
appearing in a table on the same page. Having issues syncing these items; I
also wonder if there is a better approach than what I'm trying to currently
use...still new to JSF.
I have a table <tr:table> that gets populated via a SQL query whose results
fill a Vector of Hashtables, where key=column name and value=value for that
column. In other words, each Hashtable represents a row from the query.
A backend java bean Data Access Object does the assembly of Hashtable
objects into a Vector in this manner:
Statement statement = dbConnection.createStatement();
ResultSet resultSet = statement.executeQuery(sql);
while (resultSet.next()) {
Hashtable<String, String> rowHt = new Hashtable<String, String>();
for (int i = 1; i < resultSet.getMetaData().getColumnCount(); i++)
{
String fn = resultSet.getMetaData().getColumnName(i);
Object rslt = resultSet.getObject(i);
String rsltString = "";
if (rslt != null) {
rsltString = rslt.toString();
} else {
rsltString = "";
}
rowHt.put(fn, rsltString);
}
result.add(rowHt);
}
statement.close();
The Façade Backing Bean then provides the Vector to the JSF page via this
method:
public Vector<Hashtable> getPropertyRights(){
if (this.propertyRights == null) {
this.propertyRights = new PropertyRights().getPropertyRights();
}
return this.propertyRights;
}
The JSF table output looks like this:
<tr:table value="#{propertyRightBean.propertyRights}" var="row"
rowBandingInterval="1">
<tr:column headerText="Station" sortProperty="station_name"
sortable="true">
<tr:outputText value="#{row.station_name}"></tr:outputText>
</tr:column>
<tr:column headerText="River System" sortProperty="river_system"
sortable="true">
<tr:outputText value="#{row.river_system}"></tr:outputText>
</tr:column>
...
</tr:table>
Additionally, there are selectOneChoice <tr:selectOneChoice> items that are
dynamically populated:
<tr:selectOneChoice label="Station" id="stationSelectOneChoice"
valueChangeListener="#{propertyRightBean.setSelectedStationListener}"
autoSubmit="true" immediate="true">
<f:selectItems value="#{propertyRightBean.stationOptions}"/>
</tr:selectOneChoice>
<tr:selectOneChoice label="Property Type" id="propertyTypeSelectOneChoice"
unselectedLabel="(all)"
valueChangeListener="#{propertyRightBean.setSelectedPropertyTypeListener}"
autoSubmit="true" immediate="true">
<f:selectItems value="#{propertyRightBean.propertyTypeOptions}"/>
</tr:selectOneChoice>
In order to provide the options for each selectOneChoice, the Façade Backing
Bean uses the following:
private ArrayList<SelectItem> propertyTypeOptions = null;
private ArrayList<SelectItem> stationOptions = null;
public ArrayList<SelectItem> getPropertyTypeOptions() {
this.propertyTypeOptions =
getPopulatedOptions(this.propertyTypeOptions, "property_type");
return this.propertyTypeOptions;
}
public ArrayList<SelectItem> getStationOptions() {
this.stationOptions = getPopulatedOptions(this.stationOptions,
"station_name");
return this.stationOptions;
}
public ArrayList<SelectItem> getPopulatedOptions(ArrayList<SelectItem>
options, String hashKey) {
if (options == null) {
options = new ArrayList<SelectItem>();
} else {
options.clear();
}
for (int i = 0; i < propertyRights.size(); i++) {
SelectItem si = new SelectItem();
Object valueObj = propertyRights.get(i).get(hashKey);
String value = null;
if (valueObj != null) {
value = propertyRights.get(i).get(hashKey).toString();
} else {
value = "9999";
}
si.setLabel(value);
si.setValue(value);
options.add(si);
}
return options;
}
So, what I'm trying to do is make it so when the user selects an item in any
selectOneChoice list, that after the on-select event, the selected value is
used to do a query against the database (ie, the selected value becomes part
of a where clause). Perhaps this might be better done via a query against a
table in memory (the Vector of Hashtables)?
I'm beginning to suspect this approach is un-optimal at best and wrong at
worst...need advice, please. I do not understand how to bind the
controls...but would the "binding" tag attribute for selectOneChoice, or for
table, be a better way to sync these items based on user selections? Do you
have an example of this sort of functionality (ie, user selecting a choice,
then the selection causing a table to be updated)?
Many thanks for your advice on this.
Cheers,
Mike Quentel
RE: synchronising selectOneChoice and table
Posted by Mike Quentel <mq...@4dm-inc.com>.
Thank you for the advice.
I used the information on Partial Page Rendering (PPR) information described
at
http://myfaces.apache.org/trinidad/devguide/ppr.html
In particular, using the partialTriggers attribute in the table tag to
specify which selectOneChoice IDs that the table depends on.
I mistakenly thought that "PPR" was only a feature of being able to use AJAX
to submit part of the page; PPR actually refers to the kind of functionality
I was attempting to do in synchronising the selectOneChoice items with the
table. Perhaps this section of the Developer Guide should include the words
"synchronising widget events and dependencies"; just my opinion....
Also, I store a separate collection to represent the table, based on queries
that filter via the selectOneChoice events.
Thanks,
Mike Quentel
-----Original Message-----
From: Marco G
Sent: 22 May 2009 13:53
To: users@myfaces.apache.org
Subject: Re: synchronising selectOneChoice and table
Mike Quentel-3 wrote:
>
> <tr:selectOneChoice label="Station" id="stationSelectOneChoice"
> valueChangeListener="#{propertyRightBean.setSelectedStationListener}"
> autoSubmit="true" immediate="true">
> <f:selectItems value="#{propertyRightBean.stationOptions}"/>
> </tr:selectOneChoice>
> <tr:selectOneChoice label="Property Type" id="propertyTypeSelectOneChoice"
> unselectedLabel="(all)"
> valueChangeListener="#{propertyRightBean.setSelectedPropertyTypeListener}"
> autoSubmit="true" immediate="true">
> <f:selectItems value="#{propertyRightBean.propertyTypeOptions}"/>
> </tr:selectOneChoice>
>
You didn't provide the methods, which are called by the
valueChangeListeners. You either have to call
"RequestContext.getCurrentInstance().addPartialTarget(UIComponent);" there
or add partialTriggers-attribute to the tr:table to get the table refreshed
by change of the selectOneChoice.
--
View this message in context:
http://www.nabble.com/synchronising-selectOneChoice-and-table-tp23672409p236
75286.html
Sent from the MyFaces - Users mailing list archive at Nabble.com.
Re: synchronising selectOneChoice and table
Posted by Marco Grimm-2 <Ma...@rz-service-mannheim.de>.
Mike Quentel-3 wrote:
>
> <tr:selectOneChoice label="Station" id="stationSelectOneChoice"
> valueChangeListener="#{propertyRightBean.setSelectedStationListener}"
> autoSubmit="true" immediate="true">
> <f:selectItems value="#{propertyRightBean.stationOptions}"/>
> </tr:selectOneChoice>
> <tr:selectOneChoice label="Property Type" id="propertyTypeSelectOneChoice"
> unselectedLabel="(all)"
> valueChangeListener="#{propertyRightBean.setSelectedPropertyTypeListener}"
> autoSubmit="true" immediate="true">
> <f:selectItems value="#{propertyRightBean.propertyTypeOptions}"/>
> </tr:selectOneChoice>
>
You didn't provide the methods, which are called by the
valueChangeListeners. You either have to call
"RequestContext.getCurrentInstance().addPartialTarget(UIComponent);" there
or add partialTriggers-attribute to the tr:table to get the table refreshed
by change of the selectOneChoice.
--
View this message in context: http://www.nabble.com/synchronising-selectOneChoice-and-table-tp23672409p23675286.html
Sent from the MyFaces - Users mailing list archive at Nabble.com.