I disabled <p:poll> by default with autoStart="false" .
Now i have a dialog opened by commandButton with this example code :
<h:body>
<h:form>
<p:commandButton value="Open Dialog" oncomplete="PF('sampleDialog').show();PF('w_poll').start();"/>
<p:dialog header="Sample Dialog" height="300" width="400" widgetVar="sampleDialog" resizable="false" onHide="PF('w_poll').stop();">
<p:accordionPanel>
<p:ajax event="tabChange" oncomplete="PF('w_poll').start();"/>
<p:tab title="First">
<h:panelGroup id="firstGroup">
<p:poll interval="1"
id="firstPoll"
widgetVar="w_poll"
update="firstLabel"
async="true"
autoStart="false"
global="false"
listener="#{firstCounter.init}"/>
<p:outputLabel value="#{firstCounter.number}" id="firstLabel"/>
</h:panelGroup>
</p:tab>
<p:tab title="Second">
<h:panelGroup id="secondGroup">
<p:poll interval="3"
id="secondPoll"
widgetVar="w_poll"
update="secondLabel"
async="true"
autoStart="false"
global="false"
listener="#{secondCounter.init}"/>
<p:outputLabel value="#{secondCounter.number}" id="secondLabel"/>
</h:panelGroup>
</p:tab>
<p:tab title="Third">
<h:panelGroup id="thirdGroup">
<p:poll interval="5"
id="thirdPoll"
widgetVar="w_poll"
update="thirdLabel"
async="true"
autoStart="false"
global="false"
listener="#{thirdCounter.init}"/>
<p:outputLabel value="#{thirdCounter.number}" id="thirdLabel"/>
</h:panelGroup>
</p:tab>
</p:accordionPanel>
</p:dialog>
</h:form>
</h:body>
Note : you can see poll started on dialog show and stopped on hide .
this is my beans :
public abstract class AbstractBean implements Serializable {
private int number;
public void counter(int sleepTime) {
sleep(sleepTime);
this.number = number + 1;
}
public int getNumber() {
return number;
}
private static void sleep(int time) {
try {
Thread.sleep(time);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
now implement three bean with this abstract :
#Named
#ViewScoped
public class FirstCounter extends AbstractBean {
#PostConstruct
public void init() {
counter(1000);
}
}
and another :
#Named
#ViewScoped
public class SecondCounter extends AbstractBean {
#PostConstruct
public void init() {
counter(3000);
}
}
and another :
#Named
#ViewScoped
public class ThirdCounter extends AbstractBean {
#PostConstruct
public void init() {
counter(5000);
}
}
I have two problem :
1) first tab of accordion panel not started counter after dialog opened .
2) change tab event not work . i want to start counter of this same tab .
Related
I am not sure if I am making a silly mistake, but this has not been working for me on a very simple case: In my tabview / tabs when I switch from one tab to other I want to save the data that's entered in the form. The Submit button works fine on each tab, but the tabchange event shows all my form data to be null. I have tried process with #all, #form, #this, nothing seems to work. Same with update option.
Here's the XHTML:
<h:form id="form">
<p:growl id="msgs" showDetail="true" keepAlive="5000" />
<p:tabView id="tView" dynamic="true" cache="false" >
<p:ajax event="tabChange" listener="#{deleteMe.onTabChange}" update=":form:msgs" />
<p:tab title="MyTitle I" id="tab1">
<p:fieldset legend="Personal Information" toggleable="false" >
<h:panelGrid columns="2" cellpadding="10">
Value 1: <p:inputText value="#{deleteMe.thingOne}"></p:inputText>
Value 2: <p:inputText value="#{deleteMe.thingTwo}"></p:inputText>
<p:commandButton value="Submit" id="ajax" update=":form:msgs" action="#{deleteMe.onSubmit}" />
</h:panelGrid>
</p:fieldset>
</p:tab>
<p:tab title="MyTitle II" id="tab2">
<p:fieldset legend="Social Information" toggleable="false">
<h:panelGrid columns="2" cellpadding="10">
<p:inputText value="#{deleteMe.thingThree}"></p:inputText>
<p:commandButton value="Submit" id="ajax2" update=":form:msgs" action="#{deleteMe.onSubmit}" />
</h:panelGrid>
</p:fieldset>
</p:tab>
</p:tabView>
</h:form>
And here's my backing bean:
`
import javax.annotation.PostConstruct;
import javax.inject.Named;
import org.primefaces.event.TabChangeEvent;
import org.springframework.context.annotation.Scope;
#Named(value = "deleteMe")
#Scope("view")
public class DeleteBean implements Serializable {
private static final long serialVersionUID = 47L;
private String thingOne;
private String thingTwo;
private String thingThree;
#PostConstruct
public void initialize() {
}
public void onTabChange(TabChangeEvent event) {
System.out.println("Saving draft, current index: "+ event.getTab().getTitle());
System.out.println(thingOne);
System.out.println(thingTwo);
saveDraft();
}
public void onSubmit() {
System.out.println(thingOne);
System.out.println(thingTwo);
System.out.println(thingThree);
saveDraft();
}
public void saveDraft() {
System.out.println("This is thing 1 value: "+thingOne);
System.out.println("This is thing 2 value: "+thingTwo);
System.out.println("This is thing 2 value: "+thingThree);
}
public String getThingOne() {
return thingOne;
}
public void setThingOne(String thingOne) {
this.thingOne = thingOne;
}
public String getThingTwo() {
return thingTwo;
}
public void setThingTwo(String thingTwo) {
this.thingTwo = thingTwo;
}
public String getThingThree() {
return thingThree;
}
public void setThingThree(String thingThree) {
this.thingThree = thingThree;
}
}
`
On tabchange event, it triggers the method, but the values are all null.
SystemOut O This is thing 1 value: null
SystemOut O This is thing 2 value: null
SystemOut O This is thing 2 value: null
Can you please point out if I am making some silly mistake? Thank you.
The correct answer is to use skipChildren="false" on your p:ajax commands.
https://github.com/primefaces/primefaces/issues/2525
<p:ajax event="tabChange"
skipChildren="false"
listener="#{deleteMe.onTabChange}"
update=":form:msgs" />
I have the same problem.
On changing the tab without submitting, data will be lost because of not updating the input text field. You can add ajax for Input text field.
<p:inputText id="thingOneId" value="#{deleteMe.thingOne}">
<p:ajax update="thingOneId"/>
</p:inputText>
skipchildren="true"
works for not loosing the data, but it won't update the value from inputfields.
Saw a workaround for it but I am not sure why it is working this way:
I had to add the remote command with a tabchange listener on tabView.
<p:remoteCommand name="onTabChangeProcess" process="tView, #this"/>
<p:tabView activeIndex="#{deleteMe.activeIndex}" id="tView" onTabChange="onTabChangeProcess()">
<p:ajax event="tabChange" listener="#{deleteMe.onTabChange}" update="tView" process="tView"/>
This made the form to work as expected.
I am developing a project with Primefaces 5.1.
In my project, I used p:idleMonitor, on my Start button click the p:idleMonitor rendered="true" is working .
On my Stop button click the p:idleMonitor rendered="false" not working and the p:idleMonitor is still processing.
Sample Code:
index.xhtml
<p:panel id="mainPanelId">
<p:commandButton value="Start" update="mainPanelId" action="{Sample.start}"/>
<p:commandButton value="Stop" update="mainPanelId" action="#{Sample.stop}"/>
<p:idleMonitor timeout="5000" rendered="#{Sample.idleRendered}">
<p:ajax event="idle" oncomplete="PF('dialogId').show();"/>
<p:ajax event="active" oncomplete="PF('dialogId').hide();"/>
</p:idleMonitor>
<p:dialog id="dialogId" widgetVar="dialogId" header="Idle">
<p:outputLabel value="Idle Mode Actived!"/>
</p:dialog>
</p:panel>
Sample.java
class Sample
{
private boolean idleRendered;
public String start()
{
idleRendered = true;
return null;
}
public String stop()
{
idleRendered = false;
return null;
}
}
A few things you should do differently.
Use <h:form>
Use actionListener by p:commandButton and void methods of your bean
XHTML
<h:form>
<p:panel id="mainPanelId">
<p:commandButton value="Start" update="mainPanelId"
actionListener="#{Sample.start}" />
<p:commandButton value="Stop" update="mainPanelId"
actionListener="#{Sample.stop}" />
<h:outputText value="#{Sample.idleRendered}" />
<p:idleMonitor timeout="5000" rendered="#{Sample.idleRendered}">
<p:ajax event="idle" oncomplete="PF('dialogId').show();" />
<p:ajax event="active" oncomplete="PF('dialogId').hide();" />
</p:idleMonitor>
<p:dialog id="dialogId" widgetVar="dialogId" header="Idle">
<p:outputLabel value="Idle Mode Actived!" />
</p:dialog>
</p:panel>
</h:form>
Bean
#Named("Sample")
#SessionScoped
public class Sample implements Serializable {
private boolean idleRendered = true;
public void start() {
idleRendered = true;
}
public void stop() {
idleRendered = false;
}
public boolean isIdleRendered() {
return idleRendered;
}
public void setIdleRendered(boolean idleRendered) {
this.idleRendered = idleRendered;
}
}
Update:
Looks like a bug, here is a workaround:
<p:outputPanel rendered="#{Sample.idleRendered}">
<p:idleMonitor timeout="5000">
<p:ajax event="idle" oncomplete="PF('dialogId').show();" />
<p:ajax event="active" oncomplete="PF('dialogId').hide();" />
</p:idleMonitor>
</p:outputPanel>
How can dynamically show or hide a panel ?
With the given example below, when I click btn-1 then panel-2 shows and panel-1 hides. But when I click btn-2 nothing happens.
ManagedBean
#ManagedBean
#ViewScoped
public class SampleController implements Serializable {
private Boolean showPanel;
public void button1() {
showPanel = Boolean.FALSE;
}
public void button2() {
showPanel = Boolean.TRUE;
}
public Boolean showPanel1(){
return showPanel;
}
public Boolean showPanel2(){
return ! showPanel;
}
}
XHTML
<h:form id="form">
<h:panelGroup id="container-panel-1">
<h:panelGroup id="panel-1" rendered="#{sampleController.showPanel1()}">
<p:commandButton id="btn-1"
actionListener="#{sampleController.button1}"
update=":form:container-panel-1, :form:container-panel-2" />
</h:panelGroup>
</h:panelGroup>
<h:panelGroup id="container-panel-2">
<h:panelGroup id="panel-2" rendered="#{sampleController.showPanel2()}">
<p:commandButton id="btn-2"
actionListener="#{sampleController.button2}"
update=":form:container-panel-1, :form:container-panel-2" />
</h:panelGroup>
</h:panelGroup>
</h:form>
I hope you can help me with this.
Thank you,
Bell
This code is works:
View:
<h:form id="form">
<h:panelGroup id="container-panel-1">
<h:panelGroup id="panel-1" rendered="#{sampleController.showPanel1()}">
<p:commandButton id="btn-1" value="btn1"
actionListener="#{sampleController.button1}"
update=":form:container-panel-1, :form:container-panel-2" />
</h:panelGroup>
</h:panelGroup>
<h:panelGroup id="container-panel-2">
<h:panelGroup id="panel-2" rendered="#{sampleController.showPanel2()}">
<p:commandButton id="btn-2" value="btn2"
actionListener="#{sampleController.button2}"
update=":form:container-panel-1, :form:container-panel-2" />
</h:panelGroup>
</h:panelGroup>
</h:form>
Bean:
import java.io.Serializable;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
#ManagedBean
#ViewScoped
public class SampleController implements Serializable {
private boolean showPanel;
public void button1() {
showPanel = false;
}
public void button2() {
showPanel = true;
}
public boolean showPanel1(){
return showPanel;
}
public boolean showPanel2(){
return ! showPanel;
}
}
I am not able to update both the output panels after the ajax call of a method in the backing bean.
Code looks like below given sample code
abc.xhtml
<p:outputPanel id="criteriaPanel" rendered="#{myBean.showPanel}">
<h:form id="loginForm">
<ui:include src="login.xhtml" />
<p:commandButton action="#{myBean.login}" value="Login" update="criteriaPanel successPanel" />
</h:form>
</p:outputPanel>
<p:outputPanel id="successPanel" rendered="#{!myBean.showPanel}">
<h:form id="successForm">
<ui:include src="success.xhtml" />
</h:form>
</p:outputPanel>
MyBean.java
public class MyBean {
private boolean showPanel = true;
public void login() {
this.setShowPanel(false);
}
public void setShowPanel(boolean showPanel) {
this.showPanel = showPanel;
}
public boolean isShowPanel() {
return showPanel;
}
}
I'm doing a <p:commandLink value="#{bundle['registered.home.search.TEXT']}" onclick="webSearchDlg.show();"></p:commandLink> in order to show the below dialog. The p:outputPanel id="searchPnl" always renders after its initially rendered. It never disappears even though the dialogs closeListener="#{dreamSearch.close}" onCloseUpdate="searchTxtPnl,searchPnl" is executed. When I open the dialog after closing it, the panelGrid appears and the <p:inputText id="searchText"> displays the previous value that I tried to clear in the below closeListener method. Any ideas...code below...
<p:dialog header="#{bundle['dreamSearch.HEADER']}"
widgetVar="webSearchDlg" modal="true" styleClass="dialog dialog2"
draggable="false" resizable="false" showEffect="fade"
hideEffect="fade" closeListener="#{dreamSearch.close}" onCloseUpdate="searchTxtPnl,searchPnl">
<div class="dialog-top-reg"></div>
<div class="dialog-middle-reg">
<div class="close-button">
<h:form>
<p:commandButton onclick="webSearchDlg.hide()" />
</h:form>
</div>
<h:form class="dialog-content dialog-content2"
binding="#{dreamSearch.dreamSearchFrm}">
<h1 class="dream-search">
<h:outputText value="#{bundle['dreamSearch.HEADER']}" />
</h1>
<p class="dream-search">
<h:outputText value="#{bundle['dreamSearch.SUBHEADER']}" />
</p>
<div class="dream-search-wrap">
<fieldset>
<p:outputPanel id="searchTxtPnl">
<p:inputText id="searchText" value="#{dreamSearchBean.searchText}"/>
</p:outputPanel>
<p:commandButton styleClass="form-btn1"
value="#{bundle['dreamSearch.search.button.TEXT']}" onclick="webImageSearch()"/>
</fieldset>
</div>
<p:remoteCommand name="webImageSearch" process="searchText, #this" actionListener="#{dreamSearch.search}" update="searchPnl"/>
<p:outputPanel id="searchPnl" styleClass="data-grid-wrap">
<h:outputText value="#{bundle['dreamSearch.imageResults.TEXT']}" rendered="#{dreamSearchBean.shouldRender}"/>
<p:dataGrid var="img" value="#{dreamSearchBean.images}" columns="5"
rows="10" paginator="true" effect="true"
paginatorTemplate="{CurrentPageReport} {FirstPageLink} {PreviousPageLink} {PageLinks} {NextPageLink} {LastPageLink} {RowsPerPageDropdown}"
rowsPerPageTemplate="10,15,20" paginatorPosition="bottom" rendered="#{dreamSearchBean.shouldRender}">
<p:column>
<h:panelGrid columns="1" style="width:100%">
<p:graphicImage value="#{img}" width="40" height="50" />
</h:panelGrid>
</p:column>
</p:dataGrid>
</p:outputPanel>
</h:form>
</div>
<div class="dialog-bottom-reg"></div>
</p:dialog>
#Named
#Scope("request")
public class DreamSearch extends BaseAction {
#Inject
DreamService dreamService;
#Inject
ImageSearchService flickrSearchImpl;
#Inject
private DreamSearchBean dreamSearchBean;
private UIForm dreamSearchFrm;
public void init(){
if (!FacesUtils.isPostback()) {
dreamSearchBean.setShouldRender(false);
dreamSearchBean.setSearchText(null);
}
}
public void setDreamSearchFrm(UIForm dreamSearchFrm) {
this.dreamSearchFrm = dreamSearchFrm;
init();
}
public void search(ActionEvent e){
try {
if(dreamSearchBean.getSearchText() != null && !dreamSearchBean.getSearchText().isEmpty()){
List<String> searchResults = flickrSearchImpl.searchByKeyWord(dreamSearchBean.getSearchText());
dreamSearchBean.setImages(searchResults);
dreamSearchBean.setShouldRender(true);
}else{
dreamSearchBean.setShouldRender(false);
}
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
}
public void close(CloseEvent e){
dreamSearchBean.setShouldRender(false);
dreamSearchBean.setSearchText(null);
}
public UIForm getDreamSearchFrm() {
return dreamSearchFrm;
}
}
#Named
#Scope("session")
public class DreamSearchBean extends BaseSessionBean {
private List<String> images;
private String searchText;
private boolean shouldRender;
public String getSearchText() {
return searchText;
}
public void setSearchText(String searchText) {
this.searchText = searchText;
}
public boolean isShouldRender() {
return shouldRender;
}
public void setShouldRender(boolean shouldRender) {
this.shouldRender = shouldRender;
}
public List<String> getImages() {
return images;
}
public void setImages(List<String> images) {
this.images = images;
}
}
Don't really know what the reason for this behavior is, but you could try the following:
For the <p:outputPanel id="searchPnl">: try to set the rendered tag on the panel and not on the h:outputText and p:dataGrid.
For the searchText try to update the <p:outputPanel id="searchTxtPnl"> instead of the h:inputText.
I noticed that the scope of your bean is request. If your doing ajax updates this really needs to be a ViewScoped bean with the JSF #ManagedBean and #ViewScoped annotations.
Another thing: make sure your not updating the form where the dialog resides in. This could have unwanted results.