20 package net.sf.gridarta.gui.dialog.shortcuts;
22 import java.awt.Color;
23 import java.awt.Component;
24 import java.awt.Container;
25 import java.awt.Dimension;
26 import java.awt.GridBagConstraints;
27 import java.awt.GridBagLayout;
28 import java.awt.Insets;
29 import java.util.regex.Pattern;
30 import javax.swing.Action;
31 import javax.swing.Icon;
32 import javax.swing.JButton;
33 import javax.swing.JComponent;
34 import javax.swing.JDialog;
35 import javax.swing.JOptionPane;
36 import javax.swing.JPanel;
37 import javax.swing.JScrollPane;
38 import javax.swing.JTextArea;
39 import javax.swing.JTree;
40 import javax.swing.JViewport;
41 import javax.swing.ScrollPaneConstants;
42 import javax.swing.ToolTipManager;
43 import javax.swing.WindowConstants;
44 import javax.swing.border.LineBorder;
45 import javax.swing.border.TitledBorder;
46 import javax.swing.event.TreeSelectionListener;
47 import javax.swing.tree.DefaultMutableTreeNode;
48 import javax.swing.tree.DefaultTreeCellRenderer;
49 import javax.swing.tree.DefaultTreeModel;
50 import javax.swing.tree.MutableTreeNode;
51 import javax.swing.tree.TreeCellRenderer;
52 import javax.swing.tree.TreeNode;
53 import javax.swing.tree.TreeSelectionModel;
58 import net.
sf.japi.swing.action.ActionBuilder;
59 import net.
sf.japi.swing.action.ActionBuilderFactory;
60 import net.
sf.japi.swing.action.ActionMethod;
61 import net.
sf.japi.swing.action.IconManager;
62 import org.jetbrains.annotations.NotNull;
63 import org.jetbrains.annotations.Nullable;
94 private static final ActionBuilder
ACTION_BUILDER = ActionBuilderFactory.getInstance().getActionBuilder(
"net.sf.gridarta");
149 public String convertValueToText(
final Object value,
final boolean selected,
final boolean expanded,
final boolean leaf,
final int row,
final boolean hasFocus) {
151 if (action !=
null) {
155 return super.convertValueToText(value, selected, expanded, leaf, row, hasFocus);
188 final JButton defaultsButton =
new JButton(
ACTION_BUILDER.createAction(
false,
"shortcutsDefaults",
this));
189 setOptions(
new Object[] {
okButton, defaultsButton });
194 dialog.setResizable(
true);
195 dialog.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE);
199 dialog.setMinimumSize(
new Dimension(400, 300));
200 dialog.setPreferredSize(
new Dimension(800, 600));
208 public void showDialog(@NotNull
final Component parentComponent) {
209 dialog.setLocationRelativeTo(parentComponent);
225 actionsTree.setModel(
new DefaultTreeModel(top,
false));
227 actionsTree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);
229 actionsTree.addTreeSelectionListener(treeSelectionListener);
233 final TreeCellRenderer treeCellRenderer =
new DefaultTreeCellRenderer() {
247 public Component getTreeCellRendererComponent(
final JTree tree,
final Object value,
final boolean sel,
final boolean expanded,
final boolean leaf,
final int row,
final boolean hasFocus) {
250 if (action ==
null) {
254 icon = tmpIcon ==
null ? emptyIcon : tmpIcon;
260 return super.getTreeCellRendererComponent(tree, value, sel, expanded, leaf, row, hasFocus);
264 public Icon getLeafIcon() {
271 ToolTipManager.sharedInstance().registerComponent(
actionsTree);
273 final GridBagConstraints gbc =
new GridBagConstraints();
274 gbc.insets =
new Insets(2, 2, 2, 2);
276 final JScrollPane actionsScrollPane =
new JScrollPane();
278 actionsScrollPane.setBackground(
actionsTree.getBackground());
280 actionsScrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
281 actionsScrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
282 actionsScrollPane.getViewport().setScrollMode(JViewport.SIMPLE_SCROLL_MODE);
283 final JComponent actionsPanel =
new JPanel(
new GridBagLayout());
287 gbc.fill = GridBagConstraints.BOTH;
290 actionsPanel.add(actionsScrollPane, gbc);
307 final Container actionDescriptionPanel =
new JPanel(
new GridBagLayout());
310 gbc.fill = GridBagConstraints.HORIZONTAL;
315 gbc.fill = GridBagConstraints.BOTH;
319 final Container actionShortcutPanel =
new JPanel(
new GridBagLayout());
322 gbc.fill = GridBagConstraints.HORIZONTAL;
329 final Component addShortcutButton =
new JButton(
aSetShortcut);
330 final Component removeShortcutButton =
new JButton(
aUnsetShortcut);
331 final Container actionButtonsPanel =
new JPanel();
332 actionButtonsPanel.setLayout(
new GridBagLayout());
335 gbc.fill = GridBagConstraints.HORIZONTAL;
338 actionButtonsPanel.add(addShortcutButton, gbc);
340 actionButtonsPanel.add(removeShortcutButton, gbc);
342 final JComponent selectedActionPanel =
new JPanel();
343 selectedActionPanel.setLayout(
new GridBagLayout());
347 gbc.fill = GridBagConstraints.BOTH;
350 selectedActionPanel.add(actionDescriptionPanel, gbc);
351 gbc.fill = GridBagConstraints.HORIZONTAL;
354 selectedActionPanel.add(actionShortcutPanel, gbc);
356 selectedActionPanel.add(actionButtonsPanel, gbc);
358 final JPanel panel =
new JPanel(
new GridBagLayout());
361 gbc.fill = GridBagConstraints.BOTH;
364 panel.add(actionsPanel, gbc);
367 panel.add(selectedActionPanel, gbc);
394 public void setValue(@Nullable
final Object newValue) {
395 super.setValue(newValue);
396 if (newValue != UNINITIALIZED_VALUE) {
405 private void createNodes(@NotNull
final DefaultMutableTreeNode root) {
409 addNode(root, category, action);
420 private static void addNode(@NotNull
final DefaultMutableTreeNode root, @NotNull
final CharSequence category, @NotNull
final Action action) {
422 final MutableTreeNode treeNode =
new DefaultMutableTreeNode(action,
false);
433 private static DefaultMutableTreeNode
getOrCreateNodeForCategory(@NotNull
final DefaultMutableTreeNode root, @NotNull
final CharSequence category) {
434 DefaultMutableTreeNode node = root;
448 private static DefaultMutableTreeNode
getOrCreateChildNode(@NotNull
final MutableTreeNode root, @NotNull
final String subCategory) {
449 final int childCount = root.getChildCount();
450 for (
int i = 0; i < childCount; i++) {
451 final TreeNode treeNode = root.getChildAt(i);
452 final String nodeTitle =
getTitle(treeNode);
453 if (nodeTitle !=
null && nodeTitle.equals(
CATEGORY_PREFIX + subCategory)) {
454 assert treeNode instanceof DefaultMutableTreeNode;
455 return (DefaultMutableTreeNode) treeNode;
459 final DefaultMutableTreeNode treeNode =
new DefaultMutableTreeNode(subCategory);
469 private static void insertChildNode(@NotNull
final MutableTreeNode branchNode, @NotNull
final MutableTreeNode childNode) {
479 private static int getInsertionIndex(@NotNull
final TreeNode parentNode, @NotNull
final TreeNode childNode) {
480 final String childTitle =
getTitle(childNode);
481 if (childTitle ==
null) {
482 throw new IllegalArgumentException(
"invalid child node: " + childNode);
485 final int childCount = parentNode.getChildCount();
486 for (
int i = 0; i < childCount; i++) {
487 final TreeNode treeNode = parentNode.getChildAt(i);
488 final String nodeTitle =
getTitle(treeNode);
489 if (nodeTitle !=
null && nodeTitle.compareToIgnoreCase(childTitle) > 0) {
503 private static Action
getAction(@Nullable
final Object node) {
504 if (!(node instanceof DefaultMutableTreeNode)) {
508 final DefaultMutableTreeNode defaultMutableTreeNode = (DefaultMutableTreeNode) node;
509 final Object userObject = defaultMutableTreeNode.getUserObject();
510 if (!(userObject instanceof Action)) {
514 return (Action) userObject;
523 private static String
getTitle(@NotNull
final TreeNode node) {
524 if (!(node instanceof DefaultMutableTreeNode)) {
528 final DefaultMutableTreeNode defaultMutableTreeNode = (DefaultMutableTreeNode) node;
529 final Object userObject = defaultMutableTreeNode.getUserObject();
530 if (userObject ==
null) {
534 if (userObject instanceof String) {
538 if (userObject instanceof Action) {
584 if (action ==
null) {
602 if (action !=
null) {