2013-01-07 8 views
5

Próbuję dowiedzieć się, jak zrobić prawdziwą paginację z datascroller richfaces.Richfaces 3 jak uczynić datascroller prawdziwą paginacją?

Obecnie moje zapytanie pobiera wszystkie dane z tabeli i chcę je, więc po kliknięciu następnego przycisku z datascroller, zapyta db do następnych 20 wierszy.

Rozumiem, jak napisać zapytanie, aby ograniczyć wiersze, ale nie jestem pewien, jak uzyskać następny przycisk urządzenia do przenoszenia danych w celu wywołania konkretnej metody.

Widzę, że wiele osób publikuje na forach Richfaces z potencjalnymi rozwiązaniami, ale wszystkie używają DataModel. Ponieważ nie używam ORM, nie jestem pewien, w jaki sposób mogę dopasować te rozwiązania do tego, co mam.

Każda pomoc jest doceniana.

<rich:extendedDataTable id="resultsTable" value="#{tableBacking.results}" var="results" sortMode="single" rowKeyVar="row"> 
    <rich:columns value="#{tableBacking.columns == null ? '' : tableBacking.columns}" var="columns" index="ind" id="column#{ind}" sortBy="#{results[ind].data}" rendered="#{tableBacking.columns != null}"> 
     <f:facet name="header"> 
      <h:outputText value="#{columns.columnDescription}" /> 
     </f:facet> 

     <h:outputText value="#{results[ind].data}" /> 

    </rich:columns> 

</rich:extendedDataTable> 

<rich:datascroller for="resultsTable" page="#{tableBacking.page}" renderIfSinglePage="false" /> 

Backing Bean

public class TableBacking { 
    private List<List<TableData>> results = null; 
    private int page = 0; 

    public int getPage() { 
    return page; 
    } 
    public void setPage(int page) { 
    this.page = page; 
    } 
    public List<List<TableData>> getResults() throws Exception { 
    return results; 
    } 
    public void setResults(List<List<TableData>> results) { 
    this.results = results; 
    } 

    private void getData(String whereClause) { 

    try { 
    DataDao dd = new DataDao(); 
    results = dd.getData(); // dd.getData just runs a query on a table and puts the results in a List of lists. 
    } catch (Exception e) {} 
} 

Odpowiedz

0

Musisz powiązać rich:extendedDataTable do atrybutu w swoim podkładowej fasoli.

Java

private HtmlExtendedDataTable Table; 
//Getter and setter 

Po tym wiążą Twój widok

xhtml

<rich:extendedDataTable id="resultsTable" value="#{tableBacking.results}" var="results" sortMode="single" rowKeyVar="row" binding="#{tableBacking.Table}">

Richfaces HtmlExtendedDataTable ma sposobu, aby sprawdzić, ile wierszy są wyświetlane na stronie o nazwie getRows(). Po inicjalizacji komponentu bean po prostu wczytaj wartości pierwszej strony, zgodnie z tym (możesz wczytać tylko identyfikatory elementów na pozostałych stronach, a później, gdy masz zamiar uzyskać dostęp do strony, załaduj je na podstawie identyfikatora).

<rich:datascroller/> ma również zdarzenie, które jest opalane po naciśnięciu strona kliknięciu można nabyć że z fasoli podkładowej w następujący sposób:

xhtml

<f:facet name="footer"> 
<rich:datascroller id="ds" 
       scrollerListener="#{tableBacking.actionOnPageChange}" /> 
</f:facet> 

Java

public String actionOnPageChange(DataScrollerEvent event)

Ta DataScrollerEvent zawiera stronę, która została kliknięta przez użytkownika, którą można uzyskać za pomocą getNewScrolVal(). Kiedy tak się stanie, po prostu załaduj wartości odpowiedniej strony w tabeli i to wszystko.

+0

Problem mam z tego rozwiązania jest to, że nie jest świadczenie datascroller ponieważ Mam DataTable wiersze ustawiono na 20, a kiedy ładuje się strona, dostaje tylko 20 wierszy. Czy wiesz, jak sobie z tym poradzić? Czy istnieje sposób na przekazanie do dziennika danych maksymalnej liczby wierszy, aby wiedzieć, ile stron należy obliczyć? – Catfish

+0

Nie jestem pewien, czy rozumiem, co masz na myśli przez "" możesz wczytać tylko identyfikatory elementów na pozostałych stronach, a później, gdy masz zamiar uzyskać dostęp do strony, załaduj je na podstawie identyfikatora " – Catfish

+0

Ty powiedziałeś, że nie korzystasz z ORM. Użyłem tego rozwiązania z Hibernate, ładując całe dane, ale niektóre cechy w leniwym ładowaniu, z tym, kiedy zażądam jakiejś strony, mogę załadować te obiekty i zapobiec wyjątkom leniwego ładowania. W twoim przypadku myślę, że możesz przechowywać * fałszywe * obiekty (które tylko będą miały przypisany atrybut id) na niewidocznych stronach. Jak to osiągnąć? Ładowanie całej listy id od początku i pobieranie względnych informacji tylko wtedy, gdy jest to potrzebne. Nie wiem, jak działa twój model, po prostu wpadam na pomysł. –

2

Spróbuj to zrobić:

JSF Stuff:

<rich:dataTable id="listTable" var="record" rows="10" value="#{personBean.data}"> 
    .... 
    <f:facet name="footer"> 
     <rich:column colspan="8"> 
     <rich:dataScroller page="#{personBean.page}" for="listTable" 
       scrollListener="#{personBean.scrollPage}" render="listTable" /> 
     </rich:column> 
     Records : #{personBean.data.size()} 
    </f:facet> 
</rich:dataTable> 

Java BackBean Stuff:

public class PersonBean { 
    // List of Persons 
    private PagedList<Person> data; 

