So I have a bean like this. It holds the currentPara which will be used later in another bean (which should only hold one type of Para).
This currentPara is either a ParaA or a ParaB.
public class ParaBuilderBean {
private Para currentPara;
private ParaA paraA;
private ParaB paraB;
}
public class ParaA extends Para{
private List<String> strings;
private String currentString;
}
public class ParaB extends Para{
private int min;
private int max;
}
For each ParaX there is a p:commandButton. By clicking on one, the matched .xhtml gets set in paraPanelBean. This is my main.xhtml.
<h:panelGrid>
<p:commandButton value="ParaA" update="#form" actionListener="#{paraPanelBean.setCurrentPanel('paraAPanel')}"/>
<p:commandButton value="ParaB" update="#form" actionListener="#{paraPanelBean.setCurrentPanel('paraBPanel')}"/>
<ui:include src="#{paraPanelBean.currentPanel}.xhtml" />
</h:panelGrid>
So for each type of Para there should be a different .xhtml. Each .xhtml holds individual elements to set the fields of its Para type. For example paraAPanel.xhtml:
<h:panelGrid>
<p:outputLabel value="Enter String" />
<p:inputText value="#{paraBuilderBean.paraA.currentString}"/>
<p:commandButton value="Add" ajax="false">
<p:collector value="#{paraBuilderBean.paraA.currentString}" unique="false" addTo="#{paraBuilderBean.paraA.strings}"></p:collector>
</p:commandButton>
</h:panelGrid>
So now my question:
How to set the currentPara of my ParaBuilderBean to the choosen one by using a p:commandButton in main.xhtml? I want to achieve something like action="#{paraBuilderBean.setCurrentPara(paraBuilderBean.paraA)}".
May be this could do the job
<p:commandButton value="ParaA" update="#form" actionListener="#{paraPanelBean.setCurrentPanel('paraAPanel')}">
<f:setPropertyActionListener target="#{paraBuilderBean.currentPara}" value="#{paraBuilderBean.paraA}" />
</p:commandButton>
Related
InputText field in the following dialog retains previous value even though I set it to blank before calling show(). The inputText field is only displayed blank when show() is called for the first time. My bean is session scoped.
<p:dialog id="dlgId" widgetVar="dlgVar" dynamic="true">
<h:form>
<h:panelGrid columns="1">
<h:outputLabel for="nametext" value="Name" />
<p:inputText id="nametext" value="#{myBean.name}" />
</h:panelGrid>
<p:commandButton value="Save" actionListener="#{myBean.saveAction}" />
</h:form>
public void add(TreeNode selectedTreeNode) {
setName("");
RequestContext.getCurrentInstance().execute("PF('dlgVar').show()");
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return name;
}
How can I get the inputTEext field to display the value I set before calling show() rather then the value previously entered by the user?
The thing is: you need to update your form. To make it, you can use one of these solutions.
Solution 1 : update it from your xhtml
<h:form id="form">
<h:panelGrid columns="1">
<h:outputLabel for="nametext" value="Name" />
<p:inputText id="nametext" value="#{myBean.name}" />
</h:panelGrid>
<p:commandButton value="Save" actionListener="#{myBean.saveAction}" update=":form" />
</h:form>
Solution 2 : update it from your managedBean
YourXhtml
<h:form id="form">
...
</h:form>
YourManagedBean
public void saveAction() {
...
name = "";
RequestContext.getCurrentInstance().update(":form");
}
You can also read this post Can I update a JSF component from a JSF backing bean method?.
Solution 3 : update it using an Ajax event
You can also add an ajax event
<p:commandButton value="Save" type="button" >
<p:ajax event="click" listener="#{myBean.saveAction}" update=":form"/>
</p:commandButton>
I am trying to pass parameters from UI to service which is managed bean. Values are not getting set to bean properties
<ui>
<p:dialog header="Account Search" widget-var="account Search">
<h:inputText id="account Name" value="#{accountSub.request.accountName}"/>
<p:commandButton id="btnSearch" update="">
<h:inputText id="account Name" value="#{accountSub.request.accountNumber}"/>
<p:commandButton id="btnSearch" update="">
<p:ajax event="click" listener="#{accountSub.process}" update="#widgetVar(resultPanel)">
</p:dialog>
</ui>
Managed Bean
#ManagedBean
#VieweScoped
public class AccountSub {
private Account request;
//getter and setter for same
public void process(){
// process logic goes here.
}
}
class Account{
private String accountName;
private String accountNumber;
//getter and setter
}
There are a couple of errors in the example.
Id of input component is not valid. You should not include space.
Ajax Event 'click' is not supported
Use form element as below.
<h:form>
<p:dialog header="Basic Dialog" widgetVar="dlg1" minHeight="40">
<h:inputText id="name" value="#{accountSub.request.accountName}"/>
<h:inputText id="number" value="#{accountSub.request.accountNumber}"/>
<p:commandButton id="btnSearch" actionListener="#{accountSub.process}">Click</p:commandButton>
</p:dialog>
</h:form>
I have a p:inputTextarea and I need the value of it while processing the form. It turned out that every time I submit the form I get all the values except the one from the textarea. #{xyzUI.description} is a String object with regular getters and setters.
<ui:composition>
<h:form id="form1">
<p:panel rendered="...">
<p:panel id="formPanel">
<p:panelGrid columns="2" cellpadding="5">
<!-- other form elements -->
<p:outputLabel>Description:</p:outputLabel>
<p:inputTextarea value="#{xyzUI.description}" style="width: 350px;" counter="display" counterTemplate="{0} characters remaining" maxlength="2000" autoResize="true" rows="4" />
<h:panelGroup />
<h:outputText id="display" />
</p:panelGrid>
<p:commandButton rendered="#{not xyzUI.noChange}" action="#{xyzUI.submitForm}" update="formPanel" ajax="true" value="Apply" >
<p:ajax update="formPanel"></p:ajax>
</p:commandButton>
</p:panel>
</p:panel>
</h:form>
<ui:composition>
In my backing bean the value is always "". I don't know what's wrong.
public void submitForm()
{
...
tmp.setDescription(description); // String is always "" while debugging
myList.add(tmp);
RequestContext.getCurrentInstance().update("content");
}
I ran your code locally and discovered the issue. In the command button, remove the p:ajax call.
PrimeFaces command buttons are ajax enabled by default.
So change this:
<p:commandButton rendered="#{not xyzUI.noChange}" action="#{xyzUI.submitForm}" update="formPanel" ajax="true" value="Apply" >
<p:ajax update="formPanel"></p:ajax>
</p:commandButton>
To this:
<p:commandButton rendered="#{not xyzUI.noChange}" action="#{xyzUI.submitForm}" update="formPanel" value="Apply" />
My backing bean for reference
#ManagedBean
#ViewScoped
public class xyzUI implements Serializable{
private static final long serialVersionUID = 6259024062406526022L;
private String description;
private boolean noChange = false;
public xyzUI(){
}
public void submitForm(){
System.out.println(description);
}
public boolean isNoChange() {
return noChange;
}
public void setNoChange(boolean noChange) {
this.noChange = noChange;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
}
I am attempting to create a dialog that will serve the purpose of both creating objects and updating them. So if I happen to click the 'new' button I will be presented a dialog containing empty fields to be filled or if I click on an edit button for an entry, that entry's data will presented in the dialog for update.
Following the example in the primefaces showcase for version 5.2, I can present the data in a read only outputText form, however when I change it to an inputText, the field remains empty. The following code is an example of what I have:
<h:form id="form">
<p:dataGrid id="guestList" var="guest" value="${guestList.guests}" columns="3" paginator="true" rows="20">
<f:facet name="header">
Guest List
</f:facet>
<p:panel>
<h:outputText value="${guest.name}" />
<br />
<h:outputText value="${guest.street}" />
<br />
<h:outputText rendered="#{guest.street2.length() gt 0}"
value="${guest.street2}" />
<h:panelGroup rendered="#{guest.street2.length() gt 0}">
<br />
</h:panelGroup>
<h:outputText value="${guest.city}, " />
<h:outputText value="${guest.state} " />
<h:outputText value="${guest.zipCode}" />
<p:commandButton update="#form:newGuestDetail" oncomplete="PF('newGuestDialog').show()" icon="ui-icon-edit" styleClass="ui-btn-inline">
<h:outputText styleClass="ui-icon ui-icon-edit" style="margin:0 auto;" />
<f:setPropertyActionListener value="#{guest}" target="#{guestList.selectedGuest}" />
</p:commandButton>
</p:panel>
</p:dataGrid>
<p:dialog header="#{guestList.hasSelected() ? 'Edit Guest' : 'New Guest'}" widgetVar="newGuestDialog" modal="true" showEffect="fade" hideEffect="fade">
<p:outputPanel id="newGuestDetail">
<h:outputText value="'#{guestList.selectedGuest.name}'"/>
<p:inputText id="guestName" value="#{guestList.hasSelected() ? '' : guestList.selectedGuest.name}" pt:placeholder="Name"/>
<p:commandButton value="#{guestList.selectedGuest == null ? 'Create Guest' : 'Update Guest'}"/>
</p:outputPanel>
</p:dialog>
</h:form>
The hasSelected() method evaluates whether the selected guest is null or not, returning true if not null. The selectedGuest should be set when the commandButton is clicked so that an object is available for retrieval by the dialog, however, with tracers in the get/set for selectedGuest, I am not seeing the setter called with the above snippet. If I remove the inputText, then even though the hasSelected is still returning false, and thus the 'New Guest' is heading the dialog, the outputText is filled with a value.
I found this great post talking about the order of execution with respect to the action, action listener, etc., but don't think this quite my issue: Differences between action and actionListener.
So the ultimate question is why will my setter get called with the command button when I only have an outputText, but with an inputText, I never see it called in the log?
I appreciate the time and help anyone can provide.
Even if we fix your problem, this construct
<p:inputText value="#{guestList.hasSelected() ? '' : guestList.selectedGuest.name}">
is not ever going to work. It needs to reference a model property, not an empty string.
You'd best just reuse the edit form and let the create button precreate an empty entity. This would simplify a lot in the view side. It'd be more easy if the entity has an #Id property which is only present when it's persisted in the database.
Here's a kickoff example:
<h:form id="entitiesForm">
<p:dataTable id="entitiesTable" value="#{bean.entities}" var="entity">
<p:column>#{entity.foo}</p:column>
<p:column>#{entity.bar}</p:column>
<p:column>
<p:commandButton id="edit" value="Edit"
process="#this" action="#{bean.edit(entity)}"
update=":entityDialog" oncomplete="PF('entityDialog').show()" />
<p:commandButton id="delete" value="Delete"
process="#this" action="#{bean.delete(entity)}"
update=":entitiesForm:entitiesTable" />
</p:column>
</p:dataTable>
<p:commandButton id="add" value="Add"
process="#this" action="#{bean.add}"
update=":entityDialog" oncomplete="PF('entityDialog').show()" />
</h:form>
<p:dialog id="entityDialog" widgetVar="entityDialog"
header="#{empty bean.entity.id ? 'New' : 'Edit'} entity">
<h:form id="entityForm">
<p:inputText id="foo" value="#{bean.entity.foo}" />
<p:inputText id="bar" value="#{bean.entity.bar}" />
<p:commandButton id="save" value="#{empty bean.entity.id ? 'Create' : 'Update'} entity"
process="#form" action="#{bean.save}"
update=":entitiesForm:entitiesTable" oncomplete="PF('entityDialog').hide()" />
</h:form>
</p:dialog>
With this #ViewScoped bean:
private List<Entity> entities; // +getter
private Entity entity; // +getter
#EJB
private EntityService entityService;
#PostConstruct
public void load() {
entities = entityService.list();
entity = null;
}
public void add() {
entity = new Entity();
}
public void edit(Entity entity) {
this.entity = entity;
}
public void save() {
entityService.save(entity); // if (id==null) em.persist() else em.merge()
load();
}
public void delete(Entity entity) {
entityService.delete(entity); // em.remove(em.find(type, id))
load();
}
See also:
Creating master-detail pages for entities, how to link them and which bean scope to choose
Keep p:dialog open when a validation error occurs after submit
Im trying to implement the modification of an entity in JSF using Primefaces.
My main view, which lists the users is the following:
<p:growl id="growlEditUnit" showDetail="true" life="12000" />
<p:dialog id="dialogEditUnit" header="Edit Unit" widgetVar="editUnitDialog" showEffect="fade" hideEffect="fade" resizable="false" >
<ui:include src="editUnit.xhtml" />
</p:dialog>
<h:form id="form2">
<p:dataTable id="units" var="unit" value="#{unitController.unitsOfLoggedInUser}" >
<f:facet name="header">
Click Edit or Delete after selecting a unit to modify or remove it
</f:facet>
<p:column headerText="Code">
#{unit.unitCode}
</p:column>
<p:column headerText="Name">
#{unit.unitName}
</p:column>
<p:column headerText="Semester" >
#{unit.semester}
</p:column>
<p:column headerText="Academic Year">
#{unit.academicYear}
</p:column>
<p:column headerText="Twitter Username">
#{unit.twitterUsername}
</p:column>
<p:column headerText="Actions">
<p:commandButton id="editButton" value="Edit" action="#{unitController.setCurrent(unit)}" update=":dialogEditUnit" oncomplete"editUnitDialog.show()" />
</p:column>
</p:dataTable>
</h:form>
This view lists all the data correctly. However, when I press the current, my aim is to set the current attribute of the managed bean (code listed below) with the unit based on the button clicked. After this I try to update the edit dialog, so it will be filled with the values of that unit, and then make it visible using the oncomplete attribute. However, it seems that the managed been method setCurrent(unit) is never called when clicking the edit button. Subsequently the dialog is shown empty. Can someone help me with what am I doing wrong?
I am posting the managed bean code too.
#ManagedBean(name = "unitController")
#ViewScoped
public class UnitController implements Serializable {
private Unit current;
private List<Unit> unitsOfLoggedInUser;
#ManagedProperty(value="#{loginController.checkedUser}")
private Lecturer lecturer;
#EJB
private web.effectinet.ejb.UnitFacade ejbFacade;
#EJB
private web.effectinet.ejb.LecturerFacade lecturerFacade;
public UnitController() {
}
#PostConstruct
public void init(){
if (lecturer.getLecturerId() == null)
unitsOfLoggedInUser = null;
else
unitsOfLoggedInUser = (List<Unit>) lecturer.getUnitCollection();
}
public List<Unit> getUnitsOfLoggedInUser() {
return unitsOfLoggedInUser;
}
public void setCurrent(Unit current) {
this.current = current;
}
public Lecturer getLecturer() {
return lecturer;
}
public void setLecturer(Lecturer lecturer) {
this.lecturer = lecturer;
}
The action attribute of the commandButton is rendered without information on the value of the unit variable.
To pass the unit to the action method of your managed bean, then you need to pass the ID of unit in an <f:param> child tag of commandButton.
<p:commandButton action="#{managedBean.actionMethod}" ........>
<f:param name="unitid" value="#{unit.id}" />
</p:commandButton>
From your action method you can get the request parameter by the name from the ExternalContext and this will give you the ID of the unit that the commandButton was pressed for in your dataTable.