[
https://jira.jboss.org/jira/browse/RF-4283?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
]
Nick Belaevski resolved RF-4283.
--------------------------------
Fix Version/s: 3.2.2
Resolution: Out of Date
Assignee: Tsikhon Kuprevich
This problem is not reproduced with 3.2.2.BETA5, but is reproduced with BETA2,
so I resolve the issue.
One more note: set ajaxSingle="false" in datascroller in order for update()
method to be called or add dataTable to process attribute of datascroller!
Without that, datascroller works, but data do not get scrolled.
> Rich:datascroller does not show the correct number of pages when used with
> ExtendedDataModel
> --------------------------------------------------------------------------------------------
>
> Key: RF-4283
> URL: https://jira.jboss.org/jira/browse/RF-4283
> Project: RichFaces
> Issue Type: Bug
> Affects Versions: 3.0.0
> Reporter: Hristo Mitkov
> Assignee: Tsikhon Kuprevich
> Priority: Critical
> Fix For: 3.2.2
>
>
> Rich:datascroller cannnot be set to show the correct number of pages when
> using an ExtendedDataModel. The reason for this is that ListSequenceDataModel
> is used for calculating the number of pages instead of ExtendedDataModel.
> I have TestDataModel class which extends SerializableDataModel where in
> wrappedData I return just 10 elements but my getRowCount method returns the
> number of all records in the database which is 500. The datascroller though
> shows that there is only one page.
> I debug the richfaces code to see how the datascroller is rendered.
> This is done mainly in DatascrollerTemplate and DataScrollerRenderer in
> package org.richfaces.renderkit.html. As expected the datascroller uses the
> DataModel of the DataTable to calculate the number of pages:
> org.richfaces.component.UIDatascroller.getRowCount(UIData data)
> and after:
> UIDataAdapter.getRowCount(){
> ... return getExtendedDataModel().getRowCount();
> }
> Here getExtendedDataModel() returns an instance of ModifiableModel which
> field "originalModel" contains my custom TestDataModel. So
> modifiableModel.getOriginalModel.getRowCount will return 500 as I need. But
> look at the implementation of modifiableModel.getRowCount:
> public int getRowCount() {
> return delegate.getRowCount();
> }
> !!!???
> delegate is an instance of ListSequenceDataModel which contains the list
> wrappedKeys. So getRowCount() returns wrappedKeys.size() which is 10 so the
> datascroller renders with only one page.
> The correct implementation of modifiableModel.getRowCount should be:
> public int getRowCount() {
> return originalModel.getRowCount();
> }
> At the time of rendering the dataTable when the model is created () both
> fields: modifiableModel.originalModel and modifiableModel.delegate are set to
> TestDataModel. But at some point delegate is set to ListSequenceDataModel and
> returns the size of the list.
> Another thing is that there is no way to set the number of pages directly to
> the UIDatascroller component either by an attribute or by the API
> Here is an example code:
> This is the datamodel class:
> @Name("testDataModel")
> @Scope(ScopeType.SESSION)
> public class TestDataModel extends SerializableDataModel {
> private Integer currentPk;
> private boolean detached = false;
> private boolean descending;
> private List<Integer> wrappedKeys = null;
> private final Map<Integer, Container> wrappedData = new
> HashMap<Integer, Container>();
> private int rowCount=0;
> @Override
> public Object getRowKey() {
> return currentPk;
> }
> @Override
> public void setRowKey(Object key) {
> this.currentPk = (Integer) key;
> }
> @In(create = true)
> private ContainerService containerManager;
> @Override
> public void walk(FacesContext context, DataVisitor visitor, Range
> range, Object argument) throws IOException {
> if (detached){
> for (Integer key : wrappedKeys) {
> setRowKey(key);
> visitor.process(context, key, argument);
> }
> } else {
> int firstRow = ((SequenceRange) range).getFirstRow();
> int numberOfRows = 10;// ((SequenceRange)
> range).getRows();
> wrappedKeys = new ArrayList<Integer>();
> for (Container container :
> containerManager.findContainersPaged(firstRow, numberOfRows, null, null)) {
> wrappedKeys.add(container.getId());
> wrappedData.put(container.getId(), container);
> visitor.process(context, container.getId(),
> argument);
> }
> }
> }
> @Override
> public SerializableDataModel getSerializableModel(Range range) {
> if (wrappedKeys != null) {
> detached = true;
> return this;
> }
> return null;
> }
> @Override
> public void update() {
> detached = false;
> }
>
> @Override
> public int getRowCount() {
> if(rowCount==0){
> rowCount=containerManager.countContainers();
> }
> // Here for test and debug purposes you can comment the code
> above and just do:
> // return 500;
> return rowCount;
> }
> @Override
> public Object getRowData() {
>
> if (currentPk == null) {
> return null;
> } else {
> Container container = wrappedData.get(currentPk);
> if (container == null) {
> container =
> containerManager.getContainerById(currentPk);
> wrappedData.put(currentPk, container);
> }
> return container;
> }
> }
> @Override
> public boolean isRowAvailable() {
> if (currentPk == null) {
> return false;
> }
> if (wrappedKeys.contains(currentPk)) {
> return true;
> }
> if (wrappedData.entrySet().contains(currentPk)) {
> return true;
> }
> if (containerManager.getContainerById(currentPk) != null) {
> return true;
> }
> return false;
> }
> @Override
> public void setRowIndex(int index) {
> }
> @Override
> public int getRowIndex() {
> throw new UnsupportedOperationException();
> }
> @Override
> public Object getWrappedData() {
> throw new UnsupportedOperationException();
> }
> @Override
> public void setWrappedData(java.lang.Object data) {
> throw new UnsupportedOperationException();
> }
> }
> Thisis the seam managed bean. It can be any kind of jsf managed bean:
> @Stateful
> @Name("containerManager")
> public class ContainerManager implements ContainerService {
> public Integer countContainers() {
> //For test and debug purposes you can comment the following
> code and just: return 500;
> Session session = (Session) entityManager.getDelegate();
> Criteria criteria =
> session.createCriteria(Container.class).setProjection(Projections.rowCount());
> Integer containerCount = (Integer) criteria.uniqueResult();
> return containerCount;
> }
> public List<Container> findContainersPaged(int firstRow, int
> numberOfRows, String sortField, boolean descending) {
> List<Container> container = entityManager.createQuery("select c
> from Container c
> ").setFirstResult(firstRow).setMaxResults(numberOfRows).getResultList();
> return container;
> }
> public Container getContainerById(Integer id) {
> return entityManager.find(Container.class, id);
> }
> }
> This is the page
> <rich:dataTable id="containerList" rows="10" var="c"
> value="#{testDataModel}">
> <rich:column>
> <f:facet name="header">
> <h:outputText
> value="Name" />
> </f:facet>
> <h:outputText value="#{c.name}"
> />
> </rich:column>
> </rich:dataTable>
> <rich:datascroller align="left" for="containerList" maxPages="10"
> rendered="true" />
--
This message is automatically generated by JIRA.
-
If you think it was sent incorrectly contact one of the administrators:
https://jira.jboss.org/jira/secure/Administrators.jspa
-
For more information on JIRA, see: http://www.atlassian.com/software/jira
_______________________________________________
richfaces-issues mailing list
[email protected]
https://lists.jboss.org/mailman/listinfo/richfaces-issues