p:resetInput does not reset the p:dialog when it is reopened - jsf

Here is some html I am writing to allow categories to be added using a dialog:
<p:dialog id="newCategoryDlg" header="Add New Category" widgetVar="newCategoryDialog" resizable="false">
<h:form id="newCategoryForm">
<p:panelGrid id="displayNewCategory" columns="2" cellpadding="4" style="margin:0 auto;">
<h:outputText value="Category Name :"></h:outputText>
<p:inputText value="#{categoryController.newCategory.name}"
required="true" requiredMessage="Please Enter a Category ID!" />
<f:facet name="footer">
<p:commandButton value="Submit" update=":form:categoryTable"
oncomplete="newCategoryDialog.hide();"
actionListener="#{categoryController.addCategory}">
<p:resetInput target="displayNewCategory" />
</p:commandButton>
<p:commandButton type="reset" value="Reset"></p:commandButton>
</f:facet>
</p:panelGrid>
</h:form>
</p:dialog>
Now, for whatever reason, "" just doesn't seem to work no matter which widget or identifier I use. All I want is for old input entries to disappear after they have been submitted. What am I doing wrong?

You misunderstood the purpose of <p:resetInput>. This misunderstanding is essentially already answered/explained here: Why does p:resetInput require properties of a managed bean to be set to null first after the form is submitted?
As to your concrete functional requirement of the need to update the dialog's content before opening, just do exactly that in the command button which opens the dialog:
<h:form>
<p:commandButton value="Open dialog" action="#{dialogBean.init}"
process="#this" update=":dialog" oncomplete="w_dialog.open()" />
</h:form>
...
<p:dialog id="dialog" widgetVar="w_dialog" ...>
Note that when the dialog contains fields which needs to be validated, then the <p:resetInput> would be very applicable in the button who's updating and opening the dialog in order to clear out invalid state.
See also:
How to show details of current row from p:dataTable in a p:dialog and update after save
Understanding PrimeFaces process/update and JSF f:ajax execute/render attributes

Related

Primefaces Panels don't update collapsed status after a dialog was dismissed

I'm seeing a strange behaviour with Primefaces (4.0) related to Panels whose collapsed-attributes are bound to a property in a backing bean. Updating the state works fine so the panel collapses/expands correctly when the value of the backing bean changes.
The problem is: I have some p:Dialogs that can be opened to enter some additional/optional information. After closing the dialog, the panel fails to expand/collapse when changing the value. Strangely, other attributes bound to the same property get updated like before.
Example:
XHTML of two panels whose collapsed Attribute is bound to a property. Note that the disabled-attribute of the checkboxes are bound to the same property and still get updated after the dialog is closed.
<p:panel id="panel1" style="width:80%;" toggleable="true" collapsed="#{!bean.panel1.enabled}" widgetVar="panel1Var">
<f:facet name="header">
<p:outputLabel value="Panel1"/>
<p:selectBooleanCheckbox id="p1_enabled" style="margin-left:20px;" disabled="#{bean.panel2.enabled}" value="#{bean.panel1.enabled}">
<f:ajax render="panel1 panel2" />
</p:selectBooleanCheckbox>
</f:facet>
<p:panelGrid columns="2" style="width:100%;" columnClasses="input-col1,input-col2">
<!-- omitted -->
</p:panelGrid>
</p:panel>
<p:panel id="panel2" style="width:80%;" toggleable="true" collapsed="#{!bean.panel2.enabled}" widgetVar="panel2Var">
<f:facet name="header">
<p:outputLabel value="Panel2"/>
<p:selectBooleanCheckbox id="p2_enabled" style="margin-left:20px;" disabled="#{bean.panel1.enabled}" value="#{bean.panel2.enabled}">
<f:ajax render="panel1 panel2" />
</p:selectBooleanCheckbox>
</f:facet>
<p:panelGrid columns="2" style="width:100%;" columnClasses="input-col1,input-col2">
<!-- omitted -->
</p:panelGrid>
</p:panel>
XHTML somewhere else on the same page which opens a dialog:
<p:commandLink id="contactbutton" onclick="PF('contactextended').show();">
<h:outputText value="Extended" />
</p:commandLink>
The dialog is configured like this:
<p:dialog widgetVar="contactextended" modal="true" width="600px" height="500px" showEffect="fade" hideEffect="fade" resizable="false" draggable="false">
The backing bean is a straightforward bean with properties and getters/setter which obviously work. Is there a problem in my implementation? Any ideas how to work around this issue?
Thanks in advance!
Fixed this by myself. The solution seems to be to add process="#this"to the commandLink. I am still not sure what the underlying problem is/was, but at least it doesn't get triggered anymore.