    // Current page 
    private Integer page; 

    // Default rows to display 
    private Integer rows = 10; 

    // Persistence layer 
    private DaoService daoService; 

    @PostConstruct 
    public void init(){ 
     page= 1; 
    } 

    // Event trigger on scroll page 
    public void scrollPage(DataScrollEvent ev) { 
     log.debug("Scroll event"); 
     reset(); 

     // getPersons execute 2 queries : the first query is the count(*) and the result is set in TotalElements 
     // the second query gets the 'n' records defined in rows , something like this : 
     // select * from Persons LIMIT page*rows, (page*rows) + rows and the result is set in Content 
     Page<Person> pageResult = this.daoService.getPersons(filter, page - 1, rows); 

     // Now create a pagedList with the constructor 
     this.data = new PagedList<Person>(pageResult.getContent(), (int) pageResult.getTotalElements(), this.pageSize); 
    } 
} 

Java PagedList

public final class PagedList<E> extends AbstractList<E> { 

    private final List<E> lista; 
    private final int total; 
    private final int pageSize; 

    public PagedList(List<E> lista, int total, int pageSize) { 
     this.lista = lista; 
     this.total = total; 
     this.pageSize = pageSize; 
    } 

    public int size() { 
     return total; 
    } 

    public E get(int i) { 
     i = i % this.pageSize; 
     return lista.get(i); 
    } 
} 

Podstęp polega na ustaleniu całkowitej wartości klasy PagedList z liczbą dataTable w bazie danych i ustawieniu elementów stronicowanych na liście PageList.

Przepraszam za mój zły język angielski: P

0

najlepszym rozwiązaniem znalazłem jest mapowanie „wartość” atrybut DataTable do org.richfaces.model.ExtendedTableDataModelproperty. Następnie należy zainicjować ExtendedTableDataModel za pomocą instancji org.richfaces.model.DataProvider. Próbka:

W widoku:

<rich:dataTable id="table" value="#{bean.model}" rows="#{bean.rows}"> 
    <!-- columns --> 
    <f:facet name="footer"> 
     <rich:dataScroller for="table"/> 
    </f:facet> 
</rich:dataTable> 

W fasoli:

@ManagedBean 
public class Bean { 
    private int rows = 15; // the ammount of rows per page. 
    private org.richfaces.model.ExtendedTableDataModel model = new org.richfaces.model.ExtendedTableDataModel(
     new org.richfaces.model.DataProvider(
     public int getRowCount() { 
      // count your rows. 
     } 

     public List<T> getItemsByRange(int first, int quantity) { 
      // fetch the page's rows. 
     } 

     public T getItemByKey(Object o) { 
      return null; // no need to implement this. 
     } 

     public Object getKey(T t) { 
      return null; // no need to implement this. 
     ) 
    ); 

    public int getRows() { return rows; } 
    public ExtendedTableDataModel getModel() { return model; } 

} 
Powiązane problemy