/* * Copyright (c) 2004,2009 Declarative Engineering LLC. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Declarative Engineering LLC * verson 1 which accompanies this distribution, and is available at * http://declarativeengineering.com/legal/DE_Developer_License_v1.txt */ package com.foundation.tcv.swt.server; import com.common.comparison.Comparator; import com.common.util.*; import com.common.util.optimized.IntArray; import com.foundation.metadata.Attribute; import com.foundation.tcv.swt.ITableComponent; import com.foundation.tcv.view.IAbstractRemoteViewComponent; import com.foundation.tcv.view.ViewMessage; import com.foundation.view.*; import com.foundation.view.resource.ResourceReference; /* * The simple table is a very simple implementation of a basic table. * Initialy this contains just text with no extra formatting using the native table component. */ public abstract class TableComponent extends CollectionComponent implements ITableComponent { /** The font resource for the control rows. (Note: This overrides the base font for the control defined by the Component class.) */ private MultiResourceAssociation rowFont = new MultiResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_FONT, false, null); /** The background color resource for the control. */ private MultiResourceAssociation rowBackgroundColorCustom = new MultiResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The foreground color resource for the control. */ private MultiResourceAssociation rowForegroundColorCustom = new MultiResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The background color resource for the control. */ private SingleResourceAssociation rowBackgroundColor = new SingleResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The foreground color resource for the control. */ private SingleResourceAssociation rowForegroundColor = new SingleResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The background color resource for the control. */ private SingleResourceAssociation rowBackgroundColorAlt = new SingleResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The foreground color resource for the control. */ private SingleResourceAssociation rowForegroundColorAlt = new SingleResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_COLOR, false, null); /** The selection color resource for the control. */ private VariableResourceAssociation rowSelectionGradient = new VariableResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_GRADIENT, false, null); /** The row height used. */ private SingleResourceAssociation rowHeight = new SingleResourceAssociation(this, this, getViewContext(), ResourceAssociation.TYPE_INTEGER, false, null); /** The collection of columns in order of appearance (left to right). */ private IList tableColumns = new LiteList(16); /** Tracks whether or not to try updating the selection if the collection changed. */ private boolean isSelectionInvalid = false; /** The mapping of image decoration data by the decoration object. This is used to improve efficiency when placing a decoration on multiple rows. */ protected IHashMap decorationDataMap = null; /** The last used decoration data identifier. The identifier is used to tell the client which decoration is being talked about. */ private int nextDecorationDataId = 0; /** * Maintains the reference counter and ID for each decoration in the decoration data map. Also allows a decoration to be shared by multiple rows. */ protected class DecorationData { /** The data identifier used to notify the client about this decoration's change in status. */ private int decorationId = nextDecorationDataId++; /** The number of times the data is being referenced (by rows displaying it). */ private int referenceCount = 1; /** * DecorationData constructor. * @param decoration The decoration this data object supports. */ public DecorationData(ImageDecoration decoration) { }//DecorationData()// /** * Increments the reference counter for the decoration. */ public void incrementReferenceCount() { referenceCount++; }//incrementReferenceCount()// /** * Decrements the reference counter for the decoration. * @return The reference count for the decoration data. */ public int decrementReferenceCount() { return --referenceCount; }//decrementReferenceCount()// }//DecorationData// /** * Encapsulates all the data pertaining to a single column in the table component. */ public static abstract class AbstractColumn implements IAbstractComponent, IAbstractRemoteViewComponent { /** * Registers an item in the collection with this column. *

An item can be registered more than once, but must be unregistered just as many times.

* @param rowObject The row to be registered. */ protected void registerItem(RowObject rowObject) { }//registerItem()// /** * Unregisters an item that had been previously registered. * @param rowObject The row to be unregistered. */ protected void unregisterItem(RowObject rowObject) { }//unregisterItem()// /** * Unregisters all items that had been previously registered. */ protected void unregisterAllItems() { }//unregisterAllItems()// /** * Refreshes the value for the cell(s) denoted by the item representing the row(s) and this column. * @param rowObject The row data containing the row's value and metadata. * @return Whether the cell data was altered by the refresh. */ protected abstract boolean refreshCellData(RowObject rowObject); /** * Collects the cell data for the given row and this column. * @param rowObject The row data containing the row's value and metadata. * @param cellData The table cell data structure to be filled in. */ protected void collectCellData(RowObject rowObject, TableCellData cellData) { }//collectCellData()// /** * Gets the column's creation index. * @return The index assigned to this column and used to facilitate communication with the actual column resource in the display. */ protected abstract int getIndex(); /** * Sets the column's creation index. * @param index The index assigned to this column and used to facilitate communication with the actual column resource in the display. */ protected abstract void setIndex(int index); /** * Initializes the column before the table component is initialized. */ protected abstract void initialize(); /** * Refreshes the column. */ protected abstract void refresh(); /** * Releases the column before the table component is released. */ protected abstract void release(); /* (non-Javadoc) * @see com.foundation.tcv.view.IAbstractViewComponent#processMessage(com.foundation.tcv.view.ViewMessage) */ public Object processMessage(ViewMessage viewMessage) { return null; }//processMessage()// }//AbstractColumn// /** * TableComponent constructor. * @param parent The parent container for this component. * @param name The name of the component. */ public TableComponent(Container parent, String name, int style) { super(parent, name, style); }//TableComponent()// /** * Adds a column to the component. * @param column The column to be added. */ protected void addColumn(AbstractColumn column) { if(isInitialized()) { //Allow the collection to suspend activites that would adversly affect performance while the collection make large scale changes.// preChangeCollection(); }//if// try { tableColumns.add(column.getIndex(), column); //Update the other column indices.// for(int index = column.getIndex() + 1; index < tableColumns.getSize(); index++) { ((AbstractColumn) tableColumns.get(index)).setIndex(index); }//for// //Notify the client.// sendMessage(MESSAGE_ADD_COLUMN, new Integer(column.getIndex())); }//try// finally { if(isInitialized()) { //Allow the table to refresh its self.// postChangeCollection(); }//if// }//finally// }//addColumn()// /** * Gets the number of columns in the table. * @return The count of columns. */ protected int getColumnCount() { return tableColumns.getSize(); }//getColumnCount()// /** * Gets the column at the given index. * @param index The zero based column index. * @return The column at the given index. */ protected AbstractColumn getColumn(int index) { return (AbstractColumn) tableColumns.get(index); }//getColumn()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalViewRefreshCollection(com.common.util.ICollection, com.common.util.ICollection) */ protected void internalViewRefreshCollection(ICollection newCollection, ICollection oldCollection) { itemAllRemoved(); if(newCollection != null) { // TableRowData[] data = new TableRowData[newCollection.getSize()]; // Object[] hiddenData = new Object[newCollection.getSize()]; IIterator itemIterator = newCollection.iterator(); int itemIndex = 0; //Get the array of strings representing the list contents.// while(itemIterator.hasNext()) { Object item = itemIterator.next(); itemAdded(item, itemIndex++, true); // RowObject rowObject = itemAdded(value, index, false); // // //Add the item mappings without notifying the client.// // if(rowObject.isFirstReference()) { // data[itemIndex] = new TableRowData(getRowObject(item).objectId, itemIndex, null, null); // hiddenData[itemIndex] = getItemHiddenData(item); // }//if// // else { // data[itemIndex] = new TableRowData(getRowObject(item).objectId, itemIndex, getItemData(rowObject)); // hiddenData[itemIndex] = null; // }//else// }//while// //TODO: It would probably be more efficient to send many small messages and allow the sending code to take care of bundling to the optimum size. //addMessageHold(); Use this to block message sending until finished? May not need it since the messages should bundle up anyway. // sendMessage(MESSAGE_SET_ITEMS, data, hiddenData, -1, -1); }//if// //If the selection was invalid previously then refresh the selection since it may no longer be invalid.// if(isSelectionInvalid) { internalViewRefreshSelection(); }//if// }//internalViewRefreshCollection()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#getItemData(com.foundation.tcv.swt.server.RowObject) */ protected Object getItemData(RowObject rowObject) { TableRowData rowData = createTableRowData(); TableCellData[] cellDatas = rowData.getColumnData(); collectRowData(rowObject, rowData); for(int index = 0; index < cellDatas.length; index++) { AbstractColumn column = (AbstractColumn) tableColumns.get(index); if(column != null) { column.refreshCellData(rowObject); cellDatas[index] = createTableCellData(); column.collectCellData(rowObject, cellDatas[index]); }//if// }//for// return rowData; }//getItemData()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalViewRefreshSelection(java.lang.Object) */ protected void internalViewRefreshSelection(Object selectedItem) { if(selectedItem != null) { RowObject rowObject = (RowObject) getRowObject(selectedItem); if(rowObject == null) { isSelectionInvalid = true; sendMessage(MESSAGE_SET_SELECTION, null); }//if// else { isSelectionInvalid = false; sendMessage(MESSAGE_SET_SELECTION, new int[] {rowObject.objectId}); }//else// }//if// else { //No selection.// sendMessage(MESSAGE_SET_SELECTION, null); }//else// }//internalViewRefreshSelection()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalViewRefreshSelections(com.common.util.ICollection, com.common.util.ICollection) */ protected void internalViewRefreshSelections(ICollection newSelections, ICollection oldSelections) { if(newSelections != null) { IntArray selectionObjectIds = new IntArray(newSelections.getSize()); IIterator selectionIterator = newSelections.iterator(); //Apply differences between the selection collection and the control selection. Also remove all impossible selections.// while(selectionIterator.hasNext()) { Object selection = selectionIterator.next(); RowObject rowObject = (RowObject) getRowObject(selection); if(rowObject == null) { //An invalid selection because the selection is not in the collection of displayed values.// selectionIterator.remove(); }//if// else { selectionObjectIds.add(rowObject.objectId); }//else// }//while// sendMessage(MESSAGE_SET_SELECTION, selectionObjectIds.toArray()); }//if// else { //Remove all selections.// sendMessage(MESSAGE_REMOVE_ALL_SELECTIONS, null); }//else// }//internalViewRefreshSelections()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalViewInitialize() */ protected void internalViewInitialize() { rowBackgroundColor.initialize(); rowForegroundColor.initialize(); rowBackgroundColorAlt.initialize(); rowForegroundColorAlt.initialize(); rowSelectionGradient.initialize(); rowBackgroundColorCustom.initialize(); rowForegroundColorCustom.initialize(); rowFont.initialize(); rowHeight.initialize(); //Initialize all the columns.// for(int columnIndex = 0; columnIndex < tableColumns.getSize(); columnIndex++) { ((AbstractColumn) tableColumns.get(columnIndex)).initialize(); }//for// super.internalViewInitialize(); }//internalViewInitialize()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalViewRefresh() */ protected void internalViewRefresh() { sendMessage(MESSAGE_SUSPEND_ROW_COLOR_UPDATES, null, null, -1, -1); internalViewRefreshRowHeight(); if(rowSelectionGradient.isSingle() && rowSelectionGradient.refresh(null)) { sendMessage(MESSAGE_SET_ROW_SELECTION_GRADIENT, rowSelectionGradient.getValue(null), null, -1, -1); }//if// if(rowBackgroundColor.refresh()) { sendMessage(MESSAGE_SET_ROW_BACKGROUND_COLOR, rowBackgroundColor.getValue(), null, -1, -1); }//if// if(rowForegroundColor.refresh()) { sendMessage(MESSAGE_SET_ROW_FOREGROUND_COLOR, rowForegroundColor.getValue(), null, -1, -1); }//if// if(rowBackgroundColorAlt.refresh()) { sendMessage(MESSAGE_SET_ROW_BACKGROUND_COLOR_ALT, rowBackgroundColorAlt.getValue(), null, -1, -1); }//if// if(rowForegroundColorAlt.refresh()) { sendMessage(MESSAGE_SET_ROW_FOREGROUND_COLOR_ALT, rowForegroundColorAlt.getValue(), null, -1, -1); }//if// sendMessage(MESSAGE_RESUME_ROW_COLOR_UPDATES, null, null, -1, -1); super.internalViewRefresh(); //Refresh all the columns.// for(int columnIndex = 0; columnIndex < tableColumns.getSize(); columnIndex++) { ((AbstractColumn) tableColumns.get(columnIndex)).refresh(); }//for// }//internalViewRefresh()// /** * Refreshes the component's row height. */ protected void internalViewRefreshRowHeight() { if(rowHeight.refresh()) { Integer height = (Integer) rowHeight.getValue(); //Reset to the default height if null but was previously non-null.// sendMessage(MESSAGE_SET_ROW_HEIGHT, height, null, -1, -1); }//if// }//internalViewRefreshRowHeight()// /* (non-Javadoc) * @see com.foundation.view.swt.AbstractComponent#internalViewRelease() */ protected void internalViewRelease() { //Release all the columns.// for(int columnIndex = 0; columnIndex < tableColumns.getSize(); columnIndex++) { ((AbstractColumn) tableColumns.get(columnIndex)).release(); }//for// rowBackgroundColor.release(); rowForegroundColor.release(); rowBackgroundColorAlt.release(); rowForegroundColorAlt.release(); rowSelectionGradient.release(); rowBackgroundColorCustom.release(); rowForegroundColorCustom.release(); rowFont.release(); rowHeight.release(); super.internalViewRelease(); }//internalViewRelease()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.AbstractComponent#internalOnValueChanged(com.foundation.view.MultiResourceAssociation, java.lang.Object, java.lang.Object, boolean) */ protected void internalOnValueChanged(MultiResourceAssociation resourceAssociation, Object item, Object data, boolean isUpdate) { if(isInitialized()) { if(resourceAssociation == rowBackgroundColorCustom) { //Verify that the item cell data has actually been altered.// if(rowBackgroundColorCustom.refresh(item)) { sendMessage(MESSAGE_SET_ROW_CUSTOM_BACKGROUND_COLOR, rowBackgroundColorCustom.getValue(item), null, -1, -1); }//if// }//if// else if(resourceAssociation == rowForegroundColorCustom) { //Verify that the item cell data has actually been altered.// if(rowForegroundColorCustom.refresh(item)) { sendMessage(MESSAGE_SET_ROW_CUSTOM_FOREGROUND_COLOR, rowForegroundColorCustom.getValue(item), null, -1, -1); }//if// }//else if// else if(rowSelectionGradient.hasAssociation(resourceAssociation)) { //Verify that the item cell data has actually been altered.// if(rowSelectionGradient.refresh(item)) { sendMessage(MESSAGE_SET_ROW_SELECTION_GRADIENT, rowSelectionGradient.getValue(item), null, -1, -1); }//if// }//else if// else if(resourceAssociation == rowFont) { //Verify that the item cell data has actually been altered.// if(rowFont.refresh(item)) { sendMessage(MESSAGE_SET_ROW_FONT, rowFont.getValue(item), null, -1, -1); }//if// }//else if// else { super.internalOnValueChanged(resourceAssociation, item, data, isUpdate); }//else// }//if// }//internalOnValueChanged()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#internalOnValueChanged(com.foundation.view.SingleResourceAssociation, boolean) */ protected void internalOnValueChanged(SingleResourceAssociation resourceAssociation, int flags) { if(isInitialized()) { if(resourceAssociation == rowHeight) { sendMessage(MESSAGE_SET_ROW_HEIGHT, rowHeight.getValue(), null, -1, -1); }//if// else if(resourceAssociation == rowBackgroundColor) { sendMessage(MESSAGE_SET_ROW_BACKGROUND_COLOR, rowBackgroundColor.getValue(), null, -1, -1); }//else if// else if(resourceAssociation == rowForegroundColor) { sendMessage(MESSAGE_SET_ROW_FOREGROUND_COLOR, rowForegroundColor.getValue(), null, -1, -1); }//else if// else if(resourceAssociation == rowBackgroundColorAlt) { sendMessage(MESSAGE_SET_ROW_BACKGROUND_COLOR_ALT, rowBackgroundColorAlt.getValue(), null, -1, -1); }//else if// else if(resourceAssociation == rowForegroundColorAlt) { sendMessage(MESSAGE_SET_ROW_FOREGROUND_COLOR_ALT, rowForegroundColorAlt.getValue(), null, -1, -1); }//else if// else { super.internalOnValueChanged(resourceAssociation, flags); }//else// }//if// }//internalOnValueChanged()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#itemSorted(int[]) */ protected void itemSorted(int[] mapping) { sendMessage(MESSAGE_ORDER_ROWS, mapping); }//itemSorted()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#selectionAdded(java.lang.Object) */ protected void selectionAdded(Object value) { RowObject rowObject = getRowObject(value); if(rowObject != null) { sendMessage(MESSAGE_ADD_SELECTION, null, null, rowObject.objectId, -1); }//if// }//selectionAdded()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#selectionRemoved(java.lang.Object) */ protected void selectionRemoved(Object value) { RowObject rowObject = getRowObject(value); if(rowObject != null) { sendMessage(MESSAGE_REMOVE_SELECTION, null, null, rowObject.objectId, -1); }//if// }//selectionRemoved()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#selectionAllRemoved() */ protected void selectionAllRemoved() { sendMessage(MESSAGE_REMOVE_ALL_SELECTIONS, null); }//selectionAllRemoved()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#registerItem(com.foundation.tcv.swt.server.RowObject) */ protected void registerItem(RowObject rowObject) { super.registerItem(rowObject); //Add the item to each of the columns so we receive updates.// for(int index = 0; index < tableColumns.getSize(); index++) { ((AbstractColumn) tableColumns.get(index)).registerItem(rowObject); }//for// }//registerItem()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#unregisterItem(com.foundation.tcv.swt.server.RowObject) */ protected void unregisterItem(RowObject rowObject) { super.unregisterItem(rowObject); //Unregister the value with the columns so we stop receiving updates.// for(int index = 0; index < tableColumns.getSize(); index++) { ((AbstractColumn) tableColumns.get(index)).unregisterItem(rowObject); }//for// }//unregisterItem()// /* (non-Javadoc) * @see com.foundation.tcv.swt.server.CollectionComponent#unregisterItems() */ protected void unregisterItems() { super.unregisterItems(); //Unregister the items from the columns so we stop recieving updates.// for(int index = 0; index < tableColumns.getSize(); index++) { ((AbstractColumn) tableColumns.get(index)).unregisterAllItems(); }//for// }//unregisterItems()// /** * Collects the data for the given row item. * @param rowObject The row data containing the row's value and metadata. * @param rowData The row data container. */ protected void collectRowData(RowObject rowObject, TableRowData rowData) { Object item = rowObject.value; rowBackgroundColorCustom.refresh(item); rowData.setBackgroundColor(rowBackgroundColorCustom.getValue(item)); rowForegroundColorCustom.refresh(item); rowData.setForegroundColor(rowForegroundColorCustom.getValue(item)); rowFont.refresh(item); rowData.setFont(rowFont.getValue(item)); }//collectRowData()// /** * Creates a new data container for the table row. *

Subclasses that add row data elements should override this.

* @return The new container for row data. */ protected TableRowData createTableRowData() { return new TableRowData(new TableCellData[getColumnCount()]); }//createTableRowData()// /** * Creates a new data container for the table cell. *

Subclasses that add row data elements should override this.

* @return The new container for cell data. */ protected TableCellData createTableCellData() { return new TableCellData(); }//createTableRowData()// /* (non-Javadoc) * @see com.foundation.tcv.view.IViewComponent#processMessage(com.foundation.tcv.model.ViewMessage) */ public Object processMessage(ViewMessage viewMessage) { Object retVal = null; switch(viewMessage.getMessageNumber()) { case MESSAGE_VIEW_SYNCHRONIZE_SELECTION: { //Receive the selection information from the client.// Object messageData = viewMessage.getMessageData(); if(getAllowMultiSelection()) { int[] selectionObjectIds = (int[]) messageData; ICollection modelSelections = getModelSelections(); //Prevent the selection additions from causing a feedback loop.// suspendSelectionHooks = true; try { //We require that the collection for the selections be created by the model.// if(modelSelections != null) { if(selectionObjectIds != null) { LiteHashSet selectedRowSet = new LiteHashSet(selectionObjectIds.length, LiteHashSet.DEFAULT_LOAD_FACTOR, Comparator.getIdentityComparator(), LiteHashSet.STYLE_ADD_DUPLICATES); IIterator iterator = modelSelections.iterator(); LiteList removed = new LiteList(modelSelections.getSize()); for(int index = 0; index < selectionObjectIds.length; index++) { selectedRowSet.add(getRowObject(selectionObjectIds[index]).value); }//for// //Iterate over the model's selections, removing those that are not currently selected and tracking those not yet in the model selection collection.// while(iterator.hasNext()) { Object nextValue = iterator.next(); RowObject nextRowObject = nextValue == null ? null : getRowObject(nextValue); if(nextRowObject != null) { //Check to see if the model selection is in the view.// if(!selectedRowSet.remove(nextRowObject.value)) { //Remove the selection from the model if it is not currently selected in the view.// removed.add(nextValue); }//if// }//if// else { //Remove the model selection since it is invalid.// removed.add(nextValue); }//else// }//while// //Add any selections not already in the model selection collection.// modelSelections.replaceAll(removed, selectedRowSet); }//if// else { modelSelections.removeAll(); }//else// }//if// }//try// finally { suspendSelectionHooks = false; }//finally// }//if// else { int selectedObjectId = messageData != null ? ((Integer) messageData).intValue() : -1; RowObject selectedRowObject = (RowObject) (selectedObjectId >= 0 ? getRowObject(selectedObjectId) : null); setModelSelection(selectedRowObject == null ? null : selectedRowObject.value); }//else// if(getAutoValidate()) { postSynchronizeValidate(); }//if// break; }//case// default: { retVal = super.processMessage(viewMessage); }//default// }//switch// return retVal; }//processMessage()// /** * Sets the component's default background color. * @param backgroundColor The default background color. */ public void setRowBackgroundColor(JefColor backgroundColor) { verifyThread(); this.rowBackgroundColor.setDefaultValue(backgroundColor); }//setRowHeaderBackgroundColor()// /** * Sets the component's default background color. * @param backgroundColor The default background color. */ public void setRowBackgroundColor(ResourceReference backgroundColor) { verifyThread(); this.rowBackgroundColor.setDefaultValue(backgroundColor); }//setRowHeaderBackgroundColor()// /** * Sets the component's default foreground color. * @param foregroundColor The default foreground color. */ public void setRowForegroundColor(JefColor foregroundColor) { verifyThread(); this.rowForegroundColor.setDefaultValue(foregroundColor); }//setRowHeaderForegroundColor()// /** * Sets the component's default foreground color. * @param foregroundColor The default foreground color. */ public void setRowForegroundColor(ResourceReference foregroundColor) { verifyThread(); this.rowForegroundColor.setDefaultValue(foregroundColor); }//setRowHeaderForegroundColor()// /** * Sets the component's default background alternate color. * @param backgroundColorAlt The default background alternate color. */ public void setRowBackgroundColorAlt(JefColor backgroundColorAlt) { verifyThread(); this.rowBackgroundColorAlt.setDefaultValue(backgroundColorAlt); }//setRowHeaderBackgroundColorAlt()// /** * Sets the component's default background alternate color. * @param backgroundColorAlt The default background alternate color. */ public void setRowBackgroundColorAlt(ResourceReference backgroundColorAlt) { verifyThread(); this.rowBackgroundColorAlt.setDefaultValue(backgroundColorAlt); }//setRowHeaderBackgroundColorAlt()// /** * Sets the component's default foreground alternate color. * @param foregroundColorAlt The default foreground alternate color. */ public void setRowForegroundColorAlt(JefColor foregroundColorAlt) { verifyThread(); this.rowForegroundColorAlt.setDefaultValue(foregroundColorAlt); }//setRowHeaderForegroundColorAlt()// /** * Sets the component's default foreground alternate color. * @param foregroundColorAlt The default foreground alternate color. */ public void setRowForegroundColorAlt(ResourceReference foregroundColorAlt) { verifyThread(); this.rowForegroundColorAlt.setDefaultValue(foregroundColorAlt); }//setRowHeaderForegroundColorAlt()// /** * Sets the component's default selection gradient. * @param selectionGradient The default selection gradient. */ public void setRowSelectionGradient(JefGradient selectionGradient) { verifyThread(); this.rowSelectionGradient.setDefaultValue(selectionGradient); }//setRowHeaderSelectionGradient()// /** * Sets the component's default selection gradient. * @param selectionGradient The default selection gradient. */ public void setRowSelectionGradient(ResourceReference selectionGradient) { verifyThread(); this.rowSelectionGradient.setDefaultValue(selectionGradient); }//setRowSelectionGradient()// /** * Sets the font for the row header. This will be the default font if there is a font attribute associated with this component. * @param font The default font metadata. */ public void setRowFont(JefFont[] font) { verifyThread(); this.rowFont.setDefaultValue(font); }//setRowHeaderFont()// /** * Sets the font for the row header. This will be the default font if there is a font attribute associated with this component. * @param font The default font metadata. */ public void setRowFont(ResourceReference font) { verifyThread(); this.rowFont.setDefaultValue(font); }//setRowHeaderFont()// /** * Sets the height for the rows. * @param height The row height in pixels. */ public void setRowHeight(Integer height) { verifyThread(); this.rowHeight.setDefaultValue(height); }//setRowHeight()// /** * Sets the association container used to access the row background color for each row. *

The resulting value will override the row's normal color.

* @param container The row background color association metadata. */ public void setRowBackgroundColorCustomAssociation(MultiAssociationContainer container) { verifyThread(); this.rowBackgroundColorCustom.setAssociations(container); }//setRowBackgroundColorCustomAssociation()// /** * Sets the association container used to access the row foreground color for each row. *

The resulting value will override the row's normal color.

* @param container The row foreground color association metadata. */ public void setRowForegroundColorCustomAssociation(MultiAssociationContainer container) { verifyThread(); this.rowForegroundColorCustom.setAssociations(container); }//setRowForegroundColorCustomAssociation()// /** * Sets the association container used to access the row background color. * @param container The row background color association metadata. */ public void setRowBackgroundColorAssociation(SingleAssociationContainer container) { verifyThread(); this.rowBackgroundColor.setAssociations(container); }//setRowBackgroundColorAssociation()// /** * Sets the association container used to access the row foreground color. * @param container The row foreground color association metadata. */ public void setRowForegroundColorAssociation(SingleAssociationContainer container) { verifyThread(); this.rowForegroundColor.setAssociations(container); }//setRowForegroundColorAssociation()// /** * Sets the association container used to access the alternate row background color. * @param container The alternate row background color association metadata. */ public void setRowBackgroundColorAltAssociation(SingleAssociationContainer container) { verifyThread(); this.rowBackgroundColorAlt.setAssociations(container); }//setRowBackgroundColorAltAssociation()// /** * Sets the association container used to access the alternate row foreground color. * @param container The alternate row foreground color association metadata. */ public void setRowForegroundColorAltAssociation(SingleAssociationContainer container) { verifyThread(); this.rowForegroundColorAlt.setAssociations(container); }//setRowForegroundColorAltAssociation()// /** * Sets the association container used to access the row selection color. * @param container The row selection color association metadata. */ public void setRowSelectionGradientAssociation(AssociationContainer container) { verifyThread(); this.rowSelectionGradient.setAssociations(container); }//setRowSelectionGradientAssociation()// /** * Sets the association container used to access the row font. * @param container The row font association metadata. */ public void setRowFontAssociation(MultiAssociationContainer container) { verifyThread(); this.rowFont.setAssociations(container); }//setRowFontAssociation()// /** * Sets the association container used to access the row height. * @param container The row font association metadata. */ public void setRowHeightAssociation(SingleAssociationContainer container) { verifyThread(); this.rowHeight.setAssociations(container); }//setRowHeightAssociation()// /** * Determines whether the control is capable of processing collection item decorations. * @return Whether the control can handle collection item decorations. */ protected boolean canDecorate() { return true; }//canDecorate()// /* (non-Javadoc) * @see com.foundation.controller.IDecorationMultiListener#isListening(java.lang.Class, java.lang.Object, com.foundation.metadata.Attribute) */ public boolean isListening(Class decorationType, Object object, Attribute attribute) { return super.isListening(decorationType, object, attribute) && (HighlightDecoration.class.isAssignableFrom(decorationType) || ImageDecoration.class.isAssignableFrom(decorationType)); }//isListening()// /* (non-Javadoc) * @see com.foundation.controller.IDecorationMultiListener#addDecoration(com.foundation.view.AbstractDecoration, java.lang.Object, com.foundation.metadata.Attribute) */ public void addDecoration(AbstractDecoration decoration, Object object, Attribute attribute) { if(decoration instanceof HighlightDecoration) { sendMessage(MESSAGE_ADD_ROW_HIGHLIGHT_DECORATION, decoration, null, getRowObject(object).objectId, -1); }//if// else if(decoration instanceof ImageDecoration) { //TODO: Support ControlDecoration also or instead? DecorationData decorationData = (DecorationData) decorationDataMap.get(decoration); if(decorationData == null) { decorationData = new DecorationData((ImageDecoration) decoration); decorationDataMap.put(decoration, decorationData); sendMessage(MESSAGE_ADD_ROW_IMAGE_DECORATION, decoration, null, getRowObject(object).objectId, decorationData.decorationId); }//if// else { decorationData.incrementReferenceCount(); sendMessage(MESSAGE_ADD_ROW_IMAGE_DECORATION, null, null, getRowObject(object).objectId, decorationData.decorationId); }//else// }//else if// }//addDecoration()// /* (non-Javadoc) * @see com.foundation.controller.IDecorationMultiListener#removeDecoration(com.foundation.view.AbstractDecoration, java.lang.Object, com.foundation.metadata.Attribute) */ public void removeDecoration(AbstractDecoration decoration, Object object, Attribute attribute) { if(decoration instanceof HighlightDecoration) { sendMessage(MESSAGE_REMOVE_ROW_HIGHLIGHT_DECORATION, null, null, getRowObject(object).objectId, -1); }//if// else if(decoration instanceof ImageDecoration) { DecorationData decorationData = (DecorationData) decorationDataMap.get(decoration); if(decorationData.decrementReferenceCount() == 0) { decorationDataMap.remove(decoration); }//if// sendMessage(MESSAGE_REMOVE_ROW_IMAGE_DECORATION, null, null, getRowObject(object).objectId, decorationData.decorationId); }//else if// }//removeDecoration()// }//TableComponent//