You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@click.apache.org by sa...@apache.org on 2009/03/19 15:00:54 UTC
svn commit: r756003 - in /incubator/click/trunk/click: documentation/docs/
examples/src/org/apache/click/examples/page/table/ examples/webapp/WEB-INF/
examples/webapp/table/ framework/src/org/apache/click/control/
Author: sabob
Date: Thu Mar 19 14:00:54 2009
New Revision: 756003
URL: http://svn.apache.org/viewvc?rev=756003&view=rev
Log:
Promoted Table getFirstRow and getLastRow to public. New demo added showcasing how to page through a large dataset
Added:
incubator/click/trunk/click/examples/src/org/apache/click/examples/page/table/LargeDatasetDemo.java
incubator/click/trunk/click/examples/webapp/table/large-dataset-demo.htm
Modified:
incubator/click/trunk/click/documentation/docs/roadmap-changes.html
incubator/click/trunk/click/examples/webapp/WEB-INF/menu.xml
incubator/click/trunk/click/framework/src/org/apache/click/control/Table.java
Modified: incubator/click/trunk/click/documentation/docs/roadmap-changes.html
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/documentation/docs/roadmap-changes.html?rev=756003&r1=756002&r2=756003&view=diff
==============================================================================
--- incubator/click/trunk/click/documentation/docs/roadmap-changes.html (original)
+++ incubator/click/trunk/click/documentation/docs/roadmap-changes.html Thu Mar 19 14:00:54 2009
@@ -85,6 +85,11 @@
</div>
<ul style="padding: 0em; margin-left:0em;margin-bottom: 2em">
<li>
+ <a target="_blank" class="external" href="http://www.avoka.com/click-examples/table/large-dataset-demo.htm">
+ Large Dataset Demo</a> demonstrates a Table with a large number of rows
+ and how to lazily page through the rows using a custom Table model.
+ </li>
+ <li>
<a target="_blank" class="external" href="http://www.avoka.com/click-examples/panel/reusable-panel-demo.htm">
Reusable Panel Demo</a> is an example of a reusable Panel
which provides a Form for capturing Client details.
@@ -96,6 +101,14 @@
</div>
<ul style="padding: 0em; margin-left:0em;margin-bottom: 2em">
<li class="change">
+ Improved Table to support very large datasets by promoting the methods
+ <a href="click-api/org/apache/click/control/Table.html#getFirstRow()">getFirstRow()</a>
+ and <a href="click-api/org/apache/click/control/Table.html#getLastRow()">getLastRow()</a>
+ as public. These methods provide the necessary information to only
+ retrieve the displayed rows
+ [<a target='_blank' href="https://issues.apache.org/click/browse/CLK-504">504</a>].
+ </li>
+ <li class="change">
Added ability to specify a custom TreeNode icon through the new method
TreeNode.<a href="extras-api/org/apache/click/extras/tree/TreeNode.html#setIcon(java.lang.String)">setIcon(String)</a>.
This issue was raised and fixed by Tim Hooper
Added: incubator/click/trunk/click/examples/src/org/apache/click/examples/page/table/LargeDatasetDemo.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/examples/src/org/apache/click/examples/page/table/LargeDatasetDemo.java?rev=756003&view=auto
==============================================================================
--- incubator/click/trunk/click/examples/src/org/apache/click/examples/page/table/LargeDatasetDemo.java (added)
+++ incubator/click/trunk/click/examples/src/org/apache/click/examples/page/table/LargeDatasetDemo.java Thu Mar 19 14:00:54 2009
@@ -0,0 +1,151 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.click.examples.page.table;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.click.control.Column;
+import org.apache.click.control.Table;
+import org.apache.click.examples.page.BorderPage;
+
+/**
+ * Provides a demonstration of a Table with a huge number of rows and how to
+ * lazily page through the rows using a custom List implementation.
+ *
+ * @author Bob Schellink
+ */
+public class LargeDatasetDemo extends BorderPage {
+
+ public Table table;
+
+ public LargeDatasetDemo() {
+ table = new Table();
+
+ // Setup customers table
+ table.setClass(Table.CLASS_ITS);
+
+ Column column = new Column("name");
+ column.setWidth("140px;");
+ table.addColumn(column);
+
+ column = new Column("email");
+ column.setAutolink(true);
+ column.setWidth("230px;");
+ table.addColumn(column);
+
+ column = new Column("age");
+ column.setTextAlign("center");
+ column.setWidth("40px;");
+ table.addColumn(column);
+
+ column = new Column("holdings");
+ column.setFormat("${0,number,#,##0.00}");
+ column.setTextAlign("right");
+ column.setWidth("100px;");
+ table.addColumn(column);
+
+ table.setPageSize(5);
+ }
+
+ /**
+ * @see org.apache.click.Page#onRender()
+ */
+ public void onRender() {
+ // Create TableModel for the specified table and total number of customers
+ TableModel model = new TableModel(table, getCustomerCount());
+
+ // Set the TableModel as the Table row list. Table is now able to
+ // calculate the last row value.
+ // NOTE: If table rowList is not set, table cannot calculate the last row
+ // and invoking #getLastRow will return 0.
+ table.setRowList(model);
+
+ // Retrieve customers given the firstRow, lastRow and pageSize
+ List customers = getCustomers(table.getFirstRow(), table.getLastRow(), table.getPageSize());
+
+ // Add the customers to the table model
+ model.addAll(customers);
+ }
+
+ // ---------------------------------------------------------- Inner Classes
+
+ /**
+ * Provides a custom List implementation which returns a pre-defined size,
+ * even if the underlying amount of entries is less.
+ *
+ * The List also returns correct row for a specified index by offsetting
+ * the index against the Table's firstRow value.
+ */
+ class TableModel extends ArrayList {
+
+ /** The model's Table instance. */
+ private Table table;
+
+ /** The total number of rows of the model. */
+ private int numOfRows;
+
+ /**
+ * Create a new TableModel instance for the given Table and total number
+ * of rows.
+ *
+ * @param table this model's Table instance
+ * @param numOfRows the total number of rows of the model
+ */
+ public TableModel(Table table, int numOfRows) {
+ this.table = table;
+ this.numOfRows = numOfRows;
+ }
+
+ /**
+ * Returns the row at the specified index, offsetted by the current
+ * table first row value.
+ *
+ * @param index the index of the row as viewed in the Table
+ * @return the the row at the specified index, offsetted by the
+ * current table first row value.
+ */
+ public Object get(final int index) {
+ int realIndex = index - table.getFirstRow();
+ return super.get(realIndex);
+ }
+
+ /**
+ * Always return the total number of rows even the number of entries
+ * are less.
+ */
+ public int size() {
+ return numOfRows;
+ }
+ }
+
+ // -------------------------------------------------------- Private Methods
+
+ private int getCustomerCount() {
+ return getCustomerService().getNumberOfCustomers();
+ }
+
+ private List getCustomers(int from, int to, int pageSize) {
+ // Below we retrieve only those customers between the from and to
+ // args. In a real application one would use an ORM or JDBC to only
+ // retrieve the needed rows
+ return getCustomerService().getCustomersForPage(from, pageSize);
+ }
+
+}
Modified: incubator/click/trunk/click/examples/webapp/WEB-INF/menu.xml
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/examples/webapp/WEB-INF/menu.xml?rev=756003&r1=756002&r2=756003&view=diff
==============================================================================
--- incubator/click/trunk/click/examples/webapp/WEB-INF/menu.xml (original)
+++ incubator/click/trunk/click/examples/webapp/WEB-INF/menu.xml Thu Mar 19 14:00:54 2009
@@ -110,6 +110,8 @@
<menu separator="true"/>
<menu label="Edit Table Pattern" path="table/edit-table.htm"/>
<menu label="Search Table Pattern" path="table/search-table.htm"/>
+ <menu separator="true"/>
+ <menu label="Large Dataset Demo" path="table/large-dataset-demo.htm"/>
</menu>
<menu label=" Tree" path="#" imageSrc="/assets/images/tree.png">
Added: incubator/click/trunk/click/examples/webapp/table/large-dataset-demo.htm
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/examples/webapp/table/large-dataset-demo.htm?rev=756003&view=auto
==============================================================================
--- incubator/click/trunk/click/examples/webapp/table/large-dataset-demo.htm (added)
+++ incubator/click/trunk/click/examples/webapp/table/large-dataset-demo.htm Thu Mar 19 14:00:54 2009
@@ -0,0 +1 @@
+$table
\ No newline at end of file
Modified: incubator/click/trunk/click/framework/src/org/apache/click/control/Table.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/framework/src/org/apache/click/control/Table.java?rev=756003&r1=756002&r2=756003&view=diff
==============================================================================
--- incubator/click/trunk/click/framework/src/org/apache/click/control/Table.java (original)
+++ incubator/click/trunk/click/framework/src/org/apache/click/control/Table.java Thu Mar 19 14:00:54 2009
@@ -145,40 +145,50 @@
* in your applications <tt>click-pages.properties</tt> file. For example:
*
* <pre class="codeConfig">
- * table-default-class=blue2
- * </pre>
+ * table-default-class=blue2 </pre>
*
- * <a name="paging-and-sorting"></a>
- * <h4>Paging and Sorting</h4>
+ * <a name="paging"></a>
+ * <h4>Paging</h4>
*
- * Table provides out-of-the-box paging and sorting.
+ * Table provides out-of-the-box paging.
* <p/>
* To enable Paging set the table's page size: {@link #setPageSize(int)} and
* make the Table Banner visible: {@link #setShowBanner(boolean)}.
* <p/>
+ * Table supports rendering different paginators through the method
+ * {@link #setPaginator(org.apache.click.control.Renderable) setPaginator}.
+ * The default Table Paginator is {@link TablePaginator}.
+ *
+ * <a name="sorting"></a>
+ * <h4>Sorting</h4>
+ * Table also has built in column sorting.
+ * <p/>
* To enable/disable sorting use {@link #setSortable(boolean)}.
+ *
+ * <a name="custom-parameters"></a>
+ * <h4>Custom Parameters - preserve state when paging and sorting</h4>
+ *
+ * Its often necessary to add extra parameters on the Table links in order to
+ * preserve state when navigating between pages or sorting columns.
* <p/>
- * You can also set parameters on links generated by the Table through
+ * One can easily add extra parameters to links generated by the Table through
* the Table's {@link #getControlLink() controlLink}.
* <p/>
- * One often needs to add extra parameters on the Table links in order to
- * preserve state when navigating between pages or sorting columns.
- * <p/>
* For example:
*
* <pre class="prettyprint">
* public CompanyPage extends BorderPage {
*
* // companyId is the criteria used to limit Table rows to clients from
- * // the specified company
+ * // the specified company. This variable could be selected from a drop
+ * // down list or similar means.
* public String companyId;
*
* public Table table = new Table();
*
* public onInit() {
- * // companyId could be selected from a drop down list or similar means.
* // Set the companyId on the table's controlLink. If you view the
- * // output rendered by Table you will note the companyId parameter
+ * // output rendered by Table note that the companyId parameter
* // is rendered for each Paging and Sorting link.
* table.getControlLink().setParameter("companyId", companyId);
* }
@@ -192,15 +202,43 @@
* }
* } </pre>
*
- * Table supports rendering different paginators through the method
- * {@link #setPaginator(org.apache.click.control.Renderable)}. The default Table
- * Paginator is {@link TablePaginator}.
- *
* <a name="row-attributes"></a>
* <h4>Row Attributes</h4>
*
* Sometimes it is useful to add HTML attributes on individual rows. For these
- * cases one can override the method {@link #addRowAttributes(java.util.Map, java.lang.Object, int)}.
+ * cases one can override the method {@link #addRowAttributes(java.util.Map, java.lang.Object, int)}
+ * and add custom attributes to the row's attribute Map.
+ *
+ * <a name="large-datasets"></a>
+ * <h4>Large Datasets</h4>
+ *
+ * For large datasets Table provides automatic pagination to display a
+ * limited number of rows per page. However the Table's
+ * {@link #setRowList(java.util.List) row list} must still contain all the
+ * dataset entries. With very large datasets (e.g. 100,000 rows), its not
+ * possible to retrieve that many rows from the database.
+ * <p/>
+ * In these cases a custom List implementation can be used as the
+ * Table's {@link #setRowList(java.util.List) row list}. The custom List will
+ * only be populated with the rows that must be displayed for the selected page.
+ * <p/>
+ * The Table methods {@link #getFirstRow()}, {@link #getLastRow()} and
+ * {@link #getPageSize()} provides enough information to calculate which
+ * rows to display for the selected page. Most databases provide the ability
+ * to either limit retrieved rows to a start and end value or a start offset
+ * and max number of rows.
+ * <p/>
+ * A prerequisite is that the <tt>total number of rows</tt> must be retrieved
+ * beforehand, otherwise it won't be possible to calculate the {@link #getLastRow()
+ * last row}.
+ * <p/>
+ * A custom List have two responsibilities: it must override {@link java.util.List#size()
+ * List.size()} to return the <tt>total number of rows</tt> and it must override
+ * {@link java.util.List#get(int) List.get(index)} to ensure the List returns the
+ * correct row for the specified index.
+ * <p/>
+ * Please see the <a href="http://www.avoka.com/click-examples/table/large-dataset-demo.htm">Large Dataset Demo</a>
+ * which provides a custom List implementation as described above.
* <p/>
*
* See also W3C HTML reference
@@ -1070,6 +1108,47 @@
// --------------------------------------------------------- Public Methods
/**
+ * Return the index of the first row to display. Index starts from 0.
+ * <p/>
+ * <b>Note:</b> {@link #setPageSize(int) page size} must be set for this
+ * method to correctly calculate the first row, otherwise this method will
+ * return 0.
+ *
+ * @return the index of the first row to display
+ */
+ public int getFirstRow() {
+ int firstRow = 0;
+
+ if (getPageSize() > 0) {
+ if (getPageNumber() > 0) {
+ firstRow = getPageSize() * getPageNumber();
+ }
+ }
+
+ return firstRow;
+ }
+
+ /**
+ * Return the index of the last row to diplay. Index starts from 0.
+ * <p/>
+ * <b>Note:</b> the Table {@link #setRowList(java.util.List) row list} and
+ * {@link #setPageSize(int) page size} must be set for this method to
+ * correctly calculate the last row, otherwise this method will return 0.
+ *
+ * @return the index of the last row to display
+ */
+ public int getLastRow() {
+ int numbRows = getRowList().size();
+ int lastRow = numbRows;
+
+ if (getPageSize() > 0) {
+ lastRow = getFirstRow() + getPageSize();
+ lastRow = Math.min(lastRow, numbRows);
+ }
+ return lastRow;
+ }
+
+ /**
* Deploy the <tt>table.css</tt> and column sorting icon files to the
* <tt>click</tt> web directory when the application is initialized.
*
@@ -1278,39 +1357,6 @@
// ------------------------------------------------------ Protected Methods
/**
- * Return the index of the first row to display. Index starts from 0.
- *
- * @return the index of the first row to display
- */
- protected int getFirstRow() {
- int firstRow = 0;
-
- if (getPageSize() > 0) {
- if (getPageNumber() > 0) {
- firstRow = getPageSize() * getPageNumber();
- }
- }
-
- return firstRow;
- }
-
- /**
- * Return the index of the last row to diplay. Index starts from 0.
- *
- * @return the index of the last row to display
- */
- protected int getLastRow() {
- int numbRows = getRowList().size();
- int lastRow = numbRows;
-
- if (getPageSize() > 0) {
- lastRow = getFirstRow() + getPageSize();
- lastRow = Math.min(lastRow, numbRows);
- }
- return lastRow;
- }
-
- /**
* Render the table header row of column names.
*
* @param buffer the StringBuffer to render the header row in