how to refresh referenced part of page with prime faces' p:commandLink? - jsf

Environment: Tomcat 6 ,jsf 2.0,prime faces 2.2.1 ,chrome explorer
I want to click the "ViewDetail" link in the left expanded tree and show the product's detail info. But the code below didn't work.
Then I add the attribute ajax="false" to the link, it seems work. But the "p:treeTable" which lies on left part of the page is
also refreshed and collapsed. So how can I do for this: click the link on the left expanded tree node, show the info on the right part
of the page,and keep the left expanded tree node still expanded.
<h:form id="BizTypeTreeTableForm" >
<p:layout fullPage="true">
<p:layoutUnit id="left" position="left" scrollable="true" width="350" resizable="true" closable="false" collapsible="true" minWidth="250" >
<p:treeTable id="BizTypeTreeTable" value="# {treeTableController.root}" var="treeTable">
<p:column>
<f:facet name="header">ProductName</f:facet>
<h:outputText value="#{treeTable.TYPENAME.value }" />
</p:column>
<p:column style="width:5%">
<f:facet name="header">Action</f:facet>
<p:commandLink value="ViewDetail" update="content" action="#{treeTableController.showDetail}">
</p:commandLink>
</p:column>
</p:treeTable>
</p:layoutUnit>
<p:layoutUnit id="center" rendered="true" position="center" style="text-align:left;" scrollable="true" >
<h:outputText value="Please click the left tree node" rendered="# {allTabManager.productObject.TypeNo.value eq null}"/>
<div id="content" class="ui-widget">
<div class="post">
<ui:insert name="content_tab" >...</ui:insert>
</div>
</div>
</p:layoutUnit>
</p:layout>
</h:form>

The update must point to a real JSF component in the tree, not to a plain HTML element.
Replace
<div id="content" class="ui-widget">
by
<h:panelGroup layout="block" id="content" class="ui-widget">
A panelgroup with layout="block" will render a <div> instead of a <span>.

I think your reference to the id is not correct since the div and the p:layout are not the same level.
But you can either try to get the absolute id by using update=":content" or update the whole p:layoutUnit:
<p:commandLink value="ViewDetail"
update="center"
action="#{treeTableController.showDetail}">

Related

Primefaces panels appear open when collapsed is set to true

By default when page is loaded the panel appear close because i have the attribute collapsed="true". I want that when i edit an add automatically the panel updates, the update works fine but all the panels appear open even though i have collapsed set to true. I dont know why this happens. Does any knows why? and how to solve this?
addView.xhtml:
<body>
<h:outputStylesheet name="./../../resources/css/cssLayout.css"/>
<ui:composition template="./../../Layouts/LayoutGeneral.xhtml">
<ui:define name="content">
<h1 style="text-align: center">Adds</h1> <br/>
<h:form id="allAddsId">
<ui:repeat value="#{addBean.allAdds}" var="add" >
<p:panel id="basic" header="#{add.title}" style="margin-bottom:20px" toggleable="true" collapsed="true" styleClass="">
<p:ajax event="toggle"/>
<h:panelGrid columns="2" style="width:100%">
<p:outputLabel value="#{add.description}" />
</h:panelGrid> <br/>
<p:separator/>
<p:commandButton value="Edit" oncomplete="PF('detail').show();" update="detailAdd" action="#{addBean.setAddAux(add)}"/>
<p:growl id="growl" showDetail="true" sticky="false" />
</p:panel>
</ui:repeat>
</h:form>
<p:dialog id="detail" header="Edit Add" widgetVar="detail">
<p:outputPanel id="detailAdd">
<h:form>
<p:outputLabel value="Title"/><br/>
<p:inputTextarea id="titleEdit" value="#{addBean.addAux.title}" rows="2" cols="50" counter="displayTE" maxlength="50" counterTemplate="{0} caracteres restantes" autoResize="false" required="true" requiredMessage="Title necesaria"/> <br/>
<p:outputLabel id="displayTE"/> <br/> <br/>
<p:outputLabel value="Description"/> <br/>
<p:inputTextarea id="opcion1" value="#{addBean.addAux.description}" rows="6" cols="50" counter="displayDE" maxlength="200" counterTemplate="{0} caracteres restantes" autoResize="false" required="true" requiredMessage="Description necesaria"/> <br/>
<p:outputLabel id="displayDE"/> <br/> <br/>
<p:separator/> <br/>
<h:panelGrid columns="1">
<p:commandButton value="Save" action="#{addBean.editAdd(addBean.addAux)}" onclick="detail.hide()" update=":allAddsId"/>
</h:panelGrid>
</h:form>
</p:outputPanel>
</p:dialog>
</ui:define>
</ui:composition>
</body>
Okey i found a solution!! i dont know if this is the best answers but here i go..
I was doing somo test and i delete p:ajax event="toggle" which is under the panel declaration and now works!! When i edit an add the list of adds automatically updates and the panels appear collapsed!! I dont why deleting that makes it works so if someone knows feel free to tell me!
Hope this help someone!