primefaces: Execute action before update in commandlink

I have a Dialog and a CommandLink which shows this dialog. In this Dialog i display values which has created during the action (or propertyListener) of the command link. But because the update is executed before the action, the variables are not set.
<p:commandLink update="#form:myDialog" action="#{myBean.setText('text')}"
oncomplete="myDialog.show()">
</p:commandLink>
....
<p:dialog widgetVar="myDialog" modal="true">
<p:inputText value="#{myBean.text}" />
</p:dialog>
Is it possible to execute an action before the update is done?
I dialog will update you haven't specified the Id attribute of the dialog
<p:commandLink update="myDialog" action="#{myBean.setText('text')}"
oncomplete="myDialog.show()">
</p:commandLink>
<p:dialog Id="myDialog" widgetVar="myDialog" modal="true">
<p:inputText value="#{myBean.text}" />
</p:dialog>
This will help you .
But what i prefer is use an outputpanel
<p:commandLink update="myDialogPanel " actionlistner="#{myBean.setText('text')}"
oncomplete="myDialog.show()">
</p:commandLink>
<p:dialog Id="myDialog" widgetVar="myDialog" modal="true">
<p:outputPanel Id=myDialogPanel >
<p:inputText value="#{myBean.text}" />
</p:outputPanel>
</p:dialog>
or you can update the dialog from managedBean and show the dialog. This is helpful if you get any error at your managedBean method your dialog is not show.
RequestContext.getCurrentInstance().update("myDialogPanel");
RequestContext.getCurrentInstance().execute("myDialog.show();");
You can open the Dialog from ManagedBean itself.
RequestContext.getCurrentInstance().execute(myDialog.show());
RequestContext can be used to Execute any javascript from ManagedBean.
You can also update the components from Managed Bean using RequestContext's Update
method.
RequestContext.getCurrentInstance().update("COMPONENT_ID");

<p:dialog appendToBody="true" doesn't call Converter class

