how to render selected checkbox value in jsf when i select checkbox - jsf-2

i have renderd checkboxes. when i select checkbox that checkbox value shoud be displayed in panel.i have written code for this but not worked
<h:selectManyCheckbox id="chkedition" value="#{newspaperBean.selectedEditions}" layout="lineDirection" styleClass="nostyle">
<f:selectItems value="#{newspaperBean.searchEditionByNewspaper()}" var="item" itemLabel="#{item.editionName}" itemValue="#{item.editionName}"/>
<f:ajax render="display" event="select"/>
</h:selectManyCheckbox>
</td>
</tr>
<tr>
<td colspan="2">
<p:panel id="display" header="You have selected">
<c:forEach items="#{newspaperBean.selectedEditions}" var="it">
<h:outputText value="#{it}"/><br/>
</c:forEach>
</p:panel>
</td>
</tr>
this worked when i submit form but i want that when i select checkbox.

Remove the event="select" attribute. This is the incorrect event to hook on. It's only triggered when you select any text in input fields and textareas, not when you click the checkbox.
<f:ajax render="display" />
The default event is already valueChange which will resolve to click in checkboxes and this is exactly what you need. You can if necessary explicitly specify it by event="click", but as said, it's the default value already, so just omit it.
Another potential problem is the <c:forEach> in the panel. This will fail if the bean is view scoped because it runs during view build time and get its own separate instance of the view scoped bean which may not contain the submitted data. You'd need to use <ui:repeat> instead.
<ui:repeat value="#{newspaperBean.selectedEditions}" var="it">
<h:outputText value="#{it}"/><br/>
</ui:repeat>
See also:
JSTL in JSF2 Facelets... makes sense?

Related

JSF 2 ui:repeat vs h:datatable behavior

I had a bad time trying to solve p:selectBooleanButton doesn't render preselected value, a lot of hours just to fix it changing ui:repeat to h:datatable.
Here is both pieces of code.
<ui:repeat value="#{presupuestoBean.getItemsPresupuestBySeccion('Parte Delantera')}" var="itemPresupuesto">
<tr>
<td><h:outputText value="#{itemPresupuesto.descripcion}"/></td>
<td>
<p:selectBooleanButton value="#{presupuestoBean.itemsPresupuestoAsignadoCambiar[itemPresupuesto.id]}" onLabel="Yes" offLabel="No" onIcon="ui-icon-check" offIcon="ui-icon-close"/>
<h:outputText value="#{presupuestoBean.itemsPresupuestoAsignadoCambiar[itemPresupuesto.id]}" />
</td>
</tr>
</ui:repeat>
(Notice that the button is showing 'FALSE (or NO)' value although the property value is 'TRUE' as displayed by outputText)
On the other hand, the exactly same code with h:datatable.
<h:dataTable value="#{presupuestoBean.getItemsPresupuestBySeccion('Parte Delantera')}" var="itemPresupuesto2">
<h:column>
<h:outputText value="#{itemPresupuesto2.descripcion}"/>
</h:column>
<h:column>
<p:selectBooleanButton value="#{presupuestoBean.itemsPresupuestoAsignadoCambiar[itemPresupuesto2.id]}" onLabel="Si" offLabel="No" onIcon="ui-icon-check" offIcon="ui-icon-close"/>
<h:outputText value="#{presupuestoBean.itemsPresupuestoAsignadoCambiar[itemPresupuesto2.id]}" />
</h:column>
</h:dataTable>
Anyone know why is this happening ??. As far as I know, this two tags could be exchangeable. (at least according the example that I saw e.g JSF 2 Repeat Tag Example)
I'm using com.sun.faces jsf-api and jsf-impl 2.2.4
Also Primefaces 4.0
You confuse view build time with view render time! BalusC posted an explanation here:
JSTL in JSF2 Facelets... makes sense?
I had the same behavior, and was not able to make work the ui:repeat properly with map and default value.
As you are using primefaces, you might also found p:dataGrid as an alternative to h:dataTable.

Dynamically added component are growing vertically

