001 /* This file is part of the project "Hilbert II" - http://www.qedeq.org
002 *
003 * Copyright 2000-2013, Michael Meyling <mime@qedeq.org>.
004 *
005 * "Hilbert II" is free software; you can redistribute
006 * it and/or modify it under the terms of the GNU General Public
007 * License as published by the Free Software Foundation; either
008 * version 2 of the License, or (at your option) any later version.
009 *
010 * This program is distributed in the hope that it will be useful,
011 * but WITHOUT ANY WARRANTY; without even the implied warranty of
012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
013 * GNU General Public License for more details.
014 */
015
016 package org.qedeq.gui.se.tree;
017
018 import java.awt.Component;
019 import java.awt.Graphics;
020
021 import javax.swing.Icon;
022 import javax.swing.ImageIcon;
023 import javax.swing.JTree;
024 import javax.swing.tree.DefaultMutableTreeNode;
025 import javax.swing.tree.DefaultTreeCellRenderer;
026
027 import org.qedeq.base.trace.Trace;
028 import org.qedeq.gui.se.util.DecoratedIcon;
029 import org.qedeq.gui.se.util.GuiHelper;
030 import org.qedeq.kernel.bo.common.QedeqBo;
031 import org.qedeq.kernel.se.common.Plugin;
032 import org.qedeq.kernel.se.state.AbstractState;
033 import org.qedeq.kernel.se.state.DependencyState;
034 import org.qedeq.kernel.se.state.FormallyProvedState;
035 import org.qedeq.kernel.se.state.LoadingImportsState;
036 import org.qedeq.kernel.se.state.LoadingState;
037 import org.qedeq.kernel.se.state.WellFormedState;
038
039 import furbelow.AnimatedIcon;
040
041 /**
042 * Renderer for a JTree.
043 *
044 * @author Michael Meyling
045 */
046 public final class QedeqTreeCellRenderer extends DefaultTreeCellRenderer {
047
048 /** This class. */
049 private static final Class CLASS = QedeqTreeCellRenderer.class;
050
051 /** Status icon. */
052 private static ImageIcon startIcon
053 = createImageIcon("module_start.gif");
054
055 /** Status icon. */
056 private static ImageIcon loadedIcon
057 = createImageIcon("module_loaded.gif");
058
059 /** Status icon. */
060 private static ImageIcon loadedImportsIcon
061 = createImageIcon("module_loaded_required.gif"); // LATER 20130318 m31: other icon?
062
063 /** Status icon. */
064 private static ImageIcon loadedRequiredIcon
065 = createImageIcon("module_loaded_required.gif");
066
067 /** Status icon. */
068 private static ImageIcon wellFormedIcon
069 = createImageIcon("module_checked.gif");
070
071 /** Status icon. */
072 private static ImageIcon formallyProvedIcon
073 = createImageIcon("module_checked2.gif");
074
075 /** Status icon. */
076 private static AnimatedIcon startNextIcon
077 = new AnimatedIcon(createImageIcon("next_module_start.gif"));
078
079 /** Status icon. */
080 private static AnimatedIcon startFlashIcon
081 = new AnimatedIcon(createImageIcon("flash_module_start.gif"));
082
083 /** Status icon. */
084 private static AnimatedIcon loadedNextIcon
085 = new AnimatedIcon(createImageIcon("next_module_loaded.gif"));
086
087 /** Status icon. */
088 private static AnimatedIcon loadedFlashIcon
089 = new AnimatedIcon(createImageIcon("flash_module_loaded.gif"));
090
091 /** Status icon. */
092 private static AnimatedIcon loadedImportsNextIcon // LATER 20130318 m31: other icon?
093 = new AnimatedIcon(createImageIcon("next_module_loaded_required.gif"));
094
095 /** Status icon. */
096 private static AnimatedIcon loadedImportsFlashIcon // LATER 20130318 m31: other icon?
097 = new AnimatedIcon(createImageIcon("flash_module_loaded_required.gif"));
098
099 /** Status icon. */
100 private static AnimatedIcon loadedRequiredNextIcon
101 = new AnimatedIcon(createImageIcon("next_module_loaded_required.gif"));
102
103 /** Status icon. */
104 private static AnimatedIcon loadedRequiredFlashIcon
105 = new AnimatedIcon(createImageIcon("flash_module_loaded_required.gif"));
106
107 /** Status icon. */
108 private static AnimatedIcon wellFormedNextIcon
109 = new AnimatedIcon(createImageIcon("next_module_checked.gif"));
110
111 /** Status icon. */
112 private static AnimatedIcon wellFormedFlashIcon
113 = new AnimatedIcon(createImageIcon("flash_module_checked.gif"));
114
115 /** Status icon. */
116 private static AnimatedIcon formallyProvedFlashIcon
117 = new AnimatedIcon(createImageIcon("flash_module_checked2.gif"));
118
119 /** Status icon. */
120 private static ImageIcon basicErrorOverlayIcon
121 = GuiHelper.readImageIcon("eclipse/error_co_dl.gif");
122
123 /** Status icon. */
124 private static ImageIcon pluginErrorOverlayIcon
125 = GuiHelper.readImageIcon("eclipse/error_co_ur.gif");
126
127 /** Status icon. */
128 private static ImageIcon pluginWarningOverlayIcon
129 = GuiHelper.readImageIcon("eclipse/warning_co_ur.gif");
130
131 static ImageIcon createImageIcon(final String name) {
132 return GuiHelper.readImageIcon("qedeq/16x16/" + name);
133
134 }
135
136 // LATER mime 20080502: do we want to leave it for our alternative "paint" or do we delete it?
137 //
138 // /** Color to use for the foreground for selected nodes. */
139 // private Color textSelectionColor = UIManager.getColor("Tree.selectionForeground");
140 //
141 // /** Color to use for the foreground for non-selected nodes. */
142 // private Color textNonSelectionColor = UIManager.getColor("Tree.textForeground");
143 //
144 // /** Color to use for the background when a node is selected. */
145 // private Color backgroundSelectionColor = UIManager.getColor("Tree.selectionBackground");
146 //
147 // /** Color to use for the background when the node isn't selected. */
148 // private Color backgroundNonSelectionColor = UIManager.getColor("Tree.textBackground");
149
150 public QedeqTreeCellRenderer() {
151 super();
152 }
153
154 public synchronized Component getTreeCellRendererComponent(final JTree tree,
155 final Object value, final boolean isSelected,
156 final boolean expanded, final boolean leaf, final int row,
157 final boolean hasFocus) {
158
159 final String method = "getTreeCellRendererComponent";
160 Trace.param(CLASS, this, method, row + " is selected", isSelected);
161 Trace.param(CLASS, this, method, row + " is expanded", expanded);
162 Trace.param(CLASS, this, method, row + " hasFocus", hasFocus);
163 Trace.param(CLASS, this, method, row + " leaf", leaf);
164 Trace.param(CLASS, this, method, row + " maxSelectionRow", tree.getMaxSelectionRow());
165 Trace.param(CLASS, this, method, row + " selectionCount", tree.getSelectionCount());
166 Trace.param(CLASS, this, method, row + " rowCount", tree.getRowCount());
167 Trace.param(CLASS, this, method, row + " tree path", tree.getPathForRow(row));
168
169 ModuleElement unit;
170 QedeqBo prop;
171 /* m31 20080502: Debugging code
172 TreeModel model = tree.getModel();
173 BasicTreeUI ui = (BasicTreeUI) tree.getUI();
174 VariableHeightLayoutCache vhlc = null;
175 Vector visibleNodes = null;
176 try {
177 vhlc = (VariableHeightLayoutCache) IoUtility.getFieldContentSuper(ui, "treeState");
178 visibleNodes = (Vector) IoUtility.getFieldContentSuper(vhlc, "visibleNodes");
179 System.out.println("vectorSize = " + visibleNodes.size());
180 for (int i = 0; i < visibleNodes.size(); i++) {
181 System.out.println(" " + visibleNodes.get(i));
182 }
183 } catch (Throwable e) {
184 e.printStackTrace();
185 }
186 */
187 super.getTreeCellRendererComponent(tree, value, isSelected, expanded,
188 leaf, row, hasFocus);
189 if (value instanceof DefaultMutableTreeNode) {
190 if (((DefaultMutableTreeNode) value).getUserObject()
191 instanceof ModuleElement) {
192 unit = (ModuleElement) ((DefaultMutableTreeNode) value).getUserObject();
193 setText(unit.getName());
194 } else {
195 prop = (QedeqBo) ((DefaultMutableTreeNode) value).getUserObject();
196 final String text = prop.getName();
197 setText(text);
198 final AbstractState currentState = prop.getCurrentState();
199 final Plugin plugin = prop.getCurrentlyRunningPlugin();
200 if (prop.isLoaded()) {
201 setToolTipText(prop.getUrl().toString());
202 } else {
203 setToolTipText(GuiHelper.getToolTipText(prop.getStateDescription()));
204 }
205 // setIcon(null);
206 // System.out.println(prop.getStateDescription());
207 // System.out.println("current state=" + currentState + " " + currentState.getClass());
208 // System.out.println("lasz suc.stat=" + succesfullState + " " + succesfullState.getClass());
209 // System.out.println();
210 if (currentState == LoadingState.STATE_DELETED) {
211 setIcon(null);
212 } else if (currentState == LoadingState.STATE_UNDEFINED) {
213 if (plugin == null) {
214 setIcon(prop, startIcon);
215 } else {
216 setIcon(startFlashIcon);
217 }
218 } else if (currentState == LoadingState.STATE_LOADED) {
219 if (plugin == null) {
220 setIcon(prop, loadedIcon);
221 } else {
222 setIcon(loadedFlashIcon);
223 }
224 } else if (currentState instanceof LoadingState) {
225 if (currentState.isFailure()) {
226 if (plugin == null) {
227 setIcon(prop, startIcon);
228 } else {
229 setIcon(startFlashIcon);
230 }
231 } else {
232 setIcon(startNextIcon);
233 }
234 } else if (currentState == LoadingImportsState.STATE_LOADED_IMPORTED_MODULES) {
235 if (plugin == null) {
236 setIcon(prop, loadedImportsIcon);
237 } else {
238 setIcon(loadedImportsFlashIcon);
239 }
240 } else if (currentState instanceof LoadingImportsState) {
241 if (currentState.isFailure()) {
242 if (plugin == null) {
243 setIcon(prop, loadedImportsIcon);
244 } else {
245 setIcon(loadedImportsFlashIcon);
246 }
247 } else {
248 setIcon(loadedImportsNextIcon);
249 }
250 } else if (currentState == DependencyState.STATE_LOADED_REQUIRED_MODULES) {
251 if (plugin == null) {
252 setIcon(prop, loadedRequiredIcon);
253 } else {
254 setIcon(loadedRequiredFlashIcon);
255 }
256 } else if (currentState instanceof DependencyState) {
257 if (currentState.isFailure()) {
258 if (plugin == null) {
259 setIcon(prop, loadedIcon);
260 } else {
261 setIcon(loadedFlashIcon);
262 }
263 } else {
264 setIcon(loadedNextIcon);
265 }
266 } else if (currentState == WellFormedState.STATE_CHECKED) {
267 if (plugin == null) {
268 setIcon(prop, wellFormedIcon);
269 } else {
270 setIcon(wellFormedFlashIcon);
271 }
272 } else if (currentState instanceof WellFormedState) {
273 if (currentState.isFailure()) {
274 if (plugin == null) {
275 setIcon(prop, loadedRequiredIcon);
276 } else {
277 setIcon(loadedRequiredFlashIcon);
278 }
279 } else {
280 setIcon(loadedRequiredNextIcon);
281 }
282 } else if (currentState == FormallyProvedState.STATE_CHECKED) {
283 if (plugin == null) {
284 setIcon(prop, formallyProvedIcon);
285 } else {
286 setIcon(formallyProvedFlashIcon);
287 }
288 } else if (currentState instanceof FormallyProvedState) {
289 if (currentState.isFailure()) {
290 if (plugin == null) {
291 setIcon(prop, wellFormedIcon);
292 } else {
293 setIcon(wellFormedFlashIcon);
294 }
295 } else {
296 setIcon(wellFormedNextIcon);
297 }
298 } else { // unknown loading state
299 throw new IllegalStateException("unknown module state: "
300 + currentState.getText());
301 }
302
303 }
304 }
305 // LATER m31 20080502: do we want to leave it for our alternative "paint" or do we delete it?
306 /*
307 if (isSelected) {
308 setBackground(backgroundSelectionColor);
309 setForeground(textSelectionColor);
310 } else {
311 setBackground(backgroundNonSelectionColor);
312 setForeground(textNonSelectionColor);
313 }
314 */
315 // mime 20080430: comment out, debug code!
316 // Trace.trace(CLASS, this, method, "-- global info");
317 // final DefaultMutableTreeNode node = (DefaultMutableTreeNode) tree.getModel().getRoot();
318 // Trace.param(CLASS, this, method, "-- child", node.getChildCount());
319 // for (int i = 0; i < node.getChildCount(); i++) {
320 // Trace.param(CLASS, this, method, "--- node" + i, node.getChildAt(i));
321 // Trace.param(CLASS, this, method, "--- child count" + i,
322 // node.getChildAt(i).getChildCount());
323 // }
324
325 return this;
326 }
327
328 // LATER m31 20080502: do we want to rename it back to "paint" or do we delete it?
329 /*
330 * paint is subclassed to draw the background correctly. JLabel
331 * currently does not allow backgrounds other than white, and it
332 * will also fill behind the icon. Something that isn't desirable.
333 */
334 public void paintttttt(final Graphics g) {
335 final String method = "paint";
336 Trace.param(CLASS, this, method, "label", getText());
337 Icon currentI = getIcon();
338 if (currentI != null && getText() != null) {
339 int offset = (currentI.getIconWidth() + getIconTextGap());
340 g.setColor(getBackground());
341 if (getComponentOrientation().isLeftToRight()) {
342 g.fillRect(offset, 0, getWidth() - 1 - offset, getHeight() - 1);
343 } else {
344 g.fillRect(0, 0, getWidth() - 1 - offset, getHeight() - 1);
345 }
346 } else {
347 g.fillRect(0, 0, getWidth() - 1, getHeight() - 1);
348 }
349 super.paint(g);
350 }
351
352 private void setIcon(final QedeqBo qedeq, final ImageIcon icon) {
353 final DecoratedIcon ic = new DecoratedIcon(icon);
354 if (qedeq.hasBasicFailures()) {
355 ic.decorate(basicErrorOverlayIcon);
356 }
357 // FIXME 20130220 m31: we have to separate basic failures from plugin errors, here a method is missing
358 // if (qedeq.hasErrors()) {
359 // ic.decorate(pluginErrorOverlayIcon);
360 // }
361 if (qedeq.hasWarnings()) {
362 ic.decorate(pluginWarningOverlayIcon);
363 }
364 setIcon(ic);
365 }
366
367
368 }
|