1 package siouxsie.desktop.option.impl;
2
3 import java.awt.BorderLayout;
4 import java.awt.CardLayout;
5 import java.awt.Component;
6 import java.awt.event.MouseAdapter;
7 import java.awt.event.MouseEvent;
8 import java.util.ArrayList;
9 import java.util.Collection;
10 import java.util.HashMap;
11 import java.util.List;
12 import java.util.Map;
13
14 import javax.swing.JComponent;
15 import javax.swing.JLabel;
16 import javax.swing.JPanel;
17 import javax.swing.JScrollPane;
18 import javax.swing.JTree;
19 import javax.swing.tree.DefaultMutableTreeNode;
20 import javax.swing.tree.DefaultTreeCellRenderer;
21 import javax.swing.tree.TreePath;
22
23 import org.apache.commons.logging.Log;
24 import org.apache.commons.logging.LogFactory;
25
26 import siouxsie.desktop.option.CategoryDescription;
27 import siouxsie.desktop.option.IOptionPane;
28 import siouxsie.desktop.option.IOptionPaneInitializer;
29 import siouxsie.desktop.option.IPreferencesRenderer;
30 import siouxsie.desktop.option.OptionPaneDescription;
31
32 /**
33 * JTree menu based preferences renderer.
34 * @author Arnaud Cogoluegnes
35 * @version $Id$
36 */
37 public class PreferencesRenderer implements IPreferencesRenderer {
38
39 private List<OptionPaneDescription> optionPaneDescriptions;
40
41 private List<CategoryDescription> categoryDescriptions;
42
43 private IOptionPaneInitializer initializerService;
44
45 private Collection<IOptionPane> optionPanes = new ArrayList<IOptionPane>();
46
47 private static final Log LOG = LogFactory.getLog(PreferencesRenderer.class);
48
49 private JPanel mainPanel;
50
51 private JTree tree;
52
53
54
55
56
57 public JComponent getComponent() {
58 return mainPanel;
59 }
60
61
62
63
64
65 public void save() throws Exception {
66
67 for(IOptionPane pane : optionPanes) {
68 pane.save();
69 }
70 }
71
72
73
74
75
76 public void cancel() throws Exception {
77
78
79 }
80
81 public void init() {
82 DefaultMutableTreeNode root = new DefaultMutableTreeNode();
83 Map<String, DefaultMutableTreeNode> catIdToCat = new HashMap<String, DefaultMutableTreeNode>();
84 for(CategoryDescription cat : categoryDescriptions) {
85 DefaultMutableTreeNode node = new DefaultMutableTreeNode(cat);
86 catIdToCat.put(cat.getId(), node);
87 root.add(node);
88 }
89
90
91 CategoryDescription defaultCategory = new CategoryDescription();
92 defaultCategory.setId("siouxsie_default_option_category");
93 defaultCategory.setName("Default");
94 DefaultMutableTreeNode defaultCategoryNode = new DefaultMutableTreeNode(defaultCategory);
95
96
97 final JPanel panel = new JPanel();
98 final CardLayout cardLayout = new CardLayout();
99 panel.setLayout(cardLayout);
100
101
102 panel.add(new JPanel(),"");
103
104 for(OptionPaneDescription desc : optionPaneDescriptions) {
105
106 IOptionPane optionPane;
107 try {
108 optionPane = desc.getOptionPane() != null ? desc.getOptionPane() : (IOptionPane) desc.getClass().newInstance();
109 initializerService.initialize(optionPane);
110 } catch (InstantiationException e) {
111 LOG.error("could not create option pane",e);
112 continue;
113 } catch (IllegalAccessException e) {
114 LOG.error("could not create option pane",e);
115 continue;
116 }
117
118 optionPane.init();
119
120 DefaultMutableTreeNode node = new DefaultMutableTreeNode();
121 node.setUserObject(optionPane);
122 DefaultMutableTreeNode cat = catIdToCat.get(desc.getCategoryId());
123 if(cat == null) {
124 LOG.warn("could not find preferences category "+desc.getCategoryId()+" for option pane "+optionPane.getName());
125 cat = defaultCategoryNode;
126 if(root.getIndex(cat) == -1) {
127 root.add(cat);
128 }
129 desc.setCategoryId(defaultCategory.getId());
130 }
131 cat.add(node);
132
133 panel.add(optionPane.getComponent(),desc.getCategoryId()+"."+optionPane.getName());
134 optionPanes.add(optionPane);
135
136 }
137
138 tree = new JTree(root);
139 tree.setRootVisible(false);
140 tree.setShowsRootHandles(true);
141
142 tree.setCellRenderer(new DefaultTreeCellRenderer() {
143 @Override
144 public Component getTreeCellRendererComponent(JTree tree, Object value, boolean sel, boolean expanded, boolean leaf, int row, boolean hasFocus) {
145 JLabel label = (JLabel) super.getTreeCellRendererComponent(tree, value, sel, expanded, leaf, row, hasFocus);
146 DefaultMutableTreeNode node = (DefaultMutableTreeNode) value;
147 if(node.getUserObject() instanceof IOptionPane) {
148 label.setText(((IOptionPane) node.getUserObject()).getName());
149 }
150 return label;
151 }
152 });
153
154 mainPanel = new JPanel(new BorderLayout());
155 mainPanel.add(new JScrollPane(tree),BorderLayout.WEST);
156 mainPanel.add(panel,BorderLayout.CENTER);
157
158 tree.addMouseListener(new MouseAdapter() {
159 public void mousePressed(MouseEvent e) {
160 int selRow = tree.getRowForLocation(e.getX(), e.getY());
161 TreePath selPath = tree.getPathForLocation(e.getX(), e.getY());
162 if(selRow != -1) {
163 DefaultMutableTreeNode node = (DefaultMutableTreeNode) selPath.getLastPathComponent();
164 if(node.getUserObject() instanceof IOptionPane) {
165 CategoryDescription cat = (CategoryDescription)((DefaultMutableTreeNode)node.getParent()).getUserObject();
166 IOptionPane pane = (IOptionPane) node.getUserObject();
167
168 cardLayout.show(panel, cat.getId()+"."+pane.getName());
169
170 }
171 }
172 }
173 });
174
175 }
176
177 public List<CategoryDescription> getCategoryDescriptions() {
178 return categoryDescriptions;
179 }
180
181 public void setCategoryDescriptions(
182 List<CategoryDescription> categoryDescriptions) {
183 this.categoryDescriptions = categoryDescriptions;
184 }
185
186 public IOptionPaneInitializer getInitializerService() {
187 return initializerService;
188 }
189
190 public void setInitializerService(IOptionPaneInitializer initializerService) {
191 this.initializerService = initializerService;
192 }
193
194 public List<OptionPaneDescription> getOptionPaneDescriptions() {
195 return optionPaneDescriptions;
196 }
197
198 public void setOptionPaneDescriptions(
199 List<OptionPaneDescription> optionPaneDescriptions) {
200 this.optionPaneDescriptions = optionPaneDescriptions;
201 }
202
203 /**
204 * For test purpose only.
205 * @return
206 */
207 protected JTree getTree() {
208 return tree;
209 }
210
211 }