001: /*
002: * @(#)JideToggleSplitButton.java 2/18/2005
003: *
004: * Copyright 2002 - 2005 JIDE Software Inc. All rights reserved.
005: */
006: package com.jidesoft.swing;
007:
008: import javax.accessibility.Accessible;
009: import javax.accessibility.AccessibleContext;
010: import javax.accessibility.AccessibleRole;
011: import javax.accessibility.AccessibleState;
012: import javax.swing.*;
013: import java.awt.*;
014: import java.awt.event.ActionEvent;
015: import java.awt.event.InputEvent;
016: import java.awt.event.ItemEvent;
017: import java.awt.event.ItemListener;
018:
019: /**
020: * An implementation of a two-state JideButton.
021: */
022: public class JideToggleSplitButton extends JideSplitButton implements
023: Accessible {
024: /**
025: * Creates an initially unselected toggle button
026: * without setting the text or image.
027: */
028: public JideToggleSplitButton() {
029: this (null, null, false);
030: }
031:
032: /**
033: * Creates an initially unselected toggle button
034: * with the specified image but no text.
035: *
036: * @param icon the image that the button should display
037: */
038: public JideToggleSplitButton(Icon icon) {
039: this (null, icon, false);
040: }
041:
042: /**
043: * Creates a toggle button with the specified image
044: * and selection state, but no text.
045: *
046: * @param icon the image that the button should display
047: * @param selected if true, the button is initially selected;
048: * otherwise, the button is initially unselected
049: */
050: public JideToggleSplitButton(Icon icon, boolean selected) {
051: this (null, icon, selected);
052: }
053:
054: /**
055: * Creates an unselected toggle button with the specified text.
056: *
057: * @param text the string displayed on the toggle button
058: */
059: public JideToggleSplitButton(String text) {
060: this (text, null, false);
061: }
062:
063: /**
064: * Creates a toggle button with the specified text
065: * and selection state.
066: *
067: * @param text the string displayed on the toggle button
068: * @param selected if true, the button is initially selected;
069: * otherwise, the button is initially unselected
070: */
071: public JideToggleSplitButton(String text, boolean selected) {
072: this (text, null, selected);
073: }
074:
075: /**
076: * Creates a toggle button where properties are taken from the
077: * Action supplied.
078: *
079: * @since 1.3
080: */
081: public JideToggleSplitButton(Action a) {
082: this ();
083: setAction(a);
084: }
085:
086: /**
087: * Creates a toggle button that has the specified text and image,
088: * and that is initially unselected.
089: *
090: * @param text the string displayed on the button
091: * @param icon the image that the button should display
092: */
093: public JideToggleSplitButton(String text, Icon icon) {
094: this (text, icon, false);
095: }
096:
097: /**
098: * Creates a toggle button with the specified text, image, and
099: * selection state.
100: *
101: * @param text the text of the toggle button
102: * @param icon the image that the button should display
103: * @param selected if true, the button is initially selected;
104: * otherwise, the button is initially unselected
105: */
106: public JideToggleSplitButton(String text, Icon icon,
107: boolean selected) {
108: // Create the model
109: setModel(new ToggleSplitButtonModel());
110:
111: ((SplitButtonModel) model).setButtonSelected(selected);
112:
113: // initialize
114: init(text, icon);
115: }
116:
117: // *********************************************************************
118:
119: /**
120: * The ToggleButton model
121: * <p/>
122: * <strong>Warning:</strong>
123: * Serialized objects of this class will not be compatible with
124: * future Swing releases. The current serialization support is
125: * appropriate for short term storage or RMI between applications running
126: * the same version of Swing. As of 1.4, support for long term storage
127: * of all JavaBeans<sup><font size="-2">TM</font></sup>
128: * has been added to the <code>java.beans</code> package.
129: * Please see {@link java.beans.XMLEncoder}.
130: */
131: public static class ToggleSplitButtonModel extends
132: DefaultSplitButtonModel {
133:
134: /**
135: * Creates a new ToggleButton Model
136: */
137: public ToggleSplitButtonModel() {
138: }
139:
140: /**
141: * Checks if the button is selected.
142: */
143: @Override
144: public boolean isButtonSelected() {
145: // if(getGroup() != null) {
146: // return getGroup().isSelected(this);
147: // } else {
148: return (stateMask & BUTTON_SELECTED) != 0;
149: // }
150: }
151:
152: /**
153: * Sets the selected state of the button.
154: *
155: * @param b true selects the toggle button,
156: * false deselects the toggle button.
157: */
158: @Override
159: public void setButtonSelected(boolean b) {
160: ButtonGroup group = getGroup();
161: if (group != null) {
162: // use the group model instead
163: group.setSelected(this , b);
164: b = group.isSelected(this );
165: }
166:
167: if (isButtonSelected() == b) {
168: return;
169: }
170:
171: if (b) {
172: stateMask |= BUTTON_SELECTED;
173: } else {
174: stateMask &= ~BUTTON_SELECTED;
175: }
176:
177: // Send ChangeEvent
178: fireStateChanged();
179:
180: // Send ItemEvent
181: fireItemStateChanged(new ItemEvent(this ,
182: ItemEvent.ITEM_STATE_CHANGED, this , this
183: .isSelected() ? ItemEvent.SELECTED
184: : ItemEvent.DESELECTED));
185:
186: }
187:
188: /**
189: * Sets the pressed state of the toggle button.
190: */
191: @Override
192: public void setPressed(boolean b) {
193: if ((isPressed() == b) || !isEnabled()) {
194: return;
195: }
196:
197: if (b == false && isArmed()) {
198: setButtonSelected(!this .isButtonSelected());
199: }
200:
201: if (b) {
202: stateMask |= PRESSED;
203: } else {
204: stateMask &= ~PRESSED;
205: }
206:
207: fireStateChanged();
208:
209: if (!isPressed() && isArmed()) {
210: int modifiers = 0;
211: AWTEvent currentEvent = EventQueue.getCurrentEvent();
212: if (currentEvent instanceof InputEvent) {
213: modifiers = ((InputEvent) currentEvent)
214: .getModifiers();
215: } else if (currentEvent instanceof ActionEvent) {
216: modifiers = ((ActionEvent) currentEvent)
217: .getModifiers();
218: }
219: fireActionPerformed(new ActionEvent(this ,
220: ActionEvent.ACTION_PERFORMED,
221: getActionCommand(), EventQueue
222: .getMostRecentEventTime(), modifiers));
223: }
224:
225: }
226: }
227:
228: /////////////////
229: // Accessibility support
230: ////////////////
231:
232: /**
233: * Gets the AccessibleContext associated with this JToggleButton.
234: * For toggle buttons, the AccessibleContext takes the form of an
235: * AccessibleJToggleButton.
236: * A new AccessibleJToggleButton instance is created if necessary.
237: *
238: * @return an AccessibleJToggleButton that serves as the
239: * AccessibleContext of this JToggleButton
240: */
241: @Override
242: public AccessibleContext getAccessibleContext() {
243: if (accessibleContext == null) {
244: accessibleContext = new AccessibleJToggleButton();
245: }
246: return accessibleContext;
247: }
248:
249: /**
250: * This class implements accessibility support for the
251: * <code>JToggleButton</code> class. It provides an implementation of the
252: * Java Accessibility API appropriate to toggle button user-interface
253: * elements.
254: * <p/>
255: * <strong>Warning:</strong>
256: * Serialized objects of this class will not be compatible with
257: * future Swing releases. The current serialization support is
258: * appropriate for short term storage or RMI between applications running
259: * the same version of Swing. As of 1.4, support for long term storage
260: * of all JavaBeans<sup><font size="-2">TM</font></sup>
261: * has been added to the <code>java.beans</code> package.
262: * Please see {@link java.beans.XMLEncoder}.
263: */
264: protected class AccessibleJToggleButton extends
265: AccessibleAbstractButton implements ItemListener {
266:
267: public AccessibleJToggleButton() {
268: super ();
269: JideToggleSplitButton.this .addItemListener(this );
270: }
271:
272: /**
273: * Fire accessible property change events when the state of the
274: * toggle button changes.
275: */
276: public void itemStateChanged(ItemEvent e) {
277: JideToggleSplitButton tb = (JideToggleSplitButton) e
278: .getSource();
279: if (JideToggleSplitButton.this .accessibleContext != null) {
280: if (tb.isSelected()) {
281: JideToggleSplitButton.this .accessibleContext
282: .firePropertyChange(
283: AccessibleContext.ACCESSIBLE_STATE_PROPERTY,
284: null, AccessibleState.CHECKED);
285: } else {
286: JideToggleSplitButton.this .accessibleContext
287: .firePropertyChange(
288: AccessibleContext.ACCESSIBLE_STATE_PROPERTY,
289: AccessibleState.CHECKED, null);
290: }
291: }
292: }
293:
294: /**
295: * Get the role of this object.
296: *
297: * @return an instance of AccessibleRole describing the role of the
298: * object
299: */
300: @Override
301: public AccessibleRole getAccessibleRole() {
302: return AccessibleRole.TOGGLE_BUTTON;
303: }
304: } // inner class AccessibleJToggleButton
305: }
|