I am using Primefaces 3.4.2 with JSF 2.0
I have the following in a dialog popup in JSF page.
<p:dialog header="Create New Request" style="font-weight:bold"
widgetVar="newDialog" resizable="false" id="newDlg"
showEffect="fade" hideEffect="fade" appendToBody="true"
modal="true" position="center top" width="850" height="450">
<p:panelGrid columns="2">
<h:outputLabel value="Employee" for="employee" />
<p:selectOneMenu id="employee" value="#{mymb.employee}"
converter="#{employeeConverter}">
<f:selectItems value="#{mymb.employeeItems}" var="emp"
itemLabel="#{emp.employeeName}" itemValue="#{emp.employeeNumber}"/>
<p:ajax listener="#{mymb.loadDepartments}" process="#this"/>
</p:selectOneMenu>
</p:panelGrid>
<p:separator />
</p:dialog>
If I use appendToBody="true", then selectOneMenu Converter class doesn't gets invoked, but if I make it appendToBody="false", then Converter class gets invoked.
What could be the reason for this? appendToBody="false" makes my popup dialog unusable, not able to navigate using mouse.
How can I resolve this issue?
Remove the appendToBody and put an <h:form/> inside your dialog(along with it's content).
The purpose of appendToBody="false" is to ensure your dialog is rendered within the body (and hence within the main <h:form/>) of the HTML output.
Without appendToBody="false" , the dialog might end up being appended to the end of the markup in <body/> and as a result, nothing inside it will get executed.
Adding <h:form/> to your dialog ensures that even if it winds up outside the <body/> it will still be able to submit to the server

primefaces datatable selection issue

I have some weird issue with datatable selection (most likely i'm doing something wrong).
Idea is simple - datatable with selection and a dialog to edit the records. The problem is that if i use <h:inputText> tag (or <p:inputText>) it appears to be blank, though the object in the backing bean (indicatorBean.indicator.code) contains data. Interestingly if i put <h:outputText> instead of input the data is shown.
here are contents of my body
<!-- language: xml -->
<h:body>
<h:form id="form">
<p:growl id="messages" showDetail="true"/>
<p:dataTable id="indicatorsTable" var="ind"
value="#{indicatorBean.indicators}"
selectionMode="single"
selection="#{indicatorBean.indicator}"
rowKey="#{ind.id}">
<p:column headerText="Name" style="width:125px">
#{ind.name}
</p:column>
<p:column headerText="Code" style="width:125px">
#{ind.code}
</p:column>
<f:facet name="footer">
<p:commandButton id="viewButton" value="View"
icon="ui-icon-search" update=":form:display"
oncomplete="indDialog.show()"/>
</f:facet>
</p:dataTable>
<p:dialog id="dialog" header="Indicator Detail"
widgetVar="indDialog" resizable="false"
width="400" showEffect="fade" hideEffect="fade">
<h:panelGrid id="display" columns="2" cellpadding="4">
<h:outputText value="Code:"/>
<!-- PROBLEM IS HERE -->
<h:inputText value="#{indicatorBean.indicator.code}"/>
<h:outputText value="Name:"/>
<h:outputText value="#{indicatorBean.indicator.name}"/>
</h:panelGrid>
<p:commandButton value="Save" onclick="indDialog.hide()"/>
<p:commandButton value="Cancel" onclick="indDialog.hide()"/>
</p:dialog>
</h:form>
</h:body>
Backing bean is nothing other that accessors.
Another thing i spotted is if i replace el expression in <h:inputtext> with a static text (like <h:inputText value="static text"/>), it is shown.
Here are some pictures:
Dialog with inputtext
Dialog with outputtext
Dialog with static text
primefaces 3.4
The problem as you seem to have already figured out is that you are placing the dialog itself inside of a form. This is an issue because of the way the jQuery dialog control works, which is the client side foundation of the Primefaces dialog. Essentially it will move DOM elements associated with the dialog elsewhere, possibly outside of the form that you intend to enclose it.
This problem can be easily solved by putting the dialog outside of the form, and putting a form inside of the dialog body instead.
<p:dialog id="dialogId" ...>
<h:form id="dlgForm">
....
</h:form>
</p:dialog>
In this way when jQuery UI moves the dialog control elsewhere in the DOM, the contents of that DOM, including the form come with it.

Reset input fields without executing validation

I have a Facelets view as below:
<h:form id="f1">
<p:panelGrid id="p1" columns="2">
<p: inputText value="Distance Travelled::/><p:inputText value="#{airTransportUsage.distance}" immediate="true"
required="true" requiredMessage="Distance Travelled Field cannot be left blank.."
converterMessage="Distance Travelled must be a number"
validatorMessage="Distance Travelled must be a valid number.."
id="dis">
<f:validateLongRange minimum="1"/>
</p:inputText>
<p:commandButton value="Reset" action="#{airTransportUsage.reset}" update=":f1:p1" />
</p:panelGrid>
</h:form>
When the reset button is clicked, the corresponding method can never be executed due to validation. I can't use immediate="true" on my reset button as it creates some other problems.
The <p:commandButton> processes indeed by default the entire form (process="#form"), you can change this by specifying only the current component in the process attribute.
<p:commandButton value="Reset" ... process="#this" />
However, this will fail if the form is already been validated beforehand. The input fields which have been marked invalid won't be updated with the new model value (which you've resetted yourself). If you're using PrimeFaces 3.4, then embed <p:resetInput> in the button:
<p:commandButton value="Reset" ... process="#this">
<p:resetInput target="#form" />
</p:commandButton>
If you aren't on PrimeFaces 3.4 yet and can't upgrade to it, you can use OmniFaces ResetInputAjaxActionListener for this.
A completely different alternative is to just refresh the current page by a fresh new GET request.
<p:button value="Reset" />
This worked for me in PrimeFaces 5.3
<p:commandButton action="#{bean.reset()}" value="Reset" process="#this" update="#form" resetValues="true" />
You can probably replace the "#form" target of the update attribute to a specific component if you want.

Resources