/* * The Unified Mapping Platform (JUMP) is an extensible, interactive GUI for * visualizing and manipulating spatial features with geometry and attributes. * * Copyright (C) 2003 Vivid Solutions * * This program is free software; you can redistribute it and/or modify it under * the terms of the GNU General Public License as published by the Free Software * Foundation; either version 2 of the License, or (at your option) any later * version. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License along with * this program; if not, write to the Free Software Foundation, Inc., 59 Temple * Place - Suite 330, Boston, MA 02111-1307, USA. * * For more information, contact: * * Vivid Solutions Suite #1A 2328 Government Street Victoria BC V8T 5G5 Canada * * (250)385-6040 www.vividsolutions.com */ package com.vividsolutions.jump.workbench.ui; import com.vividsolutions.jump.I18N; import com.vividsolutions.jump.workbench.model.Layer; import com.vividsolutions.jump.workbench.model.Layerable; import com.vividsolutions.jump.workbench.model.WMSLayer; import com.vividsolutions.jump.workbench.ui.images.IconLoader; import com.vividsolutions.jump.workbench.ui.plugin.wms.MapLayerPanel; import com.vividsolutions.jump.workbench.ui.renderer.RenderingManager; import java.awt.Color; import java.awt.Component; import java.awt.Font; import java.awt.GridBagConstraints; import java.awt.GridBagLayout; import java.awt.Insets; import java.awt.Rectangle; import javax.swing.DefaultListCellRenderer; import javax.swing.Icon; import javax.swing.JCheckBox; import javax.swing.JLabel; import javax.swing.JList; import javax.swing.JPanel; import javax.swing.JTree; import javax.swing.ListCellRenderer; import javax.swing.UIManager; import javax.swing.tree.TreeCellRenderer; public class LayerNameRenderer extends JPanel implements ListCellRenderer, TreeCellRenderer { //<<TODO>> See how the colour looks with other L&F's. [Jon Aquino] public static final String USE_CLOCK_ANIMATION_KEY = LayerNameRenderer.class .getName() + " - USE CLOCK ANIMATION"; private final static Color UNSELECTED_EDITABLE_FONT_COLOR = Color.red; private final static Color SELECTED_EDITABLE_FONT_COLOR = Color.yellow; protected JCheckBox checkBox = new JCheckBox(); private LayerColorPanel colorPanel = new LayerColorPanel(); GridBagLayout gridBagLayout = new GridBagLayout(); protected JLabel label = new JLabel(); private boolean indicatingEditability = false; private boolean indicatingProgress = false; private int progressIconSize = 13; private Icon[] progressIcons = null; private Icon clearProgressIcon = GUIUtil.resize(IconLoader .icon("Clear.gif"), progressIconSize); public static String PROGRESS_ICON_KEY = "PROGRESS_ICON"; public static String FEATURE_COUNT = I18N.get("ui.LayerNameRenderer.feature-count"); private DefaultListCellRenderer defaultListCellRenderer = new DefaultListCellRenderer(); private RenderingManager renderingManager; private JLabel progressIconLabel = new JLabel(); private Font font = new JLabel().getFont(); private Font editableFont = font.deriveFont(Font.BOLD); private Font unselectableFont = font.deriveFont(Font.ITALIC); private Font editableUnselectableFont = font.deriveFont(Font.BOLD+Font.ITALIC); private JLabel wmsIconLabel = new JLabel(MapLayerPanel.ICON); public LayerNameRenderer() { try { jbInit(); } catch (Exception ex) { ex.printStackTrace(); } } public void setIndicatingEditability(boolean indicatingEditability) { this.indicatingEditability = indicatingEditability; } public void setIndicatingProgress(boolean indicatingProgress, RenderingManager renderingManager) { this.indicatingProgress = indicatingProgress; this.renderingManager = renderingManager; } public JLabel getLabel() { return label; } /** * @return relative to this panel */ public Rectangle getCheckBoxBounds() { int i = gridBagLayout.getConstraints(checkBox).gridx; int x = 0; for (int j = 0; j < i; j++) { x += getColumnWidth(j); } return new Rectangle(x, 0, getColumnWidth(i), getRowHeight()); } /** * @param i * zero-based */ protected int getColumnWidth(int i) { validateTree(); return gridBagLayout.getLayoutDimensions()[0][i]; } protected int getRowHeight() { validateTree(); return gridBagLayout.getLayoutDimensions()[1][0]; } public void setCheckBoxVisible(boolean checkBoxVisible) { checkBox.setVisible(checkBoxVisible); } /** * Workaround for bug 4238829 in the Java bug database: "JComboBox * containing JPanel fails to display selected item at creation time" */ public void setBounds(int x, int y, int w, int h) { super.setBounds(x, y, w, h); validate(); } public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) { if (value == null) { return defaultListCellRenderer.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus); } Layerable layerable = (Layerable) value; label.setText(layerable.getName()); /*setToolTipText(layerable.getName() + ((layerable instanceof Layer && (((Layer) layerable).getDescription() != null) && (((Layer) layerable) .getDescription().trim().length() > 0)) ? (": " + ((Layer) layerable) .getDescription()) : ""));*/ String tooltip = ""; if (layerable instanceof Layer) { if (((Layer) layerable).getDescription() == null || ((Layer) layerable).getDescription().trim().length() == 0 || ((Layer) layerable).getDescription().equals(layerable.getName())) { tooltip = FEATURE_COUNT + " = " + ((Layer) layerable).getFeatureCollectionWrapper().size(); } else {tooltip = layerable.getName() + ": " + ((Layer) layerable).getDescription(); } } else tooltip = layerable.getName(); setToolTipText(tooltip); if (isSelected) { label.setForeground(list.getForeground()); //LDB: use this instead of following // label.setForeground(list.getSelectionForeground()); //LDB: causes Vista render problem label.setBackground(list.getSelectionBackground()); setForeground(list.getSelectionForeground()); setBackground(list.getSelectionBackground()); } else { label.setForeground(list.getForeground()); label.setBackground(list.getBackground()); setForeground(list.getForeground()); setBackground(list.getBackground()); } colorPanel.setVisible(layerable instanceof Layer); checkBox.setSelected(layerable.isVisible()); if (indicatingEditability && layerable instanceof Layer) { if (((Layer) layerable).isEditable()) { if (!((Layer) layerable).isSelectable()) { label.setFont(editableUnselectableFont); //LDB [2007-09-18] italic feedback }else { label.setFont(editableFont); } }else { if (!((Layer) layerable).isSelectable()) { label.setFont(unselectableFont); }else { label.setFont(font); } } label.setForeground(isSelected ? SELECTED_EDITABLE_FONT_COLOR : UNSELECTED_EDITABLE_FONT_COLOR); } else { label.setFont(font); } wmsIconLabel.setVisible(layerable instanceof WMSLayer); // Only show the progress icon (clocks) for WMSLayers and // database-backed layers, not Layers. Otherwise it's too busy. // [Jon Aquino] if (layerable.getBlackboard().get(USE_CLOCK_ANIMATION_KEY, false) && indicatingProgress && (renderingManager.getRenderer(layerable) != null) && renderingManager.getRenderer(layerable).isRendering()) { layerable.getBlackboard().put(PROGRESS_ICON_KEY, layerable.getBlackboard().get(PROGRESS_ICON_KEY, 0) + 1); if (layerable.getBlackboard().getInt(PROGRESS_ICON_KEY) > (getProgressIcons().length - 1)) { layerable.getBlackboard().put(PROGRESS_ICON_KEY, 0); } progressIconLabel.setIcon(getProgressIcons()[layerable .getBlackboard().getInt(PROGRESS_ICON_KEY)]); } else { progressIconLabel.setIcon(clearProgressIcon); layerable.getBlackboard().put(PROGRESS_ICON_KEY, null); } Color backgroundColor = list.getBackground(); Color selectionBackgroundColor = list.getSelectionBackground(); if (layerable instanceof Layer) { Layer layer = (Layer) layerable; colorPanel.init(layer, isSelected, backgroundColor, selectionBackgroundColor); } return this; } private JList list(JTree tree) { JList list = new JList(); list.setForeground(tree.getForeground()); list.setBackground(tree.getBackground()); list.setSelectionForeground(UIManager .getColor("Tree.selectionForeground")); list.setSelectionBackground(UIManager .getColor("Tree.selectionBackground")); return list; } public Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row, boolean hasFocus) { Layerable layerable = (Layerable) value; getListCellRendererComponent(list(tree), layerable, -1, selected, hasFocus); if (selected) { label.setForeground(UIManager.getColor("Tree.selectionForeground")); label.setBackground(UIManager.getColor("Tree.selectionBackground")); setForeground(UIManager.getColor("Tree.selectionForeground")); setBackground(UIManager.getColor("Tree.selectionBackground")); } else { label.setForeground(tree.getForeground()); label.setBackground(tree.getBackground()); setForeground(tree.getForeground()); setBackground(tree.getBackground()); } if (indicatingEditability && layerable instanceof Layer) { if (((Layer) layerable).isEditable()) { label.setForeground(selected ? SELECTED_EDITABLE_FONT_COLOR : UNSELECTED_EDITABLE_FONT_COLOR); } } return this; } void jbInit() throws Exception { checkBox.setVisible(false); this.setLayout(gridBagLayout); label.setOpaque(false); label.setText("Layer Name Goes Here"); checkBox.setOpaque(false); this.add(progressIconLabel, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.NONE, new Insets(0, 0, 0, 2), 0, 0)); this.add(wmsIconLabel, new GridBagConstraints(1, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.NONE, new Insets( 0, 0, 0, 2), 0, 0)); this.add(colorPanel, new GridBagConstraints(2, 0, 1, 1, 0.0, 0.0, GridBagConstraints.WEST, GridBagConstraints.NONE, new Insets(0, 0, 0, 5), 0, 0)); this.add(checkBox, new GridBagConstraints(3, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.NONE, new Insets( 0, 0, 0, 0), 0, 0)); this.add(label, new GridBagConstraints(4, 0, 1, 1, 1.0, 0.0, GridBagConstraints.WEST, GridBagConstraints.HORIZONTAL, new Insets(0, 0, 0, 0), 0, 0)); } private Icon[] getProgressIcons() { //Create lazily -- OptimizeIt tells me creating these images takes 20 //seconds [Jon Aquino 2004-05-14] if (progressIcons == null) { progressIcons = new Icon[] { GUIUtil.resize(IconLoader.icon("ClockN.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockNE.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockE.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockSE.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockS.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockSW.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockW.gif"), progressIconSize), GUIUtil.resize(IconLoader.icon("ClockNW.gif"), progressIconSize) }; } return progressIcons; } }