I am following the option suggested here to dynamically adding inputtext box in my PrimeFaces v3.5 application. The only problem I am facing is that the newly added inputtext are growing vertically. Screenshot is attached.
The <h:dataTable> generates a HTML <table> element wherein each iteration generates a <tr> element which represents naturally a new row.
If you don't want to generate a table at all, then you should not be using a <h:dataTable>, but e.g. <ui:repeat>.
<h:form>
<ui:repeat value="#{bean.items}" var="item">
<h:inputText value="#{item.value}" />
</ui:repeat>
<h:commandButton value="add" action="#{bean.add}" />
<h:commandButton value="submit" action="#{bean.submit}" />
</h:form>
This doesn't generate any markup and the HTML <input> elements will by default end up in a single line.

JSF not firing bean setters when using f:ajax

This is an update on a previous post I made regarding conditional rendering of page components. I can now conditionally render different components on the page based on selected user inputs using the f:ajax tag. The trouble is that when I click my commandbutton the inputs that are conditionally rendered using ajax aren't being read on submit. I am guessing it is because the whole page isn't rerendered when I add in the new components and the submit button can't see them, even though they are there. Here is the segment of my form page(it is wrapped in a h:form tag):
<h:outputLabel for="selectPersonType" value="Select Type: "/>
<h:selectOneMenu id="selectPersonType" value="#{addPersonBean.personType}" label="Person Type" required="true">
<f:selectItem itemValue=""/>
<f:selectItems value="#{listBean.personTypes}" />
<f:ajax render="results"/>
</h:selectOneMenu>
<h:message for="selectPersonType" style="color: red"/>
</h:panelGrid>
<h:panelGroup id="results">
<h:panelGroup rendered="#{addPersonBean.personType == 'STUDENT'}">
<h:outputLabel for="selectSchoolType" value="School Type: " />
<h:selectOneMenu id="selectSchoolType" value="#{addPersonBean.schoolType}">
<f:selectItems value="#{listBean.schoolTypes}" />
<f:ajax execute="selectSchoolType"/>
</h:selectOneMenu>
</h:panelGroup>
<h:panelGroup rendered="#{addPersonBean.personType == 'PATIENT'}">
<h:outputLabel for="smoker" value="Smoker? " />
<h:selectBooleanCheckbox id="smoker" value="#{addPersonBean.smoker}">
<f:ajax execute="smoker"/>
</h:selectBooleanCheckbox>
</h:panelGroup>
</h:panelGroup>
<h:commandButton value="Add Person" action="#{addPersonBean.action}"/>
The trouble here is that the components with ids 'selectSchoolType' and 'smoker's values don't get set when I click the commandButton because they are rendered conditionally using the selectPersonType select menu after the page has loaded. Is there a way to fire the components when their values change instead of when I click the submit button (therefore, their values should be processed before I even click submit). As you can see I have tried to use f:ajax with the execute attribute attached to the components in question but it didn't seem to work. (I believe the default events for these components are valueChange so haven't added them to the f:ajax tags, but I have tried 'change' and 'valueChange').
All your <f:ajax> things are inside a conditionally rendered component. This construct will fail when the condition behind rendered attribute evaluates to false during processing the form submit. This will happen when the #{addPersonBean} is in the request scope and doesn't preinitialize the condition behind the rendered attribute during (post)construction, or when it's performing business logic in getters/setters in a wrong way.
Placing the #{addPersonBean} in the view scope and ensuring that you aren't doing business logic in getters/setters should fix this problem.
See also:
commandButton/commandLink/ajax action/listener method not invoked or input value not updated - point 5 applies to you
How to choose the right bean scope?

How can I set numbers within IDs dynamically in JSF

I design a JavaEE website with the help of JSF2 and Facelets. The code beyond is just an example how the JSF-Code looks like.
When the user of the website wants to create new users but forgets to set e.g. the firstname, an error occurs and the element will be highlighted (red color and red frame around the element).
For highlighting I have to use the attribute:
class="#{faceletUtils.getLabelStyleClass('createUsersForm:allUsers:0:firstName')}"
The problem is that I have to set the number 0 dynamically but as far as I know nesting is not allowed in JSF. I could use #{curUser.number} to get the number.
Question: How can I set the numbers in the for and class attributes?
for="createUsersForm:allUsers:0:firstName"
class="#{faceletUtils.getLabelStyleClass('createUsersForm:allUsers:0:firstName')}"
An example of the JSF-Code:
<h:form id="createUsersForm">
<ui:repeat id="allUsers" value="#{createUserController.users}" var="curUser">
<div class="formLine">
<label for="createUsersForm:allUsers:0:firstName" class="#{faceletUtils.getLabelStyleClass('createUsersForm:allUsers:0:firstName')}">
<h:outputText value="#{userStaticText['user.firstName.label']}"/>
</label>
<h:inputText id="firstName" value="#{curUser.firstName}" class="#{faceletUtils.getLabelStyleClass('createUsersForm:allUsers:0:firstName')}"/>
</div>
</ui:repeat>
</h:form>
Best regards,
Jana
Just use <h:outputLabel> instead of <label>. JSF will automatically use the right for value. Further you can use #{component.clientId} to get the client ID of the current component (although I think the particular functional requirement of highlighting invalid fields can be solved in a much simpler manner).
<h:form id="createUsersForm">
<ui:repeat id="allUsers" value="#{createUserController.users}" var="curUser">
<div class="formLine">
<h:outputLabel for="firstName" styleClass="#{faceletUtils.getLabelStyleClass(component.clientId)}"
value="#{userStaticText['user.firstName.label']}"/>
<h:inputText id="firstName" value="#{curUser.firstName}" styleClass="#{faceletUtils.getLabelStyleClass(component.clientId)}"/>
</div>
</ui:repeat>
</h:form>
Note that I fixed the wrong class attribute of <h:inputText> as well.

How do I get PrimeFaces <p:selectOneMenu> to call valueChangeListener?

Using PF 3.0-RC1 Snapshot (11/22/2011)
I have a in a composite component.
I want to call the valueChangeListener when a selection is made, but it does not appear to be calling the listener.
Here is the code for the component:
<p:selectOneMenu style="width: 220px;"
value="#{customerProfileSessionBean.selectedAccount}"
valueChangeListener="#{customerProfileSessionBean.accountValueChange}" >
<f:selectItems value="#{sessionBean1.custAccountList}"/>
</p:selectOneMenu>
The listener in the backing bean has a print statement that is not being called (at least I do not see it in the server log).
Is there something else that I need to do to get the valueChangeListener to be called when the value changes?
Do I need to use ?
Also, in the listener, is there a ValueChangeEvent that is passed?
Thanks.
You seem to be expecting that the valueChangeListener method in the server side is called immediately when a change event occurs on the client side. This is not correct. It will only be invoked when the form is submitted to the server and the new value does not equals() the old value.
There are at least two ways to achieve your functional requirement:
Add onchange="submit()" so that JavaScript will submit the form whenever you change the value:
<p:selectOneMenu style="width: 220px;"
value="#{customerProfileSessionBean.selectedAccount}"
valueChangeListener="#{customerProfileSessionBean.accountValueChange}"
onchange="submit()">
<f:selectItems value="#{sessionBean1.custAccountList}"/>
</p:selectOneMenu>
This is however very JSF-1.x-ish and poor for user experience. It will also submit (and convert/validate!) all other input fields which may not be what you want.
Make use of an ajax listener instead, for sure if you are not interested in the actual value change (i.e. the old value is not interesting for you), but you're actually interested in the change event itself. You can do this using <f:ajax> or in PrimeFaces components using <p:ajax>:
<p:selectOneMenu style="width: 220px;"
value="#{customerProfileSessionBean.selectedAccount}">
<p:ajax listener="#{customerProfileSessionBean.accountValueChange}" />
<f:selectItems value="#{sessionBean1.custAccountList}"/>
</p:selectOneMenu>
And replace the ValueChangeEvent argument by the AjaxBehaviorEvent argument.
Add f:ajax statement for p:selectOneMenu , it will create ajax call and your value will be submitted EX:
<p:selectOneMenu style="width: 220px;" value="#
{customerProfileSessionBean.selectedAccount}"
valueChangeListener="#{customerProfileSessionBean.accountValueChange}" >
<f:selectItems value="#{sessionBean1.custAccountList}"/>
<f:ajax render="#form"/>
</p:selectOneMenu>
Or you can provide panel id or datatable id ,if you dont want torender the whole form, like:
<f:ajax render=":formid:panelGroupId"/>

Resources