1 7 8 package org.gjt.jclasslib.browser.config.classpath; 9 10 import org.gjt.jclasslib.browser.BrowserMDIFrame; 11 import org.gjt.jclasslib.util.GUIHelper; 12 import org.gjt.jclasslib.util.ProgressDialog; 13 14 import javax.swing.*; 15 import javax.swing.event.TreeSelectionEvent ; 16 import javax.swing.event.TreeSelectionListener ; 17 import javax.swing.tree.DefaultTreeModel ; 18 import javax.swing.tree.TreePath ; 19 import java.awt.*; 20 import java.awt.event.*; 21 22 29 public class ClasspathBrowser extends JDialog 30 implements ActionListener, ClasspathChangeListener 31 { 32 33 private static final int DIALOG_WIDTH = 450; 34 private static final int DIALOG_HEIGHT = 450; 35 36 private BrowserMDIFrame frame; 37 private ClasspathComponent classpathComponent; 38 39 private JLabel lblTitle; 40 private JTree tree; 41 private JScrollPane scpTree; 42 private JButton btnSetup; 43 private JButton btnSync; 44 private JButton btnOk; 45 private JButton btnCancel; 46 47 private ProgressDialog progressDialog; 48 private boolean resetOnNextMerge; 49 private boolean needsMerge; 50 51 private String selectedClassName; 52 53 60 public ClasspathBrowser(BrowserMDIFrame frame, ClasspathComponent classpathComponent, String title, boolean setupVisible) { 61 super(frame); 62 this.frame = frame; 63 64 setClasspathComponent(classpathComponent); 65 setupControls(title, setupVisible); 66 setupComponent(); 67 setupEventHandlers(); 68 } 69 70 public void actionPerformed(ActionEvent event) { 71 Object source = event.getSource(); 72 if (source == btnCancel) { 73 doCancel(); 74 } else if (source == btnOk) { 75 doOk(); 76 } else if (source == btnSetup) { 77 doSetup(); 78 } else if (source == btnSync) { 79 doSync(true); 80 } 81 82 } 83 84 public void classpathChanged(ClasspathChangeEvent event) { 85 needsMerge = true; 86 if (event.isRemoval()) { 87 resetOnNextMerge = true; 88 } 89 } 90 91 public void setVisible(boolean visible) { 92 if (visible) { 93 selectedClassName = null; 94 } 95 super.setVisible(visible); 96 } 97 98 102 public String getSelectedClassName() { 103 return selectedClassName; 104 } 105 106 111 public void setClasspathComponent(ClasspathComponent classpathComponent) { 112 if (this.classpathComponent != null) { 113 this.classpathComponent.removeClasspathChangeListener(this); 114 } 115 this.classpathComponent = classpathComponent; 116 if (classpathComponent != null) { 117 classpathComponent.addClasspathChangeListener(this); 118 } 119 resetOnNextMerge = true; 120 needsMerge = true; 121 clear(); 122 } 123 124 128 public void clear() { 129 if (tree != null) { 130 tree.setModel(new DefaultTreeModel (new ClassTreeNode())); 131 } 132 } 133 134 private void setupControls(String title, boolean setupVisible) { 135 136 lblTitle = new JLabel(title); 137 tree = new JTree(new ClassTreeNode()); 138 tree.setRootVisible(false); 139 tree.setShowsRootHandles(true); 140 tree.putClientProperty("JTree.lineStyle", "Angled"); 141 scpTree = new JScrollPane(tree); 142 143 btnSetup = new JButton("Setup classpath"); 144 btnSetup.setVisible(setupVisible); 145 btnSync = new JButton("Synchronize"); 146 btnOk = new JButton("Ok"); 147 btnOk.setEnabled(false); 148 btnCancel = new JButton("Cancel"); 149 btnOk.setPreferredSize(btnCancel.getPreferredSize()); 150 151 progressDialog = new ProgressDialog(this, null, "Scanning classpath ..."); 152 153 } 154 155 private void setupComponent() { 156 157 Container contentPane = getContentPane(); 158 contentPane.setLayout(new GridBagLayout()); 159 GridBagConstraints gc = new GridBagConstraints(); 160 gc.gridx = 0; 161 gc.gridy = 0; 162 gc.insets = new Insets(5, 5, 0, 5); 163 gc.weightx = 1; 164 gc.anchor = GridBagConstraints.NORTHWEST; 165 contentPane.add(lblTitle, gc); 166 gc.gridy++; 167 168 gc.weighty = 1; 169 gc.insets.top = 0; 170 gc.fill = GridBagConstraints.BOTH; 171 contentPane.add(scpTree, gc); 172 gc.gridy++; 173 gc.fill = GridBagConstraints.HORIZONTAL; 174 gc.weighty = 0; 175 gc.insets.top = 3; 176 gc.insets.bottom = 5; 177 contentPane.add(createButtonBox(), gc); 178 getRootPane().setDefaultButton(btnOk); 179 180 setSize(DIALOG_WIDTH, DIALOG_HEIGHT); 181 setModal(true); 182 setTitle("Choose a class"); 183 GUIHelper.centerOnParentWindow(this, getOwner()); 184 setDefaultCloseOperation(DO_NOTHING_ON_CLOSE); 185 186 } 187 188 private Box createButtonBox() { 189 190 Box box = Box.createHorizontalBox(); 191 box.add(btnSetup); 192 box.add(btnSync); 193 box.add(Box.createHorizontalGlue()); 194 box.add(btnOk); 195 box.add(btnCancel); 196 197 return box; 198 } 199 200 private void setupEventHandlers() { 201 202 btnCancel.addActionListener(this); 203 btnOk.addActionListener(this); 204 btnSetup.addActionListener(this); 205 btnSync.addActionListener(this); 206 207 addWindowListener(new WindowAdapter() { 208 public void windowClosing(WindowEvent event) { 209 doCancel(); 210 } 211 }); 212 KeyStroke keyStroke = KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0); 213 Object key = new Object (); 214 215 JComponent contentPane = (JComponent)getContentPane(); 216 contentPane.getInputMap(JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT).put(keyStroke, key); 217 contentPane.getActionMap().put(key, new AbstractAction() { 218 public void actionPerformed(ActionEvent event) { 219 doCancel(); 220 } 221 }); 222 223 addComponentListener(new ComponentAdapter() { 224 public void componentShown(ComponentEvent event) { 225 conditionalUpdate(); 226 } 227 }); 228 229 tree.addTreeSelectionListener(new TreeSelectionListener () { 230 public void valueChanged(TreeSelectionEvent event) { 231 checkTreeSelection(); 232 } 233 }); 234 235 tree.addMouseListener(new MouseAdapter() { 236 public void mouseClicked(MouseEvent event) { 237 if (event.getClickCount() == 2 && isValidDoubleClickPath(event)) { 238 doOk(); 239 } 240 } 241 }); 242 243 } 244 245 private void conditionalUpdate() { 246 if (needsMerge) { 247 doSync(resetOnNextMerge); 248 } 249 } 250 251 private boolean isValidDoubleClickPath(MouseEvent event) { 252 253 TreePath locationPath = tree.getPathForLocation(event.getX(), event.getY()); 254 TreePath selectionPath = tree.getSelectionPath(); 255 if (selectionPath == null || locationPath == null || !selectionPath.equals(locationPath)) { 256 return false; 257 } 258 ClassTreeNode lastPathComponent = (ClassTreeNode)selectionPath.getLastPathComponent(); 259 return !lastPathComponent.isPackageNode(); 260 } 261 262 private void checkTreeSelection() { 263 264 TreePath selectionPath = tree.getSelectionPath(); 265 boolean enabled = false; 266 if (selectionPath != null) { 267 ClassTreeNode classTreeNode = (ClassTreeNode)selectionPath.getLastPathComponent(); 268 enabled = !classTreeNode.isPackageNode(); 269 } 270 btnOk.setEnabled(enabled); 271 } 272 273 private void doOk() { 274 275 StringBuffer buffer = new StringBuffer (); 276 TreePath selectionPath = tree.getSelectionPath(); 277 for (int i = 1; i < selectionPath.getPathCount(); i++) { 278 if (buffer.length() > 0) { 279 buffer.append('/'); 280 } 281 buffer.append(selectionPath.getPathComponent(i).toString()); 282 } 283 selectedClassName = buffer.toString(); 284 285 setVisible(false); 286 } 287 288 289 private void doCancel() { 290 setVisible(false); 291 } 292 293 private void doSetup() { 294 frame.getActionSetupClasspath().actionPerformed(new ActionEvent(this, 0, null)); 295 conditionalUpdate(); 296 } 297 298 private void doSync(final boolean reset) { 299 300 final DefaultTreeModel model = reset ? new DefaultTreeModel (new ClassTreeNode()) : (DefaultTreeModel )tree.getModel(); 301 Runnable mergeTask = new Runnable () { 302 public void run() { 303 if (classpathComponent != null) { 304 classpathComponent.mergeClassesIntoTree(model, reset); 305 } 306 } 307 }; 308 309 progressDialog.setRunnable(mergeTask); 310 progressDialog.setVisible(true); 311 312 if (reset) { 313 tree.setModel(model); 314 } 315 tree.expandPath(new TreePath (model.getRoot())); 316 resetOnNextMerge = false; 317 needsMerge = false; 318 } 319 320 321 } 322 | Popular Tags |