/** * Licensed under the Artistic License; you may not use this file * except in compliance with the License. * You may obtain a copy of the License at * * http://displaytag.sourceforge.net/license.html * * THIS PACKAGE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. */ package org.displaytag.model; import java.util.ArrayList; import java.util.Collections; import java.util.List; import org.apache.commons.lang.builder.ToStringBuilder; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.displaytag.decorator.TableDecorator; import org.displaytag.properties.TableProperties; import org.displaytag.util.ShortToStringStyle; /** * Table Model. Holds table data for presentation. * @author Fabrizio Giustina * @version $Revision: 2 $ ($Author: Chidambaram_pl $) */ public class TableModel { /** * logger. */ private static Log log = LogFactory.getLog(TableModel.class); /** * list of HeaderCell. */ private List headerCellList; /** * full list (contains Row objects). */ private List rowListFull; /** * list of data to be displayed in page. */ private List rowListPage; /** * sort order = ascending? */ private boolean sortOrderAscending = true; /** * sort full List? (false sort only displayed page). */ private boolean sortFullTable = true; /** * index of the sorted column (-1 if the table is not sorted). */ private int sortedColumn = -1; /** * Table decorator. */ private TableDecorator tableDecorator; /** * id inherited from the TableTag (needed only for logging). */ private String id; /** * configurable table properties. */ private TableProperties properties; /** * Starting offset for elements in the viewable list. */ private int pageOffset; /** * Response encoding. */ private String encoding; /** * Constructor for TableModel. * @param tableProperties table properties * @param charEncoding response encoding */ public TableModel(TableProperties tableProperties, String charEncoding) { this.rowListFull = new ArrayList(20); this.headerCellList = new ArrayList(20); this.properties = tableProperties; this.encoding = charEncoding; } /** * Sets the starting offset for elements in the viewable list. * @param offset The page offset to set. */ public void setPageOffset(int offset) { this.pageOffset = offset; } /** * Setter for the tablemodel id. * @param tableId same id of table tag, needed for logging */ public void setId(String tableId) { this.id = tableId; } /** * get the full list. * @return the full list containing Row objects */ public List getRowListFull() { return this.rowListFull; } /** * gets the partial (paginated) list. * @return the partial list to display in page (contains Row objects) */ public List getRowListPage() { return this.rowListPage; } /** * adds a Row object to the table. * @param row Row */ public void addRow(Row row) { row.setParentTable(this); if (log.isDebugEnabled()) { log.debug("[" + this.id + "] adding row " + row); } this.rowListFull.add(row); } /** * sets the sort full table property. If true the full list is sorted, if false sorting is applied only to the * displayed sublist. * @param sortFull boolean */ public void setSortFullTable(boolean sortFull) { this.sortFullTable = sortFull; } /** * return the sort full table property. * @return boolean true if sorting is applied to the full list */ public boolean isSortFullTable() { return this.sortFullTable; } /** * return the sort order of the page. * @return true if sort order is ascending */ public boolean isSortOrderAscending() { return this.sortOrderAscending; } /** * set the sort order of the list. * @param isSortOrderAscending true to sort in ascending order */ public void setSortOrderAscending(boolean isSortOrderAscending) { this.sortOrderAscending = isSortOrderAscending; } /** * @param rowList - the new value for this.rowListPage */ public void setRowListPage(List rowList) { this.rowListPage = rowList; } /** * getter for the Table Decorator. * @return TableDecorator */ public TableDecorator getTableDecorator() { return this.tableDecorator; } /** * setter for the table decorator. * @param decorator - the TableDecorator object */ public void setTableDecorator(TableDecorator decorator) { this.tableDecorator = decorator; } /** * returns true if the table is sorted. * @return boolean true if the table is sorted */ public boolean isSorted() { return this.sortedColumn != -1; } /** * returns the HeaderCell for the sorted column. * @return HeaderCell */ public HeaderCell getSortedColumnHeader() { if (this.sortedColumn < 0 || (this.sortedColumn > (this.headerCellList.size() - 1))) { return null; } return (HeaderCell) this.headerCellList.get(this.sortedColumn); } /** * return the number of columns in the table. * @return int number of columns */ public int getNumberOfColumns() { return this.headerCellList.size(); } /** * return true is the table has no columns. * @return boolean */ public boolean isEmpty() { return this.headerCellList.size() == 0; } /** * return the index of the sorted column. * @return index of the sorted column or -1 if the table is not sorted */ public int getSortedColumnNumber() { return this.sortedColumn; } /** * set the sorted column index. * @param sortIndex - the index of the sorted column */ public void setSortedColumnNumber(int sortIndex) { this.sortedColumn = sortIndex; } /** * Adds a column header (HeaderCell object). * @param headerCell HeaderCell */ public void addColumnHeader(HeaderCell headerCell) { if (this.sortedColumn == this.headerCellList.size()) { headerCell.setAlreadySorted(); } headerCell.setColumnNumber(this.headerCellList.size()); this.headerCellList.add(headerCell); } /** * List containing headerCell objects. * @return List containing headerCell objects */ public List getHeaderCellList() { return this.headerCellList; } /** * returns a RowIterator on the requested (full|page) list. * @return RowIterator * @param full if true returns an iterator on te full list, if false only on the * viewable part. * @see org.displaytag.model.RowIterator */ public RowIterator getRowIterator(boolean full) { RowIterator iterator = new RowIterator( full ? this.rowListFull : this.rowListPage, this.headerCellList, this.tableDecorator, this.pageOffset); // copy id for logging iterator.setId(this.id); return iterator; } /** * sorts the given list of Rows. The method is called internally by sortFullList() and sortPageList(). * @param list List */ private void sortRowList(List list) { if (isSorted()) { HeaderCell sortedHeaderCell = getSortedColumnHeader(); if (sortedHeaderCell != null) { // If it is an explicit value, then sort by that, otherwise sort by the property... if (sortedHeaderCell.getBeanPropertyName() != null || (this.sortedColumn != -1 && this.sortedColumn < this.headerCellList.size())) { Class[] parameterTypes = new Class[4]; parameterTypes[0]=Integer.class; parameterTypes[1]=String.class; parameterTypes[2]=TableDecorator.class; parameterTypes[3]=Boolean.class; Object[] parameterValues = new Object[4]; parameterValues[0]=new Integer(this.sortedColumn); if (sortedHeaderCell.getSortProperty() != null) { parameterValues[1]=sortedHeaderCell.getSortProperty(); } else { parameterValues[1]=sortedHeaderCell.getBeanPropertyName(); } parameterValues[2]=getTableDecorator(); parameterValues[3]=new Boolean(this.sortOrderAscending); if (log.isDebugEnabled()) { log.debug("Sort comparator is - " + sortedHeaderCell.getSortComparator()); } try { Collections.sort(list, SortComparatorFactory. loadSortComparator(sortedHeaderCell.getSortComparator(), parameterTypes, parameterValues)); } catch (org.displaytag.exception.SortComparatorInstantiationException e) { log.error("Exception occured while sorting - " + e.getMessage()); e.printStackTrace(); } } } } } /** * sort the list displayed in page. */ public void sortPageList() { if (log.isDebugEnabled()) { log.debug("[" + this.id + "] sorting page list"); } sortRowList(this.rowListPage); } /** * sort the full list of data. */ public void sortFullList() { if (log.isDebugEnabled()) { log.debug("[" + this.id + "] sorting full data"); } sortRowList(this.rowListFull); } /** * Returns the table properties. * @return the configured table properties. */ public TableProperties getProperties() { return this.properties; } /** * Getter for character encoding. * @return Returns the encoding used for response. */ public String getEncoding() { return encoding; } /** * @see java.lang.Object#toString() */ public String toString() { return new ToStringBuilder(this, ShortToStringStyle.SHORT_STYLE) // .append("rowListFull", this.rowListFull) //$NON-NLS-1$ .append("rowListPage", this.rowListPage) //$NON-NLS-1$ .append("properties", this.properties) //$NON-NLS-1$ .append("empty", this.isEmpty()) //$NON-NLS-1$ .append("encoding", this.encoding) //$NON-NLS-1$ .append("numberOfColumns", this.getNumberOfColumns()) //$NON-NLS-1$ .append("headerCellList", this.headerCellList) //$NON-NLS-1$ .append("sortFullTable", this.sortFullTable) //$NON-NLS-1$ .append("sortedColumnNumber", this.getSortedColumnNumber()) //$NON-NLS-1$ .append("sortOrderAscending", this.sortOrderAscending) //$NON-NLS-1$ .append("sortedColumnHeader", this.getSortedColumnHeader()) //$NON-NLS-1$ .append("sorted", this.isSorted()) //$NON-NLS-1$ .append("tableDecorator", this.tableDecorator) //$NON-NLS-1$ .toString(); } }