package org.simantics.spreadsheet.ui; import java.awt.Color; import java.awt.Component; import java.awt.Rectangle; import java.io.Serializable; import javax.swing.JComponent; import javax.swing.JLabel; import javax.swing.JTable; import javax.swing.SwingConstants; import javax.swing.border.Border; import javax.swing.table.TableCellRenderer; public class ColumnHeaderRenderer extends JLabel implements TableCellRenderer, Serializable { private static final long serialVersionUID = 1L; /** * An empty Border. This field might not be used. To change the * Border used by this renderer override the * getTableCellRendererComponent method and set the border * of the returned component directly. */ // We need a place to store the color the JLabel should be returned // to after its foreground and background colors have been set // to the selection background color. // These ivars will be made protected when their names are finalized. private Color unselectedForeground; private Color unselectedBackground; /** * Creates a default table cell renderer. */ public ColumnHeaderRenderer() { super(); setOpaque(true); setHorizontalAlignment(SwingConstants.CENTER); setBackground(DefaultLookup.GRAY); setBorder(getNoFocusBorder()); setName("Table.cellRenderer"); } private Border getNoFocusBorder() { return TableBorder.BORDER; } /** * Overrides JComponent.setForeground to assign * the unselected-foreground color to the specified color. * * @param c set the foreground color to this value */ public void setForeground(Color c) { super.setForeground(c); unselectedForeground = c; } /** * Overrides JComponent.setBackground to assign * the unselected-background color to the specified color. * * @param c set the background color to this value */ public void setBackground(Color c) { super.setBackground(c); unselectedBackground = c; } /** * Notification from the UIManager that the look and feel * [L&F] has changed. * Replaces the current UI object with the latest version from the * UIManager. * * @see JComponent#updateUI */ public void updateUI() { super.updateUI(); setForeground(null); setBackground(null); } // implements javax.swing.table.TableCellRenderer /** * * Returns the default table cell renderer. *

* During a printing operation, this method will be called with * isSelected and hasFocus values of * false to prevent selection and focus from appearing * in the printed output. To do other customization based on whether * or not the table is being printed, check the return value from * {@link javax.swing.JComponent#isPaintingForPrint()}. * * @param table the JTable * @param value the value to assign to the cell at * [row, column] * @param isSelected true if cell is selected * @param hasFocus true if cell has focus * @param row the row of the cell to render * @param column the column of the cell to render * @return the default table cell renderer * @see javax.swing.JComponent#isPaintingForPrint() */ public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { Color fg = null; Color bg = null; JTable.DropLocation dropLocation = table.getDropLocation(); if (dropLocation != null && !dropLocation.isInsertRow() && !dropLocation.isInsertColumn() && dropLocation.getRow() == row && dropLocation.getColumn() == column) { fg = DefaultLookup.getColor(this, ui, "Table.dropCellForeground"); bg = DefaultLookup.getColor(this, ui, "Table.dropCellBackground"); isSelected = true; } if (isSelected) { super.setForeground(fg == null ? table.getSelectionForeground() : fg); super.setBackground(bg == null ? table.getSelectionBackground() : bg); } else { Color background = unselectedBackground != null ? unselectedBackground : table.getBackground(); if (background == null || background instanceof javax.swing.plaf.UIResource) { Color alternateColor = DefaultLookup.getColor(this, ui, "Table.alternateRowColor"); if (alternateColor != null && row % 2 == 0) background = alternateColor; } super.setForeground(unselectedForeground != null ? unselectedForeground : table.getForeground()); super.setBackground(background); } setFont(table.getFont()); if (hasFocus) { Border border = null; if (isSelected) { border = DefaultLookup.getBorder(this, ui, "Table.focusSelectedCellHighlightBorder"); } if (border == null) { border = DefaultLookup.getBorder(this, ui, "Table.focusCellHighlightBorder"); } setBorder(border); if (!isSelected && table.isCellEditable(row, column)) { Color col; col = DefaultLookup.getColor(this, ui, "Table.focusCellForeground"); if (col != null) { super.setForeground(col); } col = DefaultLookup.getColor(this, ui, "Table.focusCellBackground"); if (col != null) { super.setBackground(col); } } } else { setBorder(getNoFocusBorder()); } setValue(value); return this; } /* * The following methods are overridden as a performance measure to * to prune code-paths are often called in the case of renders * but which we know are unnecessary. Great care should be taken * when writing your own renderer to weigh the benefits and * drawbacks of overriding methods like these. */ /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public boolean isOpaque() { Color back = getBackground(); Component p = getParent(); if (p != null) { p = p.getParent(); } // p should now be the JTable. boolean colorMatch = (back != null) && (p != null) && back.equals(p.getBackground()) && p.isOpaque(); return !colorMatch && super.isOpaque(); } /** * Overridden for performance reasons. * See the Implementation Note * for more information. * * @since 1.5 */ public void invalidate() {} /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public void validate() {} /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public void revalidate() {} /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public void repaint(long tm, int x, int y, int width, int height) {} /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public void repaint(Rectangle r) { } /** * Overridden for performance reasons. * See the Implementation Note * for more information. * * @since 1.5 */ public void repaint() { } /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ protected void firePropertyChange(String propertyName, Object oldValue, Object newValue) { // Strings get interned... if (propertyName=="text" || propertyName == "labelFor" || propertyName == "displayedMnemonic" || ((propertyName == "font" || propertyName == "foreground") && oldValue != newValue && getClientProperty(javax.swing.plaf.basic.BasicHTML.propertyKey) != null)) { super.firePropertyChange(propertyName, oldValue, newValue); } } /** * Overridden for performance reasons. * See the Implementation Note * for more information. */ public void firePropertyChange(String propertyName, boolean oldValue, boolean newValue) { } /** * Sets the String object for the cell being rendered to * value. * * @param value the string value for this cell; if value is * null it sets the text value to an empty string * @see JLabel#setText * */ protected void setValue(Object value) { setText((value == null) ? "" : value.toString()); } }