GNU Classpath (0.18) | ||
Frames | No Frames |
1: /* BasicDesktopIconUI.java -- 2: Copyright (C) 2004, 2005 Free Software Foundation, Inc. 3: 4: This file is part of GNU Classpath. 5: 6: GNU Classpath is free software; you can redistribute it and/or modify 7: it under the terms of the GNU General Public License as published by 8: the Free Software Foundation; either version 2, or (at your option) 9: any later version. 10: 11: GNU Classpath is distributed in the hope that it will be useful, but 12: WITHOUT ANY WARRANTY; without even the implied warranty of 13: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14: General Public License for more details. 15: 16: You should have received a copy of the GNU General Public License 17: along with GNU Classpath; see the file COPYING. If not, write to the 18: Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 19: 02110-1301 USA. 20: 21: Linking this library statically or dynamically with other modules is 22: making a combined work based on this library. Thus, the terms and 23: conditions of the GNU General Public License cover the whole 24: combination. 25: 26: As a special exception, the copyright holders of this library give you 27: permission to link this library with independent modules to produce an 28: executable, regardless of the license terms of these independent 29: modules, and to copy and distribute the resulting executable under 30: terms of your choice, provided that you also meet, for each linked 31: independent module, the terms and conditions of the license of that 32: module. An independent module is a module which is not derived from 33: or based on this library. If you modify this library, you may extend 34: this exception to your version of the library, but you are not 35: obligated to do so. If you do not wish to do so, delete this 36: exception statement from your version. */ 37: 38: 39: package javax.swing.plaf.basic; 40: 41: import java.awt.BorderLayout; 42: import java.awt.Color; 43: import java.awt.Component; 44: import java.awt.Dimension; 45: import java.awt.Graphics; 46: import java.awt.Insets; 47: import java.awt.Rectangle; 48: import java.awt.event.ActionEvent; 49: import java.awt.event.ActionListener; 50: import java.awt.event.MouseEvent; 51: import java.beans.PropertyChangeEvent; 52: import java.beans.PropertyChangeListener; 53: import java.beans.PropertyVetoException; 54: 55: import javax.swing.Icon; 56: import javax.swing.JButton; 57: import javax.swing.JComponent; 58: import javax.swing.JDesktopPane; 59: import javax.swing.JInternalFrame; 60: import javax.swing.JInternalFrame.JDesktopIcon; 61: import javax.swing.SwingConstants; 62: import javax.swing.border.Border; 63: import javax.swing.event.MouseInputAdapter; 64: import javax.swing.event.MouseInputListener; 65: import javax.swing.plaf.ComponentUI; 66: import javax.swing.plaf.DesktopIconUI; 67: 68: /** 69: * This class acts as the UI delegate for JDesktopIcons for the Basic look and feel. 70: */ 71: public class BasicDesktopIconUI extends DesktopIconUI 72: { 73: /** 74: * This helper class handles mouse events that occur on the JDesktopIcon. 75: */ 76: public class MouseInputHandler extends MouseInputAdapter 77: { 78: /** The x offset from the MouseEvent coordinates to the top left corner. */ 79: private transient int xOffset; 80: 81: /** The y offset fromt he MouseEvent coordinates to the top left corner. */ 82: private transient int yOffset; 83: 84: /** A cached value of the JDesktopPane that parents this JDesktopIcon. */ 85: private transient JDesktopPane pane; 86: 87: /** 88: * This method is called when the mouse is dragged in the JDesktopIcon. 89: * 90: * @param e The MouseEvent. 91: */ 92: public void mouseDragged(MouseEvent e) 93: { 94: Rectangle b = desktopIcon.getBounds(); 95: 96: moveAndRepaint(desktopIcon, b.x + e.getX() - xOffset, 97: b.y + e.getY() - yOffset, b.width, b.height); 98: } 99: 100: /** 101: * This method is called when the mouse is moved in the JDesktopIcon. 102: * 103: * @param e The MouseEvent. 104: */ 105: public void mouseMoved(MouseEvent e) 106: { 107: // Nothing to do. 108: } 109: 110: /** 111: * This method is called when the mouse is pressed in the JDesktopIcon. 112: * 113: * @param e The MouseEvent. 114: */ 115: public void mousePressed(MouseEvent e) 116: { 117: xOffset = e.getX(); 118: yOffset = e.getY(); 119: pane = frame.getDesktopPane(); 120: if (pane != null) 121: pane.getDesktopManager().beginDraggingFrame(desktopIcon); 122: } 123: 124: /** 125: * This method is called when the mouse is released in the JDesktopIcon. 126: * 127: * @param e The MouseEvent. 128: */ 129: public void mouseReleased(MouseEvent e) 130: { 131: if (pane != null) 132: pane.getDesktopManager().endDraggingFrame(desktopIcon); 133: xOffset = 0; 134: yOffset = 0; 135: } 136: 137: /** 138: * This method moves and repaints the JDesktopIcon to the given bounds. 139: * 140: * @param f The JComponent to move and repaint. 141: * @param newX The new x coordinate. 142: * @param newY The new y coordinate. 143: * @param newWidth The new width. 144: * @param newHeight The new height. 145: */ 146: public void moveAndRepaint(JComponent f, int newX, int newY, int newWidth, 147: int newHeight) 148: { 149: if (pane != null) 150: pane.getDesktopManager().dragFrame(f, newX, newY); 151: else 152: desktopIcon.setBounds(newX, newY, newWidth, newHeight); 153: } 154: } 155: 156: /** 157: * This class acts as the border for the JDesktopIcon. 158: */ 159: private class DesktopIconBorder implements Border 160: { 161: /** The left inset value. */ 162: int left = 10; 163: 164: /** The top inset value. */ 165: int top = 4; 166: 167: /** The right inset value. */ 168: int right = top; 169: 170: /** The bottom inset value. */ 171: int bottom = top; 172: 173: /** 174: * This method returns the insets of the border. 175: * 176: * @param c The Component to find border insets for. 177: * 178: * @return The border insets. 179: */ 180: public Insets getBorderInsets(Component c) 181: { 182: return new Insets(top, left, bottom, right); 183: } 184: 185: /** 186: * This method returns whether the border is opaque. 187: * 188: * @return Whether the border is opaque. 189: */ 190: public boolean isBorderOpaque() 191: { 192: return true; 193: } 194: 195: /** 196: * This method paints the border. 197: * 198: * @param c The Component the border is in. 199: * @param g The Graphics object to paint with. 200: * @param x The x coordinate of the Component. 201: * @param y The y coordinate of the Component. 202: * @param width The width of the Component. 203: * @param height The height of the Component. 204: */ 205: public void paintBorder(Component c, Graphics g, int x, int y, int width, 206: int height) 207: { 208: g.translate(x, y); 209: Color saved = g.getColor(); 210: 211: g.setColor(Color.LIGHT_GRAY); 212: 213: g.fillRect(0, 0, left, height); 214: g.fillRect(0, 0, width, top); 215: g.fillRect(0, height - bottom, width, bottom); 216: g.fillRect(width - right, 0, right, height); 217: 218: g.setColor(Color.BLACK); 219: g.drawRect(0, 0, width - 1, height - 1); 220: 221: int fHeight = height / 4; 222: int hLeft = left / 2; 223: 224: g.setColor(Color.BLACK); 225: g.fillRect(hLeft, fHeight, 2, 2); 226: g.fillRect(hLeft, fHeight * 2, 2, 2); 227: g.fillRect(hLeft, fHeight * 3, 2, 2); 228: 229: g.setColor(saved); 230: g.translate(-x, -y); 231: } 232: } 233: 234: /** The static width and height of the iconSize. */ 235: private static final int iconSize = 16; 236: 237: /** 238: * This class represents the default frame icon when none 239: * is supplied by the JInternalFrame. 240: */ 241: static class InternalFrameDefaultMenuIcon implements Icon 242: { 243: /** 244: * This returns the icon height. 245: * 246: * @return The icon height. 247: */ 248: public int getIconHeight() 249: { 250: return iconSize; 251: } 252: 253: /** 254: * This returns the icon width. 255: * 256: * @return The icon width. 257: */ 258: public int getIconWidth() 259: { 260: return iconSize; 261: } 262: 263: /** 264: * This method paints the icon. 265: * 266: * @param c The Component this icon belongs to. 267: * @param g The Graphics object to paint with. 268: * @param x The x coordinate to paint at. 269: * @param y The y coordinate to paint at. 270: */ 271: public void paintIcon(Component c, Graphics g, int x, int y) 272: { 273: g.translate(x, y); 274: Color saved = g.getColor(); 275: 276: g.setColor(Color.BLUE); 277: g.fillRect(0, 0, iconSize, (int) ((double) iconSize / 3) + 1); 278: 279: g.setColor(Color.WHITE); 280: g.fillRect(0, (int) ((double) iconSize / 3), iconSize, iconSize * 5 / 6); 281: 282: g.setColor(Color.GRAY); 283: g.drawRect(0, 0, iconSize, iconSize); 284: 285: g.setColor(saved); 286: g.translate(-x, -y); 287: } 288: } 289: 290: /** The default JDesktopIcon width. */ 291: private static final int iconWidth = 160; 292: 293: /** The default JDesktopIcon height */ 294: private static final int iconHeight = 35; 295: 296: /** The JDesktopIcon this UI delegate represents. */ 297: protected JDesktopIcon desktopIcon; 298: 299: /** The JInternalFrame associated with the JDesktopIcon. */ 300: protected JInternalFrame frame; 301: 302: /** The MouseListener responsible for reacting to MouseEvents on the JDesktopIcon. */ 303: private transient MouseInputListener mouseHandler; 304: 305: /** The Button in the JDesktopIcon responsible for deiconifying it. 306: * This is package-private to avoid an accessor method. */ 307: transient BoundButton button; 308: 309: /** The PropertyChangeListener listening to the JDesktopIcon. */ 310: private transient PropertyChangeListener propertyHandler; 311: 312: /** The default icon used when no frame icon is given by the JInternalFrame. */ 313: static Icon defaultIcon = new InternalFrameDefaultMenuIcon(); 314: 315: /** 316: * This is a helper class that is used in JDesktopIcon and gives the Button a predetermined size. 317: */ 318: private class BoundButton extends JButton 319: { 320: /** 321: * Creates a new BoundButton object. 322: * 323: * @param title The title of the button. 324: */ 325: public BoundButton(String title) 326: { 327: super(title); 328: } 329: 330: /** 331: * This method returns a standard size (based on the defaults of the JDesktopIcon) and the insets. 332: * 333: * @return The preferred size of the JDesktopIcon. 334: */ 335: public Dimension getPreferredSize() 336: { 337: Insets insets = desktopIcon.getInsets(); 338: return new Dimension(iconWidth - insets.left - insets.right, 339: iconHeight - insets.top - insets.bottom); 340: } 341: 342: /** 343: * This method returns the minimum size of the button. 344: * 345: * @return The minimum size of the button. 346: */ 347: public Dimension getMinimumSize() 348: { 349: return getPreferredSize(); 350: } 351: 352: /** 353: * This method returns the maximum size of the button. 354: * 355: * @return The maximum size of the button. 356: */ 357: public Dimension getMaximumSize() 358: { 359: return getPreferredSize(); 360: } 361: } 362: 363: /** 364: * Creates a new BasicDesktopIconUI object. 365: */ 366: public BasicDesktopIconUI() 367: { 368: } 369: 370: /** 371: * This method creates a new BasicDesktopIconUI for the given JComponent. 372: * 373: * @param c The JComponent to create a UI for. 374: * 375: * @return A new BasicDesktopIconUI. 376: */ 377: public static ComponentUI createUI(JComponent c) 378: { 379: return new BasicDesktopIconUI(); 380: } 381: 382: /** 383: * This method installs the UI for the given JComponent. 384: * 385: * @param c The JComponent to install this UI for. 386: */ 387: public void installUI(JComponent c) 388: { 389: if (c instanceof JDesktopIcon) 390: { 391: desktopIcon = (JDesktopIcon) c; 392: desktopIcon.setLayout(new BorderLayout()); 393: frame = desktopIcon.getInternalFrame(); 394: 395: installDefaults(); 396: installComponents(); 397: installListeners(); 398: 399: desktopIcon.setOpaque(true); 400: } 401: } 402: 403: /** 404: * This method uninstalls the UI for the given JComponent. 405: * 406: * @param c The JComponent to uninstall this UI for. 407: */ 408: public void uninstallUI(JComponent c) 409: { 410: desktopIcon.setOpaque(false); 411: 412: uninstallListeners(); 413: uninstallComponents(); 414: uninstallDefaults(); 415: 416: frame = null; 417: desktopIcon.setLayout(null); 418: desktopIcon = null; 419: } 420: 421: /** 422: * This method installs the necessary sub components for the JDesktopIcon. 423: */ 424: protected void installComponents() 425: { 426: // Try to create a button based on what the frame's 427: // state is currently 428: button = new BoundButton(frame.getTitle()); 429: button.setHorizontalAlignment(SwingConstants.LEFT); 430: button.setHorizontalTextPosition(SwingConstants.TRAILING); 431: 432: Icon use = frame.getFrameIcon(); 433: if (use == null) 434: use = defaultIcon; 435: button.setIcon(use); 436: 437: desktopIcon.add(button, SwingConstants.CENTER); 438: } 439: 440: /** 441: * This method uninstalls the sub components for the JDesktopIcon. 442: */ 443: protected void uninstallComponents() 444: { 445: desktopIcon.remove(button); 446: 447: button = null; 448: } 449: 450: /** 451: * This method installs the listeners needed by this UI. 452: */ 453: protected void installListeners() 454: { 455: mouseHandler = createMouseInputListener(); 456: 457: desktopIcon.addMouseMotionListener(mouseHandler); 458: desktopIcon.addMouseListener(mouseHandler); 459: 460: propertyHandler = new PropertyChangeListener() 461: { 462: public void propertyChange(PropertyChangeEvent e) 463: { 464: if (e.getPropertyName().equals(JInternalFrame.TITLE_PROPERTY)) 465: button.setText(desktopIcon.getInternalFrame().getTitle()); 466: else if (e.getPropertyName().equals(JInternalFrame.FRAME_ICON_PROPERTY)) 467: { 468: Icon use = desktopIcon.getInternalFrame().getFrameIcon(); 469: if (use == null) 470: use = defaultIcon; 471: button.setIcon(use); 472: } 473: desktopIcon.revalidate(); 474: desktopIcon.repaint(); 475: } 476: }; 477: frame.addPropertyChangeListener(propertyHandler); 478: 479: button.addActionListener(new ActionListener() 480: { 481: public void actionPerformed(ActionEvent e) 482: { 483: deiconize(); 484: } 485: }); 486: } 487: 488: /** 489: * This method uninstalls the listeners needed by the UI. 490: */ 491: protected void uninstallListeners() 492: { 493: // button is nulled so no need to remove it. 494: 495: frame.removePropertyChangeListener(propertyHandler); 496: propertyHandler = null; 497: 498: desktopIcon.removeMouseMotionListener(mouseHandler); 499: desktopIcon.removeMouseListener(mouseHandler); 500: } 501: 502: /** 503: * This method installs the defaults for the JDesktopIcon. 504: */ 505: protected void installDefaults() 506: { 507: // FIXME: Move border to defaults. 508: desktopIcon.setBorder(new DesktopIconBorder()); 509: } 510: 511: /** 512: * This method uninstalls the defaults for the JDesktopIcon. 513: */ 514: protected void uninstallDefaults() 515: { 516: desktopIcon.setBorder(null); 517: } 518: 519: /** 520: * This method creates a new MouseInputListener for the JDesktopIcon. 521: * 522: * @return A new MouseInputListener. 523: */ 524: protected MouseInputListener createMouseInputListener() 525: { 526: return new MouseInputHandler(); 527: } 528: 529: /** 530: * This method returns the preferred size for the given JComponent. 531: * 532: * @param c The JComponent to find a preferred size for. 533: * 534: * @return The preferred size. 535: */ 536: public Dimension getPreferredSize(JComponent c) 537: { 538: return new Dimension(iconWidth, iconHeight); 539: } 540: 541: /** 542: * This method returns the minimum size for the given JComponent. 543: * 544: * @param c The JComponent to find a minimum size for. 545: * 546: * @return The minimum size. 547: */ 548: public Dimension getMinimumSize(JComponent c) 549: { 550: return getPreferredSize(c); 551: } 552: 553: /** 554: * This method returns the maximum size for the given JComponent. 555: * 556: * @param c The JComponent to find a maximum size for. 557: * 558: * @return The maximum size. 559: */ 560: public Dimension getMaximumSize(JComponent c) 561: { 562: return getPreferredSize(c); 563: } 564: 565: /** 566: * This method returns the insets of the given JComponent. 567: * 568: * @param c The JComponent to find insets for. 569: * 570: * @return The insets of the given JComponent. 571: */ 572: public Insets getInsets(JComponent c) 573: { 574: return c.getInsets(); 575: } 576: 577: /** 578: * This method deiconizes the JInternalFrame associated with the JDesktopIcon. 579: */ 580: public void deiconize() 581: { 582: try 583: { 584: frame.setIcon(false); 585: } 586: catch (PropertyVetoException pve) 587: { 588: } 589: } 590: }
GNU Classpath (0.18) |