0N/A/*
2362N/A * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
2362N/A * published by the Free Software Foundation. Oracle designates this
0N/A * particular file as subject to the "Classpath" exception as provided
2362N/A * by Oracle in the LICENSE file that accompanied this code.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
2362N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
2362N/A * or visit www.oracle.com if you need additional information or have any
2362N/A * questions.
0N/A */
0N/A
0N/Apackage javax.swing.plaf.basic;
0N/A
0N/Aimport sun.swing.DefaultLookup;
0N/Aimport sun.swing.UIAction;
0N/Aimport javax.swing.border.Border;
0N/Aimport javax.swing.border.EmptyBorder;
0N/Aimport javax.swing.*;
0N/Aimport javax.swing.event.*;
0N/Aimport javax.swing.plaf.ActionMapUIResource;
0N/Aimport javax.swing.plaf.ComponentUI;
0N/Aimport javax.swing.plaf.OptionPaneUI;
0N/Aimport java.awt.*;
0N/Aimport java.awt.event.*;
0N/Aimport java.beans.PropertyChangeEvent;
0N/Aimport java.beans.PropertyChangeListener;
0N/Aimport java.util.Locale;
0N/Aimport java.security.AccessController;
0N/A
0N/Aimport sun.security.action.GetPropertyAction;
0N/A
0N/A
0N/A/**
0N/A * Provides the basic look and feel for a <code>JOptionPane</code>.
0N/A * <code>BasicMessagePaneUI</code> provides a means to place an icon,
0N/A * message and buttons into a <code>Container</code>.
0N/A * Generally, the layout will look like:<p>
0N/A * <pre>
0N/A * ------------------
0N/A * | i | message |
0N/A * | c | message |
0N/A * | o | message |
0N/A * | n | message |
0N/A * ------------------
0N/A * | buttons |
0N/A * |________________|
0N/A * </pre>
0N/A * icon is an instance of <code>Icon</code> that is wrapped inside a
0N/A * <code>JLabel</code>. The message is an opaque object and is tested
0N/A * for the following: if the message is a <code>Component</code> it is
0N/A * added to the <code>Container</code>, if it is an <code>Icon</code>
0N/A * it is wrapped inside a <code>JLabel</code> and added to the
0N/A * <code>Container</code> otherwise it is wrapped inside a <code>JLabel</code>.
0N/A * <p>
0N/A * The above layout is used when the option pane's
0N/A * <code>ComponentOrientation</code> property is horizontal, left-to-right.
0N/A * The layout will be adjusted appropriately for other orientations.
0N/A * <p>
0N/A * The <code>Container</code>, message, icon, and buttons are all
0N/A * determined from abstract methods.
0N/A *
0N/A * @author James Gosling
0N/A * @author Scott Violet
0N/A * @author Amy Fowler
0N/A */
0N/Apublic class BasicOptionPaneUI extends OptionPaneUI {
0N/A
0N/A public static final int MinimumWidth = 262;
0N/A public static final int MinimumHeight = 90;
0N/A
0N/A private static String newline;
0N/A
0N/A /**
0N/A * <code>JOptionPane</code> that the receiver is providing the
0N/A * look and feel for.
0N/A */
0N/A protected JOptionPane optionPane;
0N/A
0N/A protected Dimension minimumSize;
0N/A
0N/A /** JComponent provide for input if optionPane.getWantsInput() returns
0N/A * true. */
0N/A protected JComponent inputComponent;
0N/A
0N/A /** Component to receive focus when messaged with selectInitialValue. */
0N/A protected Component initialFocusComponent;
0N/A
0N/A /** This is set to true in validateComponent if a Component is contained
0N/A * in either the message or the buttons. */
0N/A protected boolean hasCustomComponents;
0N/A
0N/A protected PropertyChangeListener propertyChangeListener;
0N/A
0N/A private Handler handler;
0N/A
0N/A
0N/A static {
614N/A newline = java.security.AccessController.doPrivileged(
0N/A new GetPropertyAction("line.separator"));
0N/A if (newline == null) {
0N/A newline = "\n";
0N/A }
0N/A }
0N/A
0N/A static void loadActionMap(LazyActionMap map) {
0N/A map.put(new Actions(Actions.CLOSE));
0N/A BasicLookAndFeel.installAudioActionMap(map);
0N/A }
0N/A
0N/A
0N/A
0N/A /**
0N/A * Creates a new BasicOptionPaneUI instance.
0N/A */
0N/A public static ComponentUI createUI(JComponent x) {
0N/A return new BasicOptionPaneUI();
0N/A }
0N/A
0N/A /**
0N/A * Installs the receiver as the L&F for the passed in
0N/A * <code>JOptionPane</code>.
0N/A */
0N/A public void installUI(JComponent c) {
0N/A optionPane = (JOptionPane)c;
0N/A installDefaults();
0N/A optionPane.setLayout(createLayoutManager());
0N/A installComponents();
0N/A installListeners();
0N/A installKeyboardActions();
0N/A }
0N/A
0N/A /**
0N/A * Removes the receiver from the L&F controller of the passed in split
0N/A * pane.
0N/A */
0N/A public void uninstallUI(JComponent c) {
0N/A uninstallComponents();
0N/A optionPane.setLayout(null);
0N/A uninstallKeyboardActions();
0N/A uninstallListeners();
0N/A uninstallDefaults();
0N/A optionPane = null;
0N/A }
0N/A
0N/A protected void installDefaults() {
0N/A LookAndFeel.installColorsAndFont(optionPane, "OptionPane.background",
0N/A "OptionPane.foreground", "OptionPane.font");
0N/A LookAndFeel.installBorder(optionPane, "OptionPane.border");
0N/A minimumSize = UIManager.getDimension("OptionPane.minimumSize");
0N/A LookAndFeel.installProperty(optionPane, "opaque", Boolean.TRUE);
0N/A }
0N/A
0N/A protected void uninstallDefaults() {
0N/A LookAndFeel.uninstallBorder(optionPane);
0N/A }
0N/A
0N/A protected void installComponents() {
0N/A optionPane.add(createMessageArea());
0N/A
0N/A Container separator = createSeparator();
0N/A if (separator != null) {
0N/A optionPane.add(separator);
0N/A }
0N/A optionPane.add(createButtonArea());
0N/A optionPane.applyComponentOrientation(optionPane.getComponentOrientation());
0N/A }
0N/A
0N/A protected void uninstallComponents() {
0N/A hasCustomComponents = false;
0N/A inputComponent = null;
0N/A initialFocusComponent = null;
0N/A optionPane.removeAll();
0N/A }
0N/A
0N/A protected LayoutManager createLayoutManager() {
0N/A return new BoxLayout(optionPane, BoxLayout.Y_AXIS);
0N/A }
0N/A
0N/A protected void installListeners() {
0N/A if ((propertyChangeListener = createPropertyChangeListener()) != null) {
0N/A optionPane.addPropertyChangeListener(propertyChangeListener);
0N/A }
0N/A }
0N/A
0N/A protected void uninstallListeners() {
0N/A if (propertyChangeListener != null) {
0N/A optionPane.removePropertyChangeListener(propertyChangeListener);
0N/A propertyChangeListener = null;
0N/A }
0N/A handler = null;
0N/A }
0N/A
0N/A protected PropertyChangeListener createPropertyChangeListener() {
0N/A return getHandler();
0N/A }
0N/A
0N/A private Handler getHandler() {
0N/A if (handler == null) {
0N/A handler = new Handler();
0N/A }
0N/A return handler;
0N/A }
0N/A
0N/A protected void installKeyboardActions() {
0N/A InputMap map = getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
0N/A
0N/A SwingUtilities.replaceUIInputMap(optionPane, JComponent.
0N/A WHEN_IN_FOCUSED_WINDOW, map);
0N/A
0N/A LazyActionMap.installLazyActionMap(optionPane, BasicOptionPaneUI.class,
0N/A "OptionPane.actionMap");
0N/A }
0N/A
0N/A protected void uninstallKeyboardActions() {
0N/A SwingUtilities.replaceUIInputMap(optionPane, JComponent.
0N/A WHEN_IN_FOCUSED_WINDOW, null);
0N/A SwingUtilities.replaceUIActionMap(optionPane, null);
0N/A }
0N/A
0N/A InputMap getInputMap(int condition) {
0N/A if (condition == JComponent.WHEN_IN_FOCUSED_WINDOW) {
0N/A Object[] bindings = (Object[])DefaultLookup.get(
0N/A optionPane, this, "OptionPane.windowBindings");
0N/A if (bindings != null) {
0N/A return LookAndFeel.makeComponentInputMap(optionPane, bindings);
0N/A }
0N/A }
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * Returns the minimum size the option pane should be. Primarily
0N/A * provided for subclassers wishing to offer a different minimum size.
0N/A */
0N/A public Dimension getMinimumOptionPaneSize() {
0N/A if (minimumSize == null) {
0N/A return new Dimension(MinimumWidth, MinimumHeight);
0N/A }
0N/A return new Dimension(minimumSize.width,
0N/A minimumSize.height);
0N/A }
0N/A
0N/A /**
0N/A * If <code>c</code> is the <code>JOptionPane</code> the receiver
0N/A * is contained in, the preferred
0N/A * size that is returned is the maximum of the preferred size of
0N/A * the <code>LayoutManager</code> for the <code>JOptionPane</code>, and
0N/A * <code>getMinimumOptionPaneSize</code>.
0N/A */
0N/A public Dimension getPreferredSize(JComponent c) {
614N/A if (c == optionPane) {
0N/A Dimension ourMin = getMinimumOptionPaneSize();
0N/A LayoutManager lm = c.getLayout();
0N/A
0N/A if (lm != null) {
0N/A Dimension lmSize = lm.preferredLayoutSize(c);
0N/A
0N/A if (ourMin != null)
0N/A return new Dimension
0N/A (Math.max(lmSize.width, ourMin.width),
0N/A Math.max(lmSize.height, ourMin.height));
0N/A return lmSize;
0N/A }
0N/A return ourMin;
0N/A }
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * Messaged from installComponents to create a Container containing the
0N/A * body of the message. The icon is the created by calling
0N/A * <code>addIcon</code>.
0N/A */
0N/A protected Container createMessageArea() {
0N/A JPanel top = new JPanel();
0N/A Border topBorder = (Border)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.messageAreaBorder");
0N/A if (topBorder != null) {
0N/A top.setBorder(topBorder);
0N/A }
0N/A top.setLayout(new BorderLayout());
0N/A
0N/A /* Fill the body. */
0N/A Container body = new JPanel(new GridBagLayout());
0N/A Container realBody = new JPanel(new BorderLayout());
0N/A
0N/A body.setName("OptionPane.body");
0N/A realBody.setName("OptionPane.realBody");
0N/A
0N/A if (getIcon() != null) {
0N/A JPanel sep = new JPanel();
0N/A sep.setName("OptionPane.separator");
0N/A sep.setPreferredSize(new Dimension(15, 1));
0N/A realBody.add(sep, BorderLayout.BEFORE_LINE_BEGINS);
0N/A }
0N/A realBody.add(body, BorderLayout.CENTER);
0N/A
0N/A GridBagConstraints cons = new GridBagConstraints();
0N/A cons.gridx = cons.gridy = 0;
0N/A cons.gridwidth = GridBagConstraints.REMAINDER;
0N/A cons.gridheight = 1;
0N/A cons.anchor = DefaultLookup.getInt(optionPane, this,
0N/A "OptionPane.messageAnchor", GridBagConstraints.CENTER);
0N/A cons.insets = new Insets(0,0,3,0);
0N/A
0N/A addMessageComponents(body, cons, getMessage(),
0N/A getMaxCharactersPerLineCount(), false);
0N/A top.add(realBody, BorderLayout.CENTER);
0N/A
0N/A addIcon(top);
0N/A return top;
0N/A }
0N/A
0N/A /**
0N/A * Creates the appropriate object to represent <code>msg</code> and
0N/A * places it into <code>container</code>. If <code>msg</code> is an
0N/A * instance of Component, it is added directly, if it is an Icon,
0N/A * a JLabel is created to represent it, otherwise a JLabel is
0N/A * created for the string, if <code>d</code> is an Object[], this
0N/A * method will be recursively invoked for the children.
0N/A * <code>internallyCreated</code> is true if Objc is an instance
0N/A * of Component and was created internally by this method (this is
0N/A * used to correctly set hasCustomComponents only if !internallyCreated).
0N/A */
0N/A protected void addMessageComponents(Container container,
0N/A GridBagConstraints cons,
0N/A Object msg, int maxll,
0N/A boolean internallyCreated) {
0N/A if (msg == null) {
0N/A return;
0N/A }
0N/A if (msg instanceof Component) {
0N/A // To workaround problem where Gridbad will set child
0N/A // to its minimum size if its preferred size will not fit
0N/A // within allocated cells
0N/A if (msg instanceof JScrollPane || msg instanceof JPanel) {
0N/A cons.fill = GridBagConstraints.BOTH;
0N/A cons.weighty = 1;
0N/A } else {
0N/A cons.fill = GridBagConstraints.HORIZONTAL;
0N/A }
0N/A cons.weightx = 1;
0N/A
0N/A container.add((Component) msg, cons);
0N/A cons.weightx = 0;
0N/A cons.weighty = 0;
0N/A cons.fill = GridBagConstraints.NONE;
0N/A cons.gridy++;
0N/A if (!internallyCreated) {
0N/A hasCustomComponents = true;
0N/A }
0N/A
0N/A } else if (msg instanceof Object[]) {
0N/A Object [] msgs = (Object[]) msg;
614N/A for (Object o : msgs) {
614N/A addMessageComponents(container, cons, o, maxll, false);
0N/A }
0N/A
0N/A } else if (msg instanceof Icon) {
0N/A JLabel label = new JLabel( (Icon)msg, SwingConstants.CENTER );
0N/A configureMessageLabel(label);
0N/A addMessageComponents(container, cons, label, maxll, true);
0N/A
0N/A } else {
0N/A String s = msg.toString();
0N/A int len = s.length();
0N/A if (len <= 0) {
0N/A return;
0N/A }
614N/A int nl;
0N/A int nll = 0;
0N/A
0N/A if ((nl = s.indexOf(newline)) >= 0) {
0N/A nll = newline.length();
0N/A } else if ((nl = s.indexOf("\r\n")) >= 0) {
0N/A nll = 2;
0N/A } else if ((nl = s.indexOf('\n')) >= 0) {
0N/A nll = 1;
0N/A }
0N/A if (nl >= 0) {
0N/A // break up newlines
0N/A if (nl == 0) {
0N/A JPanel breakPanel = new JPanel() {
0N/A public Dimension getPreferredSize() {
0N/A Font f = getFont();
0N/A
0N/A if (f != null) {
0N/A return new Dimension(1, f.getSize() + 2);
0N/A }
0N/A return new Dimension(0, 0);
0N/A }
0N/A };
0N/A breakPanel.setName("OptionPane.break");
0N/A addMessageComponents(container, cons, breakPanel, maxll,
0N/A true);
0N/A } else {
0N/A addMessageComponents(container, cons, s.substring(0, nl),
0N/A maxll, false);
0N/A }
0N/A addMessageComponents(container, cons, s.substring(nl + nll), maxll,
0N/A false);
0N/A
0N/A } else if (len > maxll) {
0N/A Container c = Box.createVerticalBox();
0N/A c.setName("OptionPane.verticalBox");
0N/A burstStringInto(c, s, maxll);
0N/A addMessageComponents(container, cons, c, maxll, true );
0N/A
0N/A } else {
0N/A JLabel label;
0N/A label = new JLabel( s, JLabel.LEADING );
0N/A label.setName("OptionPane.label");
0N/A configureMessageLabel(label);
0N/A addMessageComponents(container, cons, label, maxll, true);
0N/A }
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Returns the message to display from the JOptionPane the receiver is
0N/A * providing the look and feel for.
0N/A */
0N/A protected Object getMessage() {
0N/A inputComponent = null;
0N/A if (optionPane != null) {
0N/A if (optionPane.getWantsInput()) {
0N/A /* Create a user component to capture the input. If the
0N/A selectionValues are non null the component and there
0N/A are < 20 values it'll be a combobox, if non null and
0N/A >= 20, it'll be a list, otherwise it'll be a textfield. */
0N/A Object message = optionPane.getMessage();
0N/A Object[] sValues = optionPane.getSelectionValues();
0N/A Object inputValue = optionPane
0N/A .getInitialSelectionValue();
0N/A JComponent toAdd;
0N/A
0N/A if (sValues != null) {
0N/A if (sValues.length < 20) {
0N/A JComboBox cBox = new JComboBox();
0N/A
0N/A cBox.setName("OptionPane.comboBox");
0N/A for(int counter = 0, maxCounter = sValues.length;
0N/A counter < maxCounter; counter++) {
0N/A cBox.addItem(sValues[counter]);
0N/A }
0N/A if (inputValue != null) {
0N/A cBox.setSelectedItem(inputValue);
0N/A }
0N/A inputComponent = cBox;
0N/A toAdd = cBox;
0N/A
0N/A } else {
0N/A JList list = new JList(sValues);
0N/A JScrollPane sp = new JScrollPane(list);
0N/A
0N/A sp.setName("OptionPane.scrollPane");
0N/A list.setName("OptionPane.list");
0N/A list.setVisibleRowCount(10);
0N/A list.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
0N/A if(inputValue != null)
0N/A list.setSelectedValue(inputValue, true);
0N/A list.addMouseListener(getHandler());
0N/A toAdd = sp;
0N/A inputComponent = list;
0N/A }
0N/A
0N/A } else {
0N/A MultiplexingTextField tf = new MultiplexingTextField(20);
0N/A
0N/A tf.setName("OptionPane.textField");
0N/A tf.setKeyStrokes(new KeyStroke[] {
0N/A KeyStroke.getKeyStroke("ENTER") } );
0N/A if (inputValue != null) {
0N/A String inputString = inputValue.toString();
0N/A tf.setText(inputString);
0N/A tf.setSelectionStart(0);
0N/A tf.setSelectionEnd(inputString.length());
0N/A }
0N/A tf.addActionListener(getHandler());
0N/A toAdd = inputComponent = tf;
0N/A }
0N/A
0N/A Object[] newMessage;
0N/A
0N/A if (message == null) {
0N/A newMessage = new Object[1];
0N/A newMessage[0] = toAdd;
0N/A
0N/A } else {
0N/A newMessage = new Object[2];
0N/A newMessage[0] = message;
0N/A newMessage[1] = toAdd;
0N/A }
0N/A return newMessage;
0N/A }
0N/A return optionPane.getMessage();
0N/A }
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * Creates and adds a JLabel representing the icon returned from
0N/A * <code>getIcon</code> to <code>top</code>. This is messaged from
0N/A * <code>createMessageArea</code>
0N/A */
0N/A protected void addIcon(Container top) {
0N/A /* Create the icon. */
0N/A Icon sideIcon = getIcon();
0N/A
0N/A if (sideIcon != null) {
0N/A JLabel iconLabel = new JLabel(sideIcon);
0N/A
0N/A iconLabel.setName("OptionPane.iconLabel");
0N/A iconLabel.setVerticalAlignment(SwingConstants.TOP);
0N/A top.add(iconLabel, BorderLayout.BEFORE_LINE_BEGINS);
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Returns the icon from the JOptionPane the receiver is providing
0N/A * the look and feel for, or the default icon as returned from
0N/A * <code>getDefaultIcon</code>.
0N/A */
0N/A protected Icon getIcon() {
0N/A Icon mIcon = (optionPane == null ? null : optionPane.getIcon());
0N/A
0N/A if(mIcon == null && optionPane != null)
0N/A mIcon = getIconForType(optionPane.getMessageType());
0N/A return mIcon;
0N/A }
0N/A
0N/A /**
0N/A * Returns the icon to use for the passed in type.
0N/A */
0N/A protected Icon getIconForType(int messageType) {
0N/A if(messageType < 0 || messageType > 3)
0N/A return null;
0N/A String propertyName = null;
0N/A switch(messageType) {
0N/A case 0:
0N/A propertyName = "OptionPane.errorIcon";
0N/A break;
0N/A case 1:
0N/A propertyName = "OptionPane.informationIcon";
0N/A break;
0N/A case 2:
0N/A propertyName = "OptionPane.warningIcon";
0N/A break;
0N/A case 3:
0N/A propertyName = "OptionPane.questionIcon";
0N/A break;
0N/A }
0N/A if (propertyName != null) {
0N/A return (Icon)DefaultLookup.get(optionPane, this, propertyName);
0N/A }
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * Returns the maximum number of characters to place on a line.
0N/A */
0N/A protected int getMaxCharactersPerLineCount() {
0N/A return optionPane.getMaxCharactersPerLineCount();
0N/A }
0N/A
0N/A /**
0N/A * Recursively creates new JLabel instances to represent <code>d</code>.
0N/A * Each JLabel instance is added to <code>c</code>.
0N/A */
0N/A protected void burstStringInto(Container c, String d, int maxll) {
0N/A // Primitive line wrapping
0N/A int len = d.length();
0N/A if (len <= 0)
0N/A return;
0N/A if (len > maxll) {
0N/A int p = d.lastIndexOf(' ', maxll);
0N/A if (p <= 0)
0N/A p = d.indexOf(' ', maxll);
0N/A if (p > 0 && p < len) {
0N/A burstStringInto(c, d.substring(0, p), maxll);
0N/A burstStringInto(c, d.substring(p + 1), maxll);
0N/A return;
0N/A }
0N/A }
0N/A JLabel label = new JLabel(d, JLabel.LEFT);
0N/A label.setName("OptionPane.label");
0N/A configureMessageLabel(label);
0N/A c.add(label);
0N/A }
0N/A
0N/A protected Container createSeparator() {
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * Creates and returns a Container containing the buttons. The buttons
0N/A * are created by calling <code>getButtons</code>.
0N/A */
0N/A protected Container createButtonArea() {
0N/A JPanel bottom = new JPanel();
0N/A Border border = (Border)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.buttonAreaBorder");
0N/A bottom.setName("OptionPane.buttonArea");
0N/A if (border != null) {
0N/A bottom.setBorder(border);
0N/A }
0N/A bottom.setLayout(new ButtonAreaLayout(
0N/A DefaultLookup.getBoolean(optionPane, this,
0N/A "OptionPane.sameSizeButtons", true),
0N/A DefaultLookup.getInt(optionPane, this, "OptionPane.buttonPadding",
0N/A 6),
0N/A DefaultLookup.getInt(optionPane, this,
0N/A "OptionPane.buttonOrientation", SwingConstants.CENTER),
0N/A DefaultLookup.getBoolean(optionPane, this, "OptionPane.isYesLast",
0N/A false)));
0N/A addButtonComponents(bottom, getButtons(), getInitialValueIndex());
0N/A return bottom;
0N/A }
0N/A
0N/A /**
0N/A * Creates the appropriate object to represent each of the objects in
0N/A * <code>buttons</code> and adds it to <code>container</code>. This
0N/A * differs from addMessageComponents in that it will recurse on
0N/A * <code>buttons</code> and that if button is not a Component
0N/A * it will create an instance of JButton.
0N/A */
0N/A protected void addButtonComponents(Container container, Object[] buttons,
0N/A int initialIndex) {
0N/A if (buttons != null && buttons.length > 0) {
0N/A boolean sizeButtonsToSame = getSizeButtonsToSameWidth();
0N/A boolean createdAll = true;
0N/A int numButtons = buttons.length;
0N/A JButton[] createdButtons = null;
0N/A int maxWidth = 0;
0N/A
0N/A if (sizeButtonsToSame) {
0N/A createdButtons = new JButton[numButtons];
0N/A }
0N/A
0N/A for(int counter = 0; counter < numButtons; counter++) {
0N/A Object button = buttons[counter];
0N/A Component newComponent;
0N/A
0N/A if (button instanceof Component) {
0N/A createdAll = false;
0N/A newComponent = (Component)button;
0N/A container.add(newComponent);
0N/A hasCustomComponents = true;
0N/A
0N/A } else {
0N/A JButton aButton;
0N/A
0N/A if (button instanceof ButtonFactory) {
0N/A aButton = ((ButtonFactory)button).createButton();
0N/A }
0N/A else if (button instanceof Icon)
0N/A aButton = new JButton((Icon)button);
0N/A else
0N/A aButton = new JButton(button.toString());
0N/A
0N/A aButton.setName("OptionPane.button");
0N/A aButton.setMultiClickThreshhold(DefaultLookup.getInt(
0N/A optionPane, this, "OptionPane.buttonClickThreshhold",
0N/A 0));
0N/A configureButton(aButton);
0N/A
0N/A container.add(aButton);
0N/A
0N/A ActionListener buttonListener = createButtonActionListener(counter);
0N/A if (buttonListener != null) {
0N/A aButton.addActionListener(buttonListener);
0N/A }
0N/A newComponent = aButton;
0N/A }
0N/A if (sizeButtonsToSame && createdAll &&
0N/A (newComponent instanceof JButton)) {
0N/A createdButtons[counter] = (JButton)newComponent;
0N/A maxWidth = Math.max(maxWidth,
0N/A newComponent.getMinimumSize().width);
0N/A }
0N/A if (counter == initialIndex) {
0N/A initialFocusComponent = newComponent;
0N/A if (initialFocusComponent instanceof JButton) {
0N/A JButton defaultB = (JButton)initialFocusComponent;
0N/A defaultB.addHierarchyListener(new HierarchyListener() {
0N/A public void hierarchyChanged(HierarchyEvent e) {
0N/A if ((e.getChangeFlags() &
0N/A HierarchyEvent.PARENT_CHANGED) != 0) {
0N/A JButton defaultButton = (JButton) e.getComponent();
0N/A JRootPane root =
0N/A SwingUtilities.getRootPane(defaultButton);
0N/A if (root != null) {
0N/A root.setDefaultButton(defaultButton);
0N/A }
0N/A }
0N/A }
0N/A });
0N/A }
0N/A }
0N/A }
0N/A ((ButtonAreaLayout)container.getLayout()).
0N/A setSyncAllWidths((sizeButtonsToSame && createdAll));
0N/A /* Set the padding, windows seems to use 8 if <= 2 components,
0N/A otherwise 4 is used. It may actually just be the size of the
0N/A buttons is always the same, not sure. */
0N/A if (DefaultLookup.getBoolean(optionPane, this,
0N/A "OptionPane.setButtonMargin", true) && sizeButtonsToSame &&
0N/A createdAll) {
0N/A JButton aButton;
0N/A int padSize;
0N/A
0N/A padSize = (numButtons <= 2? 8 : 4);
0N/A
0N/A for(int counter = 0; counter < numButtons; counter++) {
0N/A aButton = createdButtons[counter];
0N/A aButton.setMargin(new Insets(2, padSize, 2, padSize));
0N/A }
0N/A }
0N/A }
0N/A }
0N/A
0N/A protected ActionListener createButtonActionListener(int buttonIndex) {
0N/A return new ButtonActionListener(buttonIndex);
0N/A }
0N/A
0N/A /**
0N/A * Returns the buttons to display from the JOptionPane the receiver is
0N/A * providing the look and feel for. If the JOptionPane has options
0N/A * set, they will be provided, otherwise if the optionType is
0N/A * YES_NO_OPTION, yesNoOptions is returned, if the type is
0N/A * YES_NO_CANCEL_OPTION yesNoCancelOptions is returned, otherwise
0N/A * defaultButtons are returned.
0N/A */
0N/A protected Object[] getButtons() {
0N/A if (optionPane != null) {
0N/A Object[] suppliedOptions = optionPane.getOptions();
0N/A
0N/A if (suppliedOptions == null) {
0N/A Object[] defaultOptions;
0N/A int type = optionPane.getOptionType();
0N/A Locale l = optionPane.getLocale();
0N/A int minimumWidth =
0N/A DefaultLookup.getInt(optionPane, this,
0N/A "OptionPane.buttonMinimumWidth",-1);
0N/A if (type == JOptionPane.YES_NO_OPTION) {
0N/A defaultOptions = new ButtonFactory[2];
0N/A defaultOptions[0] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.yesButtonText", l),
0N/A getMnemonic("OptionPane.yesButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.yesIcon"), minimumWidth);
0N/A defaultOptions[1] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.noButtonText", l),
0N/A getMnemonic("OptionPane.noButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.noIcon"), minimumWidth);
0N/A } else if (type == JOptionPane.YES_NO_CANCEL_OPTION) {
0N/A defaultOptions = new ButtonFactory[3];
0N/A defaultOptions[0] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.yesButtonText", l),
0N/A getMnemonic("OptionPane.yesButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.yesIcon"), minimumWidth);
0N/A defaultOptions[1] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.noButtonText",l),
0N/A getMnemonic("OptionPane.noButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.noIcon"), minimumWidth);
0N/A defaultOptions[2] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.cancelButtonText",l),
0N/A getMnemonic("OptionPane.cancelButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.cancelIcon"), minimumWidth);
0N/A } else if (type == JOptionPane.OK_CANCEL_OPTION) {
0N/A defaultOptions = new ButtonFactory[2];
0N/A defaultOptions[0] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.okButtonText",l),
0N/A getMnemonic("OptionPane.okButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.okIcon"), minimumWidth);
0N/A defaultOptions[1] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.cancelButtonText",l),
0N/A getMnemonic("OptionPane.cancelButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.cancelIcon"), minimumWidth);
0N/A } else {
0N/A defaultOptions = new ButtonFactory[1];
0N/A defaultOptions[0] = new ButtonFactory(
0N/A UIManager.getString("OptionPane.okButtonText",l),
0N/A getMnemonic("OptionPane.okButtonMnemonic", l),
0N/A (Icon)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.okIcon"), minimumWidth);
0N/A }
0N/A return defaultOptions;
0N/A
0N/A }
0N/A return suppliedOptions;
0N/A }
0N/A return null;
0N/A }
0N/A
0N/A private int getMnemonic(String key, Locale l) {
0N/A String value = (String)UIManager.get(key, l);
0N/A
0N/A if (value == null) {
0N/A return 0;
0N/A }
0N/A try {
0N/A return Integer.parseInt(value);
0N/A }
0N/A catch (NumberFormatException nfe) { }
0N/A return 0;
0N/A }
0N/A
0N/A /**
0N/A * Returns true, basic L&F wants all the buttons to have the same
0N/A * width.
0N/A */
0N/A protected boolean getSizeButtonsToSameWidth() {
0N/A return true;
0N/A }
0N/A
0N/A /**
0N/A * Returns the initial index into the buttons to select. The index
0N/A * is calculated from the initial value from the JOptionPane and
0N/A * options of the JOptionPane or 0.
0N/A */
0N/A protected int getInitialValueIndex() {
0N/A if (optionPane != null) {
0N/A Object iv = optionPane.getInitialValue();
0N/A Object[] options = optionPane.getOptions();
0N/A
0N/A if(options == null) {
0N/A return 0;
0N/A }
0N/A else if(iv != null) {
0N/A for(int counter = options.length - 1; counter >= 0; counter--){
0N/A if(options[counter].equals(iv))
0N/A return counter;
0N/A }
0N/A }
0N/A }
0N/A return -1;
0N/A }
0N/A
0N/A /**
0N/A * Sets the input value in the option pane the receiver is providing
0N/A * the look and feel for based on the value in the inputComponent.
0N/A */
0N/A protected void resetInputValue() {
0N/A if(inputComponent != null && (inputComponent instanceof JTextField)) {
0N/A optionPane.setInputValue(((JTextField)inputComponent).getText());
0N/A
0N/A } else if(inputComponent != null &&
0N/A (inputComponent instanceof JComboBox)) {
0N/A optionPane.setInputValue(((JComboBox)inputComponent)
0N/A .getSelectedItem());
0N/A } else if(inputComponent != null) {
0N/A optionPane.setInputValue(((JList)inputComponent)
0N/A .getSelectedValue());
0N/A }
0N/A }
0N/A
0N/A
0N/A /**
0N/A * If inputComponent is non-null, the focus is requested on that,
0N/A * otherwise request focus on the default value
0N/A */
0N/A public void selectInitialValue(JOptionPane op) {
0N/A if (inputComponent != null)
0N/A inputComponent.requestFocus();
0N/A else {
0N/A if (initialFocusComponent != null)
0N/A initialFocusComponent.requestFocus();
0N/A
0N/A if (initialFocusComponent instanceof JButton) {
0N/A JRootPane root = SwingUtilities.getRootPane(initialFocusComponent);
0N/A if (root != null) {
0N/A root.setDefaultButton((JButton)initialFocusComponent);
0N/A }
0N/A }
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Returns true if in the last call to validateComponent the message
0N/A * or buttons contained a subclass of Component.
0N/A */
0N/A public boolean containsCustomComponents(JOptionPane op) {
0N/A return hasCustomComponents;
0N/A }
0N/A
0N/A
0N/A /**
0N/A * <code>ButtonAreaLayout</code> behaves in a similar manner to
0N/A * <code>FlowLayout</code>. It lays out all components from left to
0N/A * right. If <code>syncAllWidths</code> is true, the widths of each
0N/A * component will be set to the largest preferred size width.
0N/A *
0N/A * This class should be treated as a &quot;protected&quot; inner class.
3972N/A * Instantiate it only within subclasses of {@code BasicOptionPaneUI}.
0N/A */
0N/A public static class ButtonAreaLayout implements LayoutManager {
0N/A protected boolean syncAllWidths;
0N/A protected int padding;
0N/A /** If true, children are lumped together in parent. */
0N/A protected boolean centersChildren;
0N/A private int orientation;
0N/A private boolean reverseButtons;
0N/A /**
0N/A * Indicates whether or not centersChildren should be used vs
0N/A * the orientation. This is done for backward compatability
0N/A * for subclassers.
0N/A */
0N/A private boolean useOrientation;
0N/A
0N/A public ButtonAreaLayout(boolean syncAllWidths, int padding) {
0N/A this.syncAllWidths = syncAllWidths;
0N/A this.padding = padding;
0N/A centersChildren = true;
0N/A useOrientation = false;
0N/A }
0N/A
0N/A ButtonAreaLayout(boolean syncAllSizes, int padding, int orientation,
0N/A boolean reverseButtons) {
0N/A this(syncAllSizes, padding);
0N/A useOrientation = true;
0N/A this.orientation = orientation;
0N/A this.reverseButtons = reverseButtons;
0N/A }
0N/A
0N/A public void setSyncAllWidths(boolean newValue) {
0N/A syncAllWidths = newValue;
0N/A }
0N/A
0N/A public boolean getSyncAllWidths() {
0N/A return syncAllWidths;
0N/A }
0N/A
0N/A public void setPadding(int newPadding) {
0N/A this.padding = newPadding;
0N/A }
0N/A
0N/A public int getPadding() {
0N/A return padding;
0N/A }
0N/A
0N/A public void setCentersChildren(boolean newValue) {
0N/A centersChildren = newValue;
0N/A useOrientation = false;
0N/A }
0N/A
0N/A public boolean getCentersChildren() {
0N/A return centersChildren;
0N/A }
0N/A
0N/A private int getOrientation(Container container) {
0N/A if (!useOrientation) {
0N/A return SwingConstants.CENTER;
0N/A }
0N/A if (container.getComponentOrientation().isLeftToRight()) {
0N/A return orientation;
0N/A }
0N/A switch (orientation) {
0N/A case SwingConstants.LEFT:
0N/A return SwingConstants.RIGHT;
0N/A case SwingConstants.RIGHT:
0N/A return SwingConstants.LEFT;
0N/A case SwingConstants.CENTER:
0N/A return SwingConstants.CENTER;
0N/A }
0N/A return SwingConstants.LEFT;
0N/A }
0N/A
0N/A public void addLayoutComponent(String string, Component comp) {
0N/A }
0N/A
0N/A public void layoutContainer(Container container) {
0N/A Component[] children = container.getComponents();
0N/A
0N/A if(children != null && children.length > 0) {
0N/A int numChildren = children.length;
0N/A Insets insets = container.getInsets();
0N/A int maxWidth = 0;
0N/A int maxHeight = 0;
0N/A int totalButtonWidth = 0;
0N/A int x = 0;
0N/A int xOffset = 0;
0N/A boolean ltr = container.getComponentOrientation().
0N/A isLeftToRight();
0N/A boolean reverse = (ltr) ? reverseButtons : !reverseButtons;
0N/A
0N/A for(int counter = 0; counter < numChildren; counter++) {
0N/A Dimension pref = children[counter].getPreferredSize();
0N/A maxWidth = Math.max(maxWidth, pref.width);
0N/A maxHeight = Math.max(maxHeight, pref.height);
0N/A totalButtonWidth += pref.width;
0N/A }
0N/A if (getSyncAllWidths()) {
0N/A totalButtonWidth = maxWidth * numChildren;
0N/A }
0N/A totalButtonWidth += (numChildren - 1) * padding;
0N/A
0N/A switch (getOrientation(container)) {
0N/A case SwingConstants.LEFT:
0N/A x = insets.left;
0N/A break;
0N/A case SwingConstants.RIGHT:
0N/A x = container.getWidth() - insets.right - totalButtonWidth;
0N/A break;
0N/A case SwingConstants.CENTER:
0N/A if (getCentersChildren() || numChildren < 2) {
0N/A x = (container.getWidth() - totalButtonWidth) / 2;
0N/A }
0N/A else {
0N/A x = insets.left;
0N/A if (getSyncAllWidths()) {
0N/A xOffset = (container.getWidth() - insets.left -
0N/A insets.right - totalButtonWidth) /
0N/A (numChildren - 1) + maxWidth;
0N/A }
0N/A else {
0N/A xOffset = (container.getWidth() - insets.left -
0N/A insets.right - totalButtonWidth) /
0N/A (numChildren - 1);
0N/A }
0N/A }
0N/A break;
0N/A }
0N/A
0N/A for (int counter = 0; counter < numChildren; counter++) {
0N/A int index = (reverse) ? numChildren - counter - 1 :
0N/A counter;
0N/A Dimension pref = children[index].getPreferredSize();
0N/A
0N/A if (getSyncAllWidths()) {
0N/A children[index].setBounds(x, insets.top,
0N/A maxWidth, maxHeight);
0N/A }
0N/A else {
0N/A children[index].setBounds(x, insets.top, pref.width,
0N/A pref.height);
0N/A }
0N/A if (xOffset != 0) {
0N/A x += xOffset;
0N/A }
0N/A else {
0N/A x += children[index].getWidth() + padding;
0N/A }
0N/A }
0N/A }
0N/A }
0N/A
0N/A public Dimension minimumLayoutSize(Container c) {
0N/A if(c != null) {
0N/A Component[] children = c.getComponents();
0N/A
0N/A if(children != null && children.length > 0) {
0N/A Dimension aSize;
0N/A int numChildren = children.length;
0N/A int height = 0;
0N/A Insets cInsets = c.getInsets();
0N/A int extraHeight = cInsets.top + cInsets.bottom;
0N/A int extraWidth = cInsets.left + cInsets.right;
0N/A
0N/A if (syncAllWidths) {
0N/A int maxWidth = 0;
0N/A
0N/A for(int counter = 0; counter < numChildren; counter++){
0N/A aSize = children[counter].getPreferredSize();
0N/A height = Math.max(height, aSize.height);
0N/A maxWidth = Math.max(maxWidth, aSize.width);
0N/A }
0N/A return new Dimension(extraWidth + (maxWidth * numChildren) +
0N/A (numChildren - 1) * padding,
0N/A extraHeight + height);
0N/A }
0N/A else {
0N/A int totalWidth = 0;
0N/A
0N/A for(int counter = 0; counter < numChildren; counter++){
0N/A aSize = children[counter].getPreferredSize();
0N/A height = Math.max(height, aSize.height);
0N/A totalWidth += aSize.width;
0N/A }
0N/A totalWidth += ((numChildren - 1) * padding);
0N/A return new Dimension(extraWidth + totalWidth, extraHeight + height);
0N/A }
0N/A }
0N/A }
0N/A return new Dimension(0, 0);
0N/A }
0N/A
0N/A public Dimension preferredLayoutSize(Container c) {
0N/A return minimumLayoutSize(c);
0N/A }
0N/A
0N/A public void removeLayoutComponent(Component c) { }
0N/A }
0N/A
0N/A
0N/A /**
0N/A * This class should be treated as a &quot;protected&quot; inner class.
3972N/A * Instantiate it only within subclasses of {@code BasicOptionPaneUI}.
0N/A */
0N/A public class PropertyChangeHandler implements PropertyChangeListener {
0N/A /**
0N/A * If the source of the PropertyChangeEvent <code>e</code> equals the
0N/A * optionPane and is one of the ICON_PROPERTY, MESSAGE_PROPERTY,
0N/A * OPTIONS_PROPERTY or INITIAL_VALUE_PROPERTY,
0N/A * validateComponent is invoked.
0N/A */
0N/A public void propertyChange(PropertyChangeEvent e) {
0N/A getHandler().propertyChange(e);
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Configures any necessary colors/fonts for the specified label
0N/A * used representing the message.
0N/A */
0N/A private void configureMessageLabel(JLabel label) {
0N/A Color color = (Color)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.messageForeground");
0N/A if (color != null) {
0N/A label.setForeground(color);
0N/A }
0N/A Font messageFont = (Font)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.messageFont");
0N/A if (messageFont != null) {
0N/A label.setFont(messageFont);
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Configures any necessary colors/fonts for the specified button
0N/A * used representing the button portion of the optionpane.
0N/A */
0N/A private void configureButton(JButton button) {
0N/A Font buttonFont = (Font)DefaultLookup.get(optionPane, this,
0N/A "OptionPane.buttonFont");
0N/A if (buttonFont != null) {
0N/A button.setFont(buttonFont);
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * This class should be treated as a &quot;protected&quot; inner class.
3972N/A * Instantiate it only within subclasses of {@code BasicOptionPaneUI}.
0N/A */
0N/A public class ButtonActionListener implements ActionListener {
0N/A protected int buttonIndex;
0N/A
0N/A public ButtonActionListener(int buttonIndex) {
0N/A this.buttonIndex = buttonIndex;
0N/A }
0N/A
0N/A public void actionPerformed(ActionEvent e) {
0N/A if (optionPane != null) {
0N/A int optionType = optionPane.getOptionType();
0N/A Object[] options = optionPane.getOptions();
0N/A
0N/A /* If the option pane takes input, then store the input value
0N/A * if custom options were specified, if the option type is
0N/A * DEFAULT_OPTION, OR if option type is set to a predefined
0N/A * one and the user chose the affirmative answer.
0N/A */
0N/A if (inputComponent != null) {
0N/A if (options != null ||
0N/A optionType == JOptionPane.DEFAULT_OPTION ||
0N/A ((optionType == JOptionPane.YES_NO_OPTION ||
0N/A optionType == JOptionPane.YES_NO_CANCEL_OPTION ||
0N/A optionType == JOptionPane.OK_CANCEL_OPTION) &&
0N/A buttonIndex == 0)) {
0N/A resetInputValue();
0N/A }
0N/A }
0N/A if (options == null) {
0N/A if (optionType == JOptionPane.OK_CANCEL_OPTION &&
0N/A buttonIndex == 1) {
215N/A optionPane.setValue(Integer.valueOf(2));
0N/A
0N/A } else {
215N/A optionPane.setValue(Integer.valueOf(buttonIndex));
0N/A }
0N/A } else {
0N/A optionPane.setValue(options[buttonIndex]);
0N/A }
0N/A }
0N/A }
0N/A }
0N/A
0N/A
0N/A private class Handler implements ActionListener, MouseListener,
0N/A PropertyChangeListener {
0N/A //
0N/A // ActionListener
0N/A //
0N/A public void actionPerformed(ActionEvent e) {
0N/A optionPane.setInputValue(((JTextField)e.getSource()).getText());
0N/A }
0N/A
0N/A
0N/A //
0N/A // MouseListener
0N/A //
0N/A public void mouseClicked(MouseEvent e) {
0N/A }
0N/A
0N/A public void mouseReleased(MouseEvent e) {
0N/A }
0N/A
0N/A public void mouseEntered(MouseEvent e) {
0N/A }
0N/A
0N/A public void mouseExited(MouseEvent e) {
0N/A }
0N/A
0N/A public void mousePressed(MouseEvent e) {
0N/A if (e.getClickCount() == 2) {
0N/A JList list = (JList)e.getSource();
0N/A int index = list.locationToIndex(e.getPoint());
0N/A
0N/A optionPane.setInputValue(list.getModel().getElementAt(index));
4780N/A optionPane.setValue(JOptionPane.OK_OPTION);
0N/A }
0N/A }
0N/A
0N/A //
0N/A // PropertyChangeListener
0N/A //
0N/A public void propertyChange(PropertyChangeEvent e) {
0N/A if(e.getSource() == optionPane) {
0N/A // Option Pane Auditory Cue Activation
0N/A // only respond to "ancestor" changes
0N/A // the idea being that a JOptionPane gets a JDialog when it is
0N/A // set to appear and loses it's JDialog when it is dismissed.
0N/A if ("ancestor" == e.getPropertyName()) {
0N/A JOptionPane op = (JOptionPane)e.getSource();
0N/A boolean isComingUp;
0N/A
0N/A // if the old value is null, then the JOptionPane is being
0N/A // created since it didn't previously have an ancestor.
0N/A if (e.getOldValue() == null) {
0N/A isComingUp = true;
0N/A } else {
0N/A isComingUp = false;
0N/A }
0N/A
0N/A // figure out what to do based on the message type
0N/A switch (op.getMessageType()) {
0N/A case JOptionPane.PLAIN_MESSAGE:
0N/A if (isComingUp) {
0N/A BasicLookAndFeel.playSound(optionPane,
0N/A "OptionPane.informationSound");
0N/A }
0N/A break;
0N/A case JOptionPane.QUESTION_MESSAGE:
0N/A if (isComingUp) {
0N/A BasicLookAndFeel.playSound(optionPane,
0N/A "OptionPane.questionSound");
0N/A }
0N/A break;
0N/A case JOptionPane.INFORMATION_MESSAGE:
0N/A if (isComingUp) {
0N/A BasicLookAndFeel.playSound(optionPane,
0N/A "OptionPane.informationSound");
0N/A }
0N/A break;
0N/A case JOptionPane.WARNING_MESSAGE:
0N/A if (isComingUp) {
0N/A BasicLookAndFeel.playSound(optionPane,
0N/A "OptionPane.warningSound");
0N/A }
0N/A break;
0N/A case JOptionPane.ERROR_MESSAGE:
0N/A if (isComingUp) {
0N/A BasicLookAndFeel.playSound(optionPane,
0N/A "OptionPane.errorSound");
0N/A }
0N/A break;
0N/A default:
0N/A System.err.println("Undefined JOptionPane type: " +
0N/A op.getMessageType());
0N/A break;
0N/A }
0N/A }
0N/A // Visual activity
0N/A String changeName = e.getPropertyName();
0N/A
0N/A if(changeName == JOptionPane.OPTIONS_PROPERTY ||
0N/A changeName == JOptionPane.INITIAL_VALUE_PROPERTY ||
0N/A changeName == JOptionPane.ICON_PROPERTY ||
0N/A changeName == JOptionPane.MESSAGE_TYPE_PROPERTY ||
0N/A changeName == JOptionPane.OPTION_TYPE_PROPERTY ||
0N/A changeName == JOptionPane.MESSAGE_PROPERTY ||
0N/A changeName == JOptionPane.SELECTION_VALUES_PROPERTY ||
0N/A changeName == JOptionPane.INITIAL_SELECTION_VALUE_PROPERTY ||
0N/A changeName == JOptionPane.WANTS_INPUT_PROPERTY) {
0N/A uninstallComponents();
0N/A installComponents();
0N/A optionPane.validate();
0N/A }
0N/A else if (changeName == "componentOrientation") {
0N/A ComponentOrientation o = (ComponentOrientation)e.getNewValue();
0N/A JOptionPane op = (JOptionPane)e.getSource();
614N/A if (o != e.getOldValue()) {
0N/A op.applyComponentOrientation(o);
0N/A }
0N/A }
0N/A }
0N/A }
0N/A }
0N/A
0N/A
0N/A //
0N/A // Classes used when optionPane.getWantsInput returns true.
0N/A //
0N/A
0N/A /**
0N/A * A JTextField that allows you to specify an array of KeyStrokes that
0N/A * that will have their bindings processed regardless of whether or
0N/A * not they are registered on the JTextField. This is used as we really
0N/A * want the ActionListener to be notified so that we can push the
0N/A * change to the JOptionPane, but we also want additional bindings
0N/A * (those of the JRootPane) to be processed as well.
0N/A */
0N/A private static class MultiplexingTextField extends JTextField {
0N/A private KeyStroke[] strokes;
0N/A
0N/A MultiplexingTextField(int cols) {
0N/A super(cols);
0N/A }
0N/A
0N/A /**
0N/A * Sets the KeyStrokes that will be additional processed for
0N/A * ancestor bindings.
0N/A */
0N/A void setKeyStrokes(KeyStroke[] strokes) {
0N/A this.strokes = strokes;
0N/A }
0N/A
0N/A protected boolean processKeyBinding(KeyStroke ks, KeyEvent e,
0N/A int condition, boolean pressed) {
0N/A boolean processed = super.processKeyBinding(ks, e, condition,
0N/A pressed);
0N/A
0N/A if (processed && condition != JComponent.WHEN_IN_FOCUSED_WINDOW) {
0N/A for (int counter = strokes.length - 1; counter >= 0;
0N/A counter--) {
0N/A if (strokes[counter].equals(ks)) {
0N/A // Returning false will allow further processing
0N/A // of the bindings, eg our parent Containers will get a
0N/A // crack at them.
0N/A return false;
0N/A }
0N/A }
0N/A }
0N/A return processed;
0N/A }
0N/A }
0N/A
0N/A
0N/A
0N/A /**
0N/A * Registered in the ActionMap. Sets the value of the option pane
0N/A * to <code>JOptionPane.CLOSED_OPTION</code>.
0N/A */
0N/A private static class Actions extends UIAction {
0N/A private static final String CLOSE = "close";
0N/A
0N/A Actions(String key) {
0N/A super(key);
0N/A }
0N/A
0N/A public void actionPerformed(ActionEvent e) {
0N/A if (getName() == CLOSE) {
0N/A JOptionPane optionPane = (JOptionPane)e.getSource();
0N/A
215N/A optionPane.setValue(Integer.valueOf(JOptionPane.CLOSED_OPTION));
0N/A }
0N/A }
0N/A }
0N/A
0N/A
0N/A /**
0N/A * This class is used to create the default buttons. This indirection is
0N/A * used so that addButtonComponents can tell which Buttons were created
0N/A * by us vs subclassers or from the JOptionPane itself.
0N/A */
0N/A private static class ButtonFactory {
0N/A private String text;
0N/A private int mnemonic;
0N/A private Icon icon;
0N/A private int minimumWidth = -1;
0N/A
0N/A ButtonFactory(String text, int mnemonic, Icon icon, int minimumWidth) {
0N/A this.text = text;
0N/A this.mnemonic = mnemonic;
0N/A this.icon = icon;
0N/A this.minimumWidth = minimumWidth;
0N/A }
0N/A
0N/A JButton createButton() {
614N/A JButton button;
0N/A
0N/A if (minimumWidth > 0) {
0N/A button = new ConstrainedButton(text, minimumWidth);
0N/A } else {
0N/A button = new JButton(text);
0N/A }
0N/A if (icon != null) {
0N/A button.setIcon(icon);
0N/A }
0N/A if (mnemonic != 0) {
0N/A button.setMnemonic(mnemonic);
0N/A }
0N/A return button;
0N/A }
0N/A
0N/A private static class ConstrainedButton extends JButton {
0N/A int minimumWidth;
0N/A
0N/A ConstrainedButton(String text, int minimumWidth) {
0N/A super(text);
0N/A this.minimumWidth = minimumWidth;
0N/A }
0N/A
0N/A public Dimension getMinimumSize() {
0N/A Dimension min = super.getMinimumSize();
0N/A min.width = Math.max(min.width, minimumWidth);
0N/A return min;
0N/A }
0N/A
0N/A public Dimension getPreferredSize() {
0N/A Dimension pref = super.getPreferredSize();
0N/A pref.width = Math.max(pref.width, minimumWidth);
0N/A return pref;
0N/A }
0N/A }
0N/A }
0N/A}