source: josm/trunk/src/org/openstreetmap/josm/gui/IconToggleButton.java@ 11279

Last change on this file since 11279 was 10384, checked in by Don-vip, 8 years ago

fix #12954 - IllegalComponentStateException with detached dialogs

  • Property svn:eol-style set to native
File size: 5.4 KB
Line 
1// License: GPL. For details, see LICENSE file.
2package org.openstreetmap.josm.gui;
3
4import java.beans.PropertyChangeEvent;
5import java.beans.PropertyChangeListener;
6
7import javax.swing.Action;
8import javax.swing.Icon;
9import javax.swing.JToggleButton;
10
11import org.openstreetmap.josm.Main;
12import org.openstreetmap.josm.actions.ExpertToggleAction;
13import org.openstreetmap.josm.actions.ExpertToggleAction.ExpertModeChangeListener;
14import org.openstreetmap.josm.tools.CheckParameterUtil;
15import org.openstreetmap.josm.tools.Destroyable;
16
17/**
18 * Just a toggle button, with smaller border and icon only to display in
19 * MapFrame toolbars.
20 * Also provides methods for storing hidden state in preferences
21 * @author imi, akks
22 */
23public class IconToggleButton extends JToggleButton implements HideableButton, PropertyChangeListener, Destroyable, ExpertModeChangeListener {
24
25 private transient ShowHideButtonListener listener;
26 private boolean hideIfDisabled;
27 private boolean isExpert;
28
29 /**
30 * Construct the toggle button with the given action.
31 * @param action associated action
32 */
33 public IconToggleButton(Action action) {
34 this(action, false);
35 }
36
37 /**
38 * Construct the toggle button with the given action.
39 * @param action associated action
40 * @param isExpert {@code true} if it's reserved to expert mode
41 */
42 public IconToggleButton(Action action, boolean isExpert) {
43 super(action);
44 CheckParameterUtil.ensureParameterNotNull(action, "action");
45 this.isExpert = isExpert;
46 setText(null);
47
48 Object o = action.getValue(Action.SHORT_DESCRIPTION);
49 if (o != null) {
50 setToolTipText(o.toString());
51 }
52
53 action.addPropertyChangeListener(this);
54
55 ExpertToggleAction.addExpertModeChangeListener(this);
56 }
57
58 @Override
59 public void propertyChange(PropertyChangeEvent evt) {
60 if ("active".equals(evt.getPropertyName())) {
61 setSelected((Boolean) evt.getNewValue());
62 requestFocusInWindow();
63 } else if ("selected".equals(evt.getPropertyName())) {
64 setSelected((Boolean) evt.getNewValue());
65 }
66 }
67
68 @Override
69 public void destroy() {
70 Action action = getAction();
71 if (action instanceof Destroyable) {
72 ((Destroyable) action).destroy();
73 }
74 if (action != null) {
75 action.removePropertyChangeListener(this);
76 }
77 }
78
79 String getPreferenceKey() {
80 String s = (String) getSafeActionValue("toolbar");
81 if (s == null) {
82 if (getAction() != null) {
83 s = getAction().getClass().getName();
84 }
85 }
86 return "sidetoolbar.hidden."+s;
87
88 }
89
90 @Override
91 public void expertChanged(boolean isExpert) {
92 applyButtonHiddenPreferences();
93 }
94
95 @Override
96 public void applyButtonHiddenPreferences() {
97 boolean alwaysHideDisabled = Main.pref.getBoolean("sidetoolbar.hideDisabledButtons", false);
98 if (!isEnabled() && (hideIfDisabled || alwaysHideDisabled)) {
99 setVisible(false); // hide because of disabled button
100 } else {
101 boolean hiddenFlag = false;
102 String hiddenFlagStr = Main.pref.get(getPreferenceKey(), null);
103 if (hiddenFlagStr == null) {
104 if (isExpert && !ExpertToggleAction.isExpert()) {
105 hiddenFlag = true;
106 }
107 } else {
108 hiddenFlag = Boolean.parseBoolean(hiddenFlagStr);
109 }
110 setVisible(!hiddenFlag); // show or hide, do what preferences say
111 }
112 }
113
114 @Override
115 public void setButtonHidden(boolean b) {
116 setVisible(!b);
117 if (listener != null) { // if someone wants to know about changes of visibility
118 if (!b) listener.buttonShown(); else listener.buttonHidden();
119 }
120 if ((b && isExpert && !ExpertToggleAction.isExpert()) ||
121 (!b && isExpert && ExpertToggleAction.isExpert())) {
122 Main.pref.put(getPreferenceKey(), null);
123 } else {
124 Main.pref.put(getPreferenceKey(), b);
125 }
126 }
127
128 /**
129 * This function should be called for plugins that want to enable auto-hiding
130 * custom buttons when they are disabled (because of incorrect layer, for example)
131 * @param b hide if disabled
132 */
133 public void setAutoHideDisabledButton(boolean b) {
134 hideIfDisabled = b;
135 if (b && !isEnabled()) {
136 setVisible(false);
137 }
138 }
139
140 @Override
141 public void showButton() {
142 setButtonHidden(false);
143 }
144
145 @Override
146 public void hideButton() {
147 setButtonHidden(true);
148 }
149
150 @Override
151 public String getActionName() {
152 return (String) getSafeActionValue(Action.NAME);
153 }
154
155 @Override
156 public Icon getIcon() {
157 Object o = getSafeActionValue(Action.LARGE_ICON_KEY);
158 if (o == null)
159 o = getSafeActionValue(Action.SMALL_ICON);
160 return (Icon) o;
161 }
162
163 @Override
164 public boolean isButtonVisible() {
165 return isVisible();
166 }
167
168 @Override
169 public void setShowHideButtonListener(ShowHideButtonListener l) {
170 listener = l;
171 }
172
173 protected final Object getSafeActionValue(String key) {
174 // Mac OS X Aqua L&F can call accessors from constructor, so getAction() can be null in those cases
175 return getAction() != null ? getAction().getValue(key) : null;
176 }
177}
Note: See TracBrowser for help on using the repository browser.