jsf required=true destroys setPropertyActionListener?

Using primefaces 4.0 and jsf 2.2.5
stmt.xhtml has 2 includes. IncludeDetail.xhtml and IncludeDuo.xhtml. IncludeDuo also includes IncludeDetail.
In IncludeDetail.xhtml the <ui:composition> Element owns no <form>, id-Attribute or any other special elements. Only <h:panelGrid>, <h:selectOneMenu> and <h:selectOneMenu>. Nothing special.
IncludeDuo.xhtml owns <p:layout> and <p:message> as child elements of <ui:composition>. Deeper inside the <p:layout> we find this piece of code:
<h:panelGrid columns="1" style="padding-left: 10px">
<h:outputText value="AS" />
<h:selectManyMenu value="#{regelBean.selectedASForNewElement}" required="true" style="height:115px">
<f:selectItems value="#{aSBean.elementList}" var="var" itemLabel="#{var.vaSl}"
itemValue="#{var.vaSl}" />
</h:selectManyMenu>
</h:panelGrid>
If I remove required="true" everything works as expected. If I leave it there, the following setPropertyActionListener won't do it's job anymore:
<h:form id="form1">
<p:dialog header="Neue Regel" widgetVar="newDuoDialog" resizable="false" id="newDuoDlg" showEffect="fade"
hideEffect="fade" modal="true" styleClass="newDialog" width="1220">
<ui:insert name="insertDuo">
<ui:include src="/includes/duoRegelStmt.xhtml" />
</ui:insert>
</p:dialog>
<p:growl id="msgs" showDetail="true" life="20000"/>
<div class="nvg-dataTable">
<p:dataTable id="dt1" var="tVar" value="#{stmtBean.elementList}"
scrollable="false" styleClass="nvg-mainTable" paginator="true"
paginatorAlwaysVisible="false" rows="10"
rowsPerPageTemplate="10,25,100" paginatorPosition="bottom"
currentPageReportTemplate="({startRecord}-{endRecord} von {totalRecords})"
emptyMessage="Keine Statements gefunden" filteredValue="#{stmtBean.filteredElements}">
<p:column styleClass="padding2" style="width:6%">
<p:commandButton value="?" update=":dlgForm"
oncomplete="PF('detDialog').show()" icon="" title="Detail">
<f:setPropertyActionListener value="#{tVar}" target="#{stmtBean.selectedElement}" />
</p:commandButton>
<p:commandButton value="N" update=""
oncomplete="PF('newDuoDialog').show()" icon="" title="Neue Regel mit diesem Statement als Grundlage">
<f:setPropertyActionListener value="#{tVar}" target="#{stmtBean.selectedElement}" />
</p:commandButton>
[ ... ]
Is this a bug or am I misusing sth?
This is expected behaviour: As you are setting the property on submit of the form the property is only set when the form is successfully submitted, which is not the case when validation fails i.e. a required field is empty.
Use process="#this" on the p:commandButton so the form is not submitted. This should work for you as you just want to open the dialog and set the property.

JSF ajax Call Error

