Search code examples
primefacesjsf-2datascroller

p:datascroller only lazyload one time


We have implement the datascroller from primefaces and extend it with lazy=true this works fine for the first lazy loading. But when I scroll down no event is fired from Frontend. The Backend works as expected.

I test it with changing the chunk size and get a better understanding what is happen in the backend code. We override the load function what primefaces is calling when you reach the end of page. I changed the code to not lazyloading by scrolling, therefor i implement a button to load the next chunk when you click the button. But Button disappear after clicking it once.

Xhtml:

                        <p:dataScroller value="#{stakeholderOverviewController.model}" var="stakeholder" chunkSize="50" lazy="true" rowIndexVar="test">

                            <f:facet name="header">
                                Scroll Down to Load More Cars 
                            </f:facet>
                            <f:facet name="loader">
                                <p:commandButton type="button" value="More" icon="pi pi-chevron-circle-down"/>
                            </f:facet>
                            <h:panelGrid columns="2" style="width:100%" columnClasses="logo,detail">
                                <p:outputPanel>
                                    <h:panelGrid columns="2" cellpadding="5">
                                        <h:outputText value="Id:" />
                                        <h:outputText value="#{stakeholder.lastname}" style="font-weight: bold"/>

                                        <h:outputText value="Year:" />
                                        <h:outputText value="#{stakeholder.firstname}" style="font-weight: bold"/>

                                    </h:panelGrid>
                                </p:outputPanel>
                            </h:panelGrid>
                            <ui:include  rendered="#{empty stakeholder}" src="/WEB-INF/compositions/stakeholderEmptyModel.xhtml" />
                        </p:dataScroller>

there is the backend code for Controller:

    public StakeholderOverviewController() {
        model = new LazyDataModel<StakeholderSearchWrapper>() {

            @Override
            public List<StakeholderSearchWrapper> load(int first, int pageSize, String sortField, SortOrder sortOrder,
                    Map filters) {

                List<StakeholderSearchWrapper> execQuery = execQuery(first, pageSize);
                return execQuery;
            }
        };
        model.setRowCount(0);
    }

....

protected synchronized List<StakeholderSearchWrapper> execQuery(int first, int pageSize) {
        if (tmpfirst != first || tmppageSize != pageSize || reExecQuery) {
            reExecQuery = false;
            tmpfirst = first;
            tmppageSize = pageSize;

            tmpModel = new LinkedList<>();

            // Query for stakeholder
            queryresponse = stakeholderService.findByLastnameOrFirstmanOwnerOrShare(getSearchText(), getClientId(),
                    first, pageSize, selectedFacets, nameSort[getSort()]);

            setFacets(queryresponse.getFacetFields());
            Set<String> stakeholderIds = new HashSet<String>();

            // convert for view
            for (SolrDocument details : queryresponse.getResults()) {
                StakeholderSearchWrapper stakeholderSearchWrapper = new StakeholderSearchWrapper(details);

                tmpModel.add(stakeholderSearchWrapper);
                stakeholderIds.add(stakeholderSearchWrapper.getId());
            }

            historyCount = stakeholderService.countHistoryEntryByStakeholders(stakeholderIds);
            notesCount = stakeholderService.countNoteEntriesByStakeholders(stakeholderIds);
            assignedProjects = projectService.findByStakeholderIds(stakeholderIds);

            for(StakeholderSearchWrapper dao : tmpModel) {
                dao.setHistoryCount(getHistoryCount(dao.getId()));
                dao.setNoteCount(getNoteEntriesCount(dao.getId()));
                dao.setProjects(getAssignedProjects(dao.getId()));
            }


            SolrDocumentList result = queryresponse.getResults();
            int numFound = (int) result.getNumFound();

            return tmpModel;
        } else {
            return tmpModel;
        }
    }

What i want is that the lazy loading dont fire only once. It should fire as often as needed. I dont know where i have to set some variable to do this. When im debuging the current code the load function is only requested at the first run of the page refresh and than one lazy loading is called but then nothing happens.


Solution

  • I think I realized the trick. Check the line:

    model.setRowCount(0);
    

    Instead, set the model row count properly using the max amount of data you want to display:

    int totalNumberOfRegisters = this.count(/* relevant paramenters*/);
    model.setRowCount(totalNumberOfRegisters);