123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379 |
- /*
- * Copyright (c) 2006-2008 Chris Smith, Shane Mc Cormack, Gregory Holmes
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy
- * of this software and associated documentation files (the "Software"), to deal
- * in the Software without restriction, including without limitation the rights
- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- * copies of the Software, and to permit persons to whom the Software is
- * furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
- * SOFTWARE.
- */
-
- package com.dmdirc.ui.swing.framemanager.buttonbar;
-
- import com.dmdirc.FrameContainer;
- import com.dmdirc.FrameContainerComparator;
- import com.dmdirc.Main;
- import com.dmdirc.config.IdentityManager;
- import com.dmdirc.interfaces.IconChangeListener;
- import com.dmdirc.interfaces.NotificationListener;
- import com.dmdirc.interfaces.SelectionListener;
- import com.dmdirc.ui.interfaces.FrameManager;
- import com.dmdirc.ui.interfaces.FramemanagerPosition;
- import com.dmdirc.ui.interfaces.Window;
- import com.dmdirc.ui.swing.UIUtilities;
- import com.dmdirc.util.MapList;
-
- import java.awt.BorderLayout;
- import java.awt.Color;
- import java.awt.Dimension;
- import java.awt.GridBagConstraints;
- import java.awt.GridBagLayout;
- import java.awt.Insets;
- import java.awt.event.ActionEvent;
- import java.awt.event.ActionListener;
- import java.awt.event.ComponentEvent;
- import java.awt.event.ComponentListener;
- import java.io.Serializable;
- import java.util.Collections;
- import java.util.HashMap;
- import java.util.List;
- import java.util.Map;
-
- import javax.swing.BorderFactory;
- import javax.swing.Icon;
- import javax.swing.JComponent;
- import javax.swing.JPanel;
- import javax.swing.JToggleButton;
- import javax.swing.SwingConstants;
-
- /**
- * The button bar manager is a grid of buttons that presents a manager similar
- * to that used by mIRC.
- *
- * @author chris
- */
- public final class ButtonBar implements FrameManager, ActionListener,
- ComponentListener, Serializable, NotificationListener,
- SelectionListener, IconChangeListener {
-
- /**
- * A version number for this class. It should be changed whenever the class
- * structure is changed (or anything else that would prevent serialized
- * objects being unserialized with the new class).
- */
- private static final long serialVersionUID = 3;
-
- /** A map of parent containers to their respective windows. */
- private final MapList<FrameContainer, FrameContainer> windows;
-
- /** A map of containers to the buttons we're using for them. */
- private final Map<FrameContainer, JToggleButton> buttons;
-
- /** The position of this frame manager. */
- private final FramemanagerPosition position;
-
- /** The parent for the manager. */
- private JComponent parent;
-
- /** The panel used for our buttons. */
- private JPanel panel;
-
- /** The currently selected window. */
- private transient FrameContainer selected;
-
- /** The number of buttons per row or column. */
- private int cells = 1;
-
- /** The number of buttons to render per {cell,row}. */
- private int maxButtons = Integer.MAX_VALUE;
-
- /** The width of buttons. */
- private int buttonWidth;
-
- /** Creates a new instance of DummyFrameManager. */
- public ButtonBar() {
- windows = new MapList<FrameContainer, FrameContainer>();
- buttons = new HashMap<FrameContainer, JToggleButton>();
- position = FramemanagerPosition.getPosition(
- IdentityManager.getGlobalConfig().getOption("ui", "framemanagerPosition"));
-
- panel = new JPanel(new GridBagLayout());
- }
-
- /** {@inheritDoc} */
- public void setParent(final JComponent parent) {
- this.parent = parent;
-
- parent.setLayout(new BorderLayout());
- parent.setBorder(BorderFactory.createEmptyBorder(
- UIUtilities.SMALL_BORDER, UIUtilities.SMALL_BORDER,
- UIUtilities.SMALL_BORDER, UIUtilities.SMALL_BORDER));
- parent.add(panel, BorderLayout.NORTH);
-
- buttonWidth = position.isHorizontal() ? 150 : (parent.getWidth() - UIUtilities.SMALL_BORDER * 3) / cells;
-
- if (position.isHorizontal()) {
- maxButtons = parent.getWidth() / (buttonWidth + UIUtilities.SMALL_BORDER * 2);
- }
-
- parent.addComponentListener(this);
- }
-
- /**
- * Removes all buttons from the bar and readds them.
- */
- private void relayout() {
- panel.removeAll();
-
- final GridBagConstraints constraints = new GridBagConstraints();
- constraints.gridx = 0;
- constraints.gridy = 0;
- constraints.insets.set(UIUtilities.SMALL_BORDER,
- UIUtilities.SMALL_BORDER, 0, 0);
-
- for (Map.Entry<FrameContainer, List<FrameContainer>> entry : windows.entrySet()) {
- buttons.get(entry.getKey()).setPreferredSize(new Dimension(buttonWidth, 25));
- buttons.get(entry.getKey()).setMinimumSize(new Dimension(buttonWidth, 25));
- panel.add(buttons.get(entry.getKey()), constraints);
- increment(constraints);
-
- Collections.sort(entry.getValue(), new FrameContainerComparator());
-
- for (FrameContainer child : entry.getValue()) {
- buttons.get(child).setPreferredSize(new Dimension(buttonWidth, 25));
- buttons.get(child).setMinimumSize(new Dimension(buttonWidth, 25));
- panel.add(buttons.get(child), constraints);
- increment(constraints);
- }
- }
- panel.validate();
- }
-
- /**
- * Increments the x and y offsets (where appropriate) of the gridbag
- * constraints.
- *
- * @param constraints The constraints to modify
- */
- public void increment(final GridBagConstraints constraints) {
- if (position.isHorizontal()) {
- constraints.gridx++;
- if (constraints.gridx > maxButtons) {
- constraints.gridy++;
- constraints.gridx = 0;
- }
- } else {
- constraints.gridy++;
- if (constraints.gridy > maxButtons) {
- constraints.gridx++;
- constraints.gridy = 0;
- }
- }
- }
-
- /**
- * Adds a button to the button array with the details from the specified
- * container.
- *
- * @param source The Container to get title/icon info from
- */
- private void addButton(final FrameContainer source) {
- final JToggleButton button = new JToggleButton(source.toString(), source.getIcon());
-
- button.addActionListener(this);
- button.setHorizontalAlignment(SwingConstants.LEFT);
- button.setMargin(new Insets(0, 0, 0, 0));
-
- buttons.put(source, button);
- }
-
- /** {@inheritDoc} */
- public boolean canPositionVertically() {
- return true;
- }
-
- /** {@inheritDoc} */
- public boolean canPositionHorizontally() {
- return true;
- }
-
- /** {@inheritDoc} */
- public void setSelected(final FrameContainer source) {
- if (selected != null && buttons.containsKey(selected)) {
- buttons.get(selected).setSelected(false);
- }
-
- selected = source;
-
- if (buttons.containsKey(source)) {
- buttons.get(source).setSelected(true);
- }
- }
-
- /** {@inheritDoc} */
- public void showNotification(final FrameContainer source, final Color colour) {
- if (buttons.containsKey(source)) {
- buttons.get(source).setForeground(colour);
- }
- }
-
- /** {@inheritDoc} */
- public void clearNotification(final FrameContainer source) {
- showNotification(source, source.getNotification());
- }
-
- /** {@inheritDoc} */
- public void addWindow(final FrameContainer window) {
- windows.add(window);
- addButton(window);
-
- relayout();
- window.addNotificationListener(this);
- window.addSelectionListener(this);
- window.addIconChangeListener(this);
- }
-
- /** {@inheritDoc} */
- public void delWindow(final FrameContainer window) {
- windows.remove(window);
-
- relayout();
- window.removeNotificationListener(this);
- window.removeIconChangeListener(this);
- window.removeSelectionListener(this);
- }
-
- /** {@inheritDoc} */
- public void addWindow(final FrameContainer parent, final FrameContainer window) {
- windows.add(parent, window);
- addButton(window);
-
- relayout();
- window.addNotificationListener(this);
- window.addSelectionListener(this);
- window.addIconChangeListener(this);
- }
-
- /** {@inheritDoc} */
- public void delWindow(final FrameContainer parent, final FrameContainer window) {
- windows.remove(parent, window);
-
- relayout();
- window.removeNotificationListener(this);
- window.removeIconChangeListener(this);
- window.removeSelectionListener(this);
- }
-
- /** {@inheritDoc} */
- public void iconUpdated(final FrameContainer window) {
- buttons.get(window).setIcon(window.getIcon());
- }
-
- /**
- * Called when the user clicks on one of the buttons.
- *
- * @param e The action event associated with this action
- */
- public void actionPerformed(final ActionEvent e) {
- final Window active = Main.getUI().getActiveWindow();
-
- for (Map.Entry<FrameContainer, JToggleButton> entry : buttons.entrySet()) {
- if (entry.getValue().equals(e.getSource())) {
- if (entry.getKey().getFrame().equals(active)) {
- entry.getValue().setSelected(true);
- }
-
- entry.getKey().activateFrame();
- }
- }
- }
-
- /**
- * Called when the parent component is resized.
- *
- * @param e A ComponentEvent corresponding to this event.
- */
- public void componentResized(final ComponentEvent e) {
- buttonWidth = position.isHorizontal() ? 150 : (parent.getWidth() - UIUtilities.SMALL_BORDER * 3) / cells;
-
- if (position.isHorizontal()) {
- maxButtons = parent.getWidth() / (buttonWidth + UIUtilities.SMALL_BORDER * 2);
- }
-
- relayout();
- }
-
- /**
- * Called when the parent component is moved.
- *
- * @param e A ComponentEvent corresponding to this event.
- */
- public void componentMoved(final ComponentEvent e) {
- // Do nothing
- }
-
- /**
- * Called when the parent component is made visible.
- *
- * @param e A ComponentEvent corresponding to this event.
- */
- public void componentShown(final ComponentEvent e) {
- // Do nothing
- }
-
- /**
- * Called when the parent component is made invisible.
- *
- * @param e A ComponentEvent corresponding to this event.
- */
- public void componentHidden(final ComponentEvent e) {
- // Do nothing
- }
-
-
- /** {@inheritDoc} */
- @Override
- public void notificationSet(final Window window, final Color colour) {
- if (buttons.containsKey(window.getContainer())) {
- buttons.get(window.getContainer()).setForeground(colour);
- }
- }
-
- /** {@inheritDoc} */
- @Override
- public void notificationCleared(final Window window) {
- notificationSet(window, window.getContainer().getNotification());
- }
-
- /** {@inheritDoc} */
- @Override
- public void selectionChanged(final Window window) {
- if (selected != null && buttons.containsKey(selected)) {
- buttons.get(selected).setSelected(false);
- }
-
- selected = window.getContainer();
-
- if (buttons.containsKey(window.getContainer())) {
- buttons.get(window.getContainer()).setSelected(true);
- }
- }
-
- /** {@inheritDoc} */
- @Override
- public void iconChanged(final Window window, final Icon icon) {
- buttons.get(window.getContainer()).setIcon(icon);
- }
- }
|