I am getting the following Error:
Cannot find component with identifier "myForm:display" referenced from "myForm_j_idt32".
my xhtml File :
<div id="divScreen" align="center">
<div id="divPage">
<ui:insert>
<ui:include src="/banner.xhtml"></ui:include>
</ui:insert>
<h:form id="menuBarForm">
<div id="menubar_link">
<p:commandLink value="Home" action="#{loginAct.homeNavigation}" style="color: #ffffff;margin-left: 10px;" ajax="false"></p:commandLink>
<p:commandLink action="#{loginAct.dologout}" style="color: #ffffff;margin-left: 10px;" value="Logout" ajax="false"></p:commandLink>
</div>
</h:form>
<div id="divMnuAndFrm">
<div id="divMnuContnr">
<h:form id="menuForm">
<p:menu style="width: 94%;" model="#{authMenuModel.model}"></p:menu>
</h:form>
</div>
<div id="divFrmContnrwithmenu">
<div style="height: 400px; margin: 10px 0px 0px 0px;width: 100%;">
<h:form id="myForm">
<p:dataTable
var="filem"
value="#{fileViewManagementPnation.data}"
rowKey="#{filem.ftype}"
paginator="true" rows="10"
selection="#{fileViewManagementPnation.selectedFile}"
selectionMode="single"
emptyMessage="No Files Found"
>
<p:ajax event="rowSelect" update="myForm:display" oncomplete="fileDialog.show()"/>
<f:facet name="header">
:: File Management ::
</f:facet>
<p:column sortBy="#{filem.ftype}" filterBy="#{filem.ftype}" headerText="FileType">
#{filem.ftype}
</p:column>
<p:column headerText="Version" sortBy="#{filem.version}">
#{filem.version}
</p:column>
<p:column headerText="Size">
#{filem.fsize}
</p:column>
<p:column headerText="File">
Action
</p:column>
</p:dataTable>
<p:dialog header="File Details" widgetVar="fileDialog" resizable="false" width="400"
showEffect="explode" hideEffect="explode">
<h:panelGrid id="display" columns="2" cellpadding="4">
<f:facet name="header_det">
<p:graphicImage value="/images/gep_logo.gif" />
</f:facet>
<h:outputText value="File Name : " />
<h:outputText value="#{fileViewManagementPnation.selectedFile.ftype}" id="ftype"/>
<h:outputText value="Size" />
<h:outputText value="#{fileViewManagementPnation.selectedFile.fsize}" id="size"/>
<h:outputText value="File Type :" />
<h:outputText value="#{fileViewManagementPnation.selectedFile.version}" id="version"/>
</h:panelGrid>
</p:dialog>
</h:form>
</div>
</div>
</div>
<div id="divFooter">
<p>Developed and Maintained by National Informatics Centre</p>
</div>
</div>
I am trying last two weeks to make it work but still am not getting any answers.
Please kindly help me in this issue.
You should be able to use update=":myForm:display" or update="display" instead of update="myForm:display".
Take a look at NamingContainer in JSF2/Primefaces, it'll give you a bit more background information. It's because myForm:display refers to nested NamingContainer within myForm which is called myForm, but you don't have that. The component you want to update is directly witin the same NamingContainer, namely myForm. So simply call one of the above mentioned and you should be fine.
You are not calling the right component.
You are calling a component withing the same form.
calling myForm:display will look for a component with id myForm inside the current form myForm as in :myForm:myForm:display which you do not have.
So you do not need to specify the full qualified name of the form. You can use the id of the component directly as in:
Both components (the calling component, and the called component) are inside the same form so use: update="display"
So instead you can either call the component directly as in the example above, or call it using its full qualified name update =":myForm:display"

PrimeFaces Dialog + appendToBody=true not working

I'm using PF 3.5 and JSF Mojarra 2.1.
I have a dialog which I want to use appendToBody=true. This usually results in "unpredictable behavior" though.
Basically what the dialog does is, when I choose an entry (a persn entity) from a datatable, it gives me filled up input boxes which I can edit, thus editing the particular entry (person details).
Sometimes the input boxes get filled up properly with the entries data. Sometimes they dont.
This behavior does not happen with appendToBody=false.
Aside from that I'm pretty sure there are no nested forms.
As you will notice I am trying out a "One page design" with purely ajax navigation.
Main page (index.xhtml)
<h:body>
<pe:layout id="page" fullPage="true">
<!-- North -->
<pe:layoutPane id="north" position="north" minSize="140"
closable="true" resizable="false">
....
</pe:layoutPane>
<!-- West -->
<pe:layoutPane id="west" position="west" minWidth="150" size="180"
style="font-size: 14px !important;" closable="true"
styleClassHeader="menuBar" resizable="false">
<f:facet name="header">Main Menu</f:facet>
<h:form id="form1">
<p:panelMenu id="panelMenu" style="width: 160px !important">
<!-- On menu click update with Ajax centerpanel and msgPanel -->
<p:submenu label="Persons" style="font-size: 10px ">
<p:menuitem value="Person List" update=":centerpanel"
actionListener="#{layout.setAll('formPersonList.xhtml', 'Person List')}"
action="#{person.init()}">
</p:menuitem>
</p:submenu>
.....
</p:panelMenu>
</h:form>
</pe:layoutPane>
<!-- Center -->
<pe:layoutPane id="content" position="center"
style="font-size: 14px !important" styleClassHeader="menuBar">
<h:panelGroup id="centerpanel" layout="block">
<ui:include id="include" src="#{layout.navigation}" />
</h:panelGroup>
</pe:layoutPane>
</pe:layout>
The dialog is in a file formPersonList.xhtml and is outside the form
<ui:composition ....>
<h:form id="mainForm">
<p:contextMenu for="personTable">
<p:menuitem value="View Details"
process="#form" actionListener="#{person.handleSelectedPerson()}"
update=":dlgPersonGrp"
oncomplete="dlgPerson.show();">
</p:menuitem>
</p:contextMenu>
<p:dataTable id="personTable ....>
....person entities
</p:dataTable>
</h:form>
<p:dialog widgetVar="dlgPerson" showEffect="size"
width="1100" appendToBody="true">
<h:panelGroup id="dlgPersonGrp">
<ui:include src="formPerson.xhtml" />
</h:panelGroup>
</p:dialog>
</ui:composition>
Finally, the form with the input boxes: formPerson.xhtml
<ui:composition ....>
<h:form id ="subForm">
....Input boxes that are supposed to be filled up from a backing bean
and then resubmitted to edit the chosen entry
</h:form>
</ui:composition>
I have tried to dumb it down as much as possible. Let me know if you need more detail.
I know this is a old question, but I was having the same problem with Primefaces 5.
The solution was simple, I've included the attribute appendTo="#(body)" in tag.
<p:dialog header="Title" widgetVar="dlg" modal="true" appendTo="#(body)">
<h:outputText value="Dialog text..." />
<p:commandButton value="Ok" onclick="PF('dlg').close()" />
</p:dialog>
Perhaps the answer is not to use appendToBody. Do you really need it?
One of the common reasons for using appendToBody is to avoid error resulting from putting modal dialogs inside layouts. This workaround, as you've already noted, results in "unpredictable behaviour".
The better way would be just to place the dialog outside the layout.
For more details please see:
http://forum.primefaces.org/viewtopic.php?f=3&t=6154
http://forum.primefaces.org/viewtopic.php?f=3&t=16504

JSF 2 + Primefaces - Update Not Working

I'lve already searched, but even implementing the solutions I've found, I was not able to get this working. I select a row in a datatable and click on delete button to delete the selected object, but the object gets deleted but the datatable is not updated. Here's my code:
<h:form id="formPesquisa">
...
<h:panelGroup id="panelToRender" layout="block">
<h:panelGroup id="panelDataTable" rendered="#{not empty bean.dataList}" layout="block">
<div id="dataTableRegion">
<p:panel id="panelBtnsUp" styleClass="cleanPanel">
<ui:include src="/templates/btnDataList.xhtml" />
</p:panel>
<h:panelGroup id="panelTableHolder" layout="block">
<p:dataTable id="dataTableBusca" value="#{bean.dataList}" var="entidade"
rendered="#{not empty bean.dataList}" paginator="true" style="width:100%;"
selection="#{bean.entidadesSelecionadas}" onRowSelectUpdate="panelBtnsUp,panelBtnsDown,dataTableBusca"
onRowUnselectUpdate="panelBtnsUp,panelBtnsDown,dataTableBusca" rowUnselectListener="#{bean.rowUnselectListener}" selectionMode="multiple">
<p:column>
<p:graphicImage url="/icons/checkbox_no.png" rendered="#{!bean.containsSelection(entidade)}" />
<p:graphicImage url="/icons/checkbox_yes.png" rendered="#{bean.containsSelection(entidade)}" />
</p:column>
<ui:insert name="colunasPesquisa" />
</p:dataTable>
</h:panelGroup>
<p:panel id="panelBtnsDown" styleClass="cleanPanel">
<ui:include src="/templates/btnDataList.xhtml" />
</p:panel>
</div>
</h:panelGroup>
</h:panelGroup>
....
</h:form>
And the Delete Button is in the included file:
<div style="margin:5px 0;">
<p:commandButton value="#{msg['commons.excluir']}" image="delete" disabled="#{bean.disableDelete()}" action="#{bean.delete}" update="panelDataTable" />
<p:commandButton value="#{msg['commons.editar']}" image="edit" disabled="#{bean.disableEdit()}" action="#{bean.prepareEdit}" ajax="false" />
</div>
I already tried:
update="dataTableBusca"
update="panelTableHolder"
update="formPesquisa:dataTableBusca"
update="formPesquisa:panelTableHolder"
What am I doing wrong???
Thanks for any help.
The first two approaches will only work if your button and the updated elements are siblings.
For the third and the fourth approach you have to traverse all containing elements in order to get the right id. You panelTableHolder is inside two other h:panelGroup (panelToRender, panelDataTable) and a div (dataTableRegion).
Furthermore to make sure that you start from highest level, prepend a : before the form id.
Try this:
update=":formPesquisa:panelToRender:panelDataTable:dataTableRegion:panelTableHolder"
You could check in the rendered html if this is the correct path for your panelTableHolder.

Resources