Source for javax.swing.plaf.metal.MetalIconFactory

   1: /* MetalIconFactory.java --
   2:    Copyright (C) 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.metal;
  40: 
  41: import java.awt.Color;
  42: import java.awt.Component;
  43: import java.awt.Graphics;
  44: import java.io.Serializable;
  45: 
  46: import javax.swing.AbstractButton;
  47: import javax.swing.Icon;
  48: import javax.swing.JCheckBox;
  49: import javax.swing.JCheckBoxMenuItem;
  50: import javax.swing.JFileChooser;
  51: import javax.swing.JInternalFrame;
  52: import javax.swing.JRadioButton;
  53: import javax.swing.JRadioButtonMenuItem;
  54: import javax.swing.JSlider;
  55: import javax.swing.SwingConstants;
  56: import javax.swing.UIManager;
  57: import javax.swing.plaf.UIResource;
  58: 
  59: 
  60: /**
  61:  * Creates icons for the {@link MetalLookAndFeel}.
  62:  */
  63: public class MetalIconFactory implements Serializable 
  64: {
  65: 
  66:   /** A constant representing "dark". */
  67:   public static final boolean DARK = false;
  68:     
  69:   /** A constant representing "light". */
  70:   public static final boolean LIGHT = true;
  71:     
  72:   /**
  73:    * An icon displayed for {@link JCheckBoxMenuItem} components.
  74:    */
  75:   private static class CheckBoxMenuItemIcon implements Icon, Serializable 
  76:   {
  77:     /**
  78:      * Creates a new icon instance.
  79:      */
  80:     public CheckBoxMenuItemIcon() 
  81:     {
  82:       // Nothing to do here.
  83:     }
  84:       
  85:     /**
  86:      * Returns the width of the icon, in pixels.
  87:      * 
  88:      * @return The width of the icon (10 pixels).
  89:      */
  90:     public int getIconWidth() 
  91:     {
  92:       return 10;
  93:     }
  94:     
  95:     /**
  96:      * Returns the height of the icon, in pixels.
  97:      * 
  98:      * @return The height of the icon (10 pixels).
  99:      */
 100:     public int getIconHeight() 
 101:     {
 102:       return 10;
 103:     }
 104:     
 105:     /**
 106:      * Paints the icon.
 107:      * 
 108:      * @param c  the component.
 109:      * @param g  the graphics device.
 110:      * @param x  the x-coordinate.
 111:      * @param y  the y-coordinate.
 112:      */
 113:     public void paintIcon(Component c, Graphics g, int x, int y) 
 114:     {
 115:       JCheckBoxMenuItem item = (JCheckBoxMenuItem) c;
 116:         
 117:       if (item.isArmed())
 118:         g.setColor(MetalLookAndFeel.getBlack());
 119:       else
 120:         g.setColor(MetalLookAndFeel.getControlDarkShadow());
 121:       g.drawLine(x, y, x + 8, y);
 122:       g.drawLine(x, y + 1, x, y + 8);
 123:       g.drawLine(x + 2, y + 8, x + 8, y + 8);
 124:       g.drawLine(x + 8, y + 2, x + 8, y + 7);
 125:       
 126:       g.setColor(MetalLookAndFeel.getWhite());
 127:       g.drawLine(x + 1, y + 1, x + 7, y + 1);
 128:       g.drawLine(x + 1, y + 2, x + 1, y + 7);
 129:       g.drawLine(x + 1, y + 9, x + 9, y + 9);
 130:       g.drawLine(x + 9, y + 1, x + 9, y + 8);
 131: 
 132:       // if the item is selected, we should draw a tick
 133:       if (item.isSelected())
 134:       {
 135:         g.setColor(MetalLookAndFeel.getBlack());
 136:         g.fillRect(x + 2, y + 2, 2, 5);
 137:         for (int i = 0; i < 6; i++)
 138:           g.drawLine(x + 8 - i, y + i, x + 9 - i, y + i);
 139:       }
 140: 
 141:     }        
 142:   }
 143: 
 144:   /**
 145:    * An icon used for the "detail view" button on a {@link JFileChooser} under
 146:    * the {@link MetalLookAndFeel}.
 147:    * 
 148:    * @see MetalIconFactory#getFileChooserDetailViewIcon()
 149:    */
 150:   private static class FileChooserDetailViewIcon implements Icon, Serializable
 151:   {
 152: 
 153:     /**
 154:      * Creates a new icon.
 155:      */
 156:     public FileChooserDetailViewIcon() 
 157:     {
 158:       // Nothing to do here.
 159:     }
 160:       
 161:     /**
 162:      * Returns the width of the icon, in pixels.
 163:      * 
 164:      * @return The width of the icon.
 165:      */
 166:     public int getIconWidth() 
 167:     {
 168:       return 18;
 169:     }
 170:     
 171:     /**
 172:      * Returns the height of the icon, in pixels.
 173:      * 
 174:      * @return The height of the icon.
 175:      */
 176:     public int getIconHeight() 
 177:     {
 178:       return 18;
 179:     }
 180:     
 181:     /**
 182:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 183:      * 
 184:      * @param c  the component (ignored).
 185:      * @param g  the graphics device.
 186:      * @param x  the x-coordinate for the top-left of the icon.
 187:      * @param y  the y-coordinate for the top-left of the icon.
 188:      */
 189:     public void paintIcon(Component c, Graphics g, int x, int y) 
 190:     {
 191:       Color savedColor = g.getColor();
 192:       g.setColor(MetalLookAndFeel.getBlack());
 193: 
 194:       // file 1 outline
 195:       g.drawLine(x + 2, y + 2, x + 5, y + 2);
 196:       g.drawLine(x + 6, y + 3, x + 6, y + 7);
 197:       g.drawLine(x + 2, y + 7, x + 6, y + 7);
 198:       g.drawLine(x + 2, y + 2, x + 2, y + 7);
 199:       
 200:       // file 2 outline
 201:       g.drawLine(x + 2, y + 10, x + 5, y + 10);
 202:       g.drawLine(x + 6, y + 11, x + 6, y + 15);
 203:       g.drawLine(x + 2, y + 15, x + 6, y + 15);
 204:       g.drawLine(x + 2, y + 10, x + 2, y + 15);
 205: 
 206:       // detail lines
 207:       g.drawLine(x + 8, y + 5, x + 15, y + 5);
 208:       g.drawLine(x + 8, y + 13, x + 15, y + 13);
 209:       
 210:       // fill files
 211:       g.setColor(MetalLookAndFeel.getPrimaryControl());
 212:       g.fillRect(x + 3, y + 3, 3, 4);
 213:       g.fillRect(x + 3, y + 11, 3, 4);
 214:       
 215:       // highlight files
 216:       g.setColor(MetalLookAndFeel.getPrimaryControlHighlight());
 217:       g.drawLine(x + 4, y + 4, x + 4, y + 5);
 218:       g.drawLine(x + 4, y + 12, x + 4, y + 13);
 219:       
 220:       g.setColor(savedColor);
 221:     }        
 222:   }
 223: 
 224:   /**
 225:    * An icon used for the "home folder" button on a {@link JFileChooser} under
 226:    * the {@link MetalLookAndFeel}.
 227:    * 
 228:    * @see MetalIconFactory#getFileChooserHomeFolderIcon()
 229:    */
 230:   private static class FileChooserHomeFolderIcon implements Icon, Serializable
 231:   {
 232: 
 233:     /**
 234:      * Creates a new icon.
 235:      */
 236:     public FileChooserHomeFolderIcon() 
 237:     {
 238:       // Nothing to do here.
 239:     }
 240: 
 241:     /**
 242:      * Returns the width of the icon, in pixels.
 243:      * 
 244:      * @return The width of the icon.
 245:      */
 246:     public int getIconWidth() 
 247:     {
 248:       return 18;
 249:     }
 250:     
 251:     /**
 252:      * Returns the height of the icon, in pixels.
 253:      * 
 254:      * @return The height of the icon.
 255:      */
 256:     public int getIconHeight() 
 257:     {
 258:       return 18;
 259:     }
 260:     
 261:     /**
 262:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 263:      * 
 264:      * @param c  the component (ignored).
 265:      * @param g  the graphics device.
 266:      * @param x  the x-coordinate for the top-left of the icon.
 267:      * @param y  the y-coordinate for the top-left of the icon.
 268:      */
 269:     public void paintIcon(Component c, Graphics g, int x, int y) 
 270:     {   
 271:       Color savedColor = g.getColor();
 272:       g.setColor(MetalLookAndFeel.getBlack());
 273:       
 274:       // roof
 275:       g.drawLine(x + 1, y + 8, x + 8, y + 1);
 276:       g.drawLine(x + 8, y + 1, x + 15, y + 8);
 277:       
 278:       // base of house
 279:       g.drawLine(x + 3, y + 6, x + 3, y + 15);
 280:       g.drawLine(x + 3, y + 15, x + 13, y + 15);
 281:       g.drawLine(x + 13, y + 6, x + 13, y + 15);
 282:       
 283:       // door frame
 284:       g.drawLine(x + 6, y + 9, x + 6, y + 15);
 285:       g.drawLine(x + 6, y + 9, x + 10, y + 9);
 286:       g.drawLine(x + 10, y + 9, x + 10, y + 15);
 287:       
 288:       // chimney
 289:       g.drawLine(x + 11, y + 2, x + 11, y + 4);
 290:       g.drawLine(x + 12, y + 2, x + 12, y + 5);
 291:       
 292:       g.setColor(MetalLookAndFeel.getControlDarkShadow());
 293:       
 294:       // roof paint
 295:       int xx = x + 8;
 296:       for (int i = 0; i < 4; i++)
 297:         g.drawLine(xx - i, y + 2 + i, xx + i, y + 2 + i);
 298:       g.fillRect(x + 4, y + 6, 9, 2);
 299:       
 300:       // door knob
 301:       g.drawLine(x + 9, y + 12, x + 9, y + 12);
 302:       
 303:       // house paint
 304:       g.setColor(MetalLookAndFeel.getPrimaryControl());
 305:       g.drawLine(x + 4, y + 8, x + 12, y + 8);
 306:       g.fillRect(x + 4, y + 9, 2, 6);
 307:       g.fillRect(x + 11, y + 9, 2, 6);
 308:       
 309:       g.setColor(savedColor);
 310:     }        
 311:   }
 312:     
 313:   /**
 314:    * An icon used for the "list view" button on a {@link JFileChooser} under
 315:    * the {@link MetalLookAndFeel}.
 316:    * 
 317:    * @see MetalIconFactory#getFileChooserListViewIcon()
 318:    */
 319:   private static class FileChooserListViewIcon implements Icon, Serializable 
 320:   {
 321:     /**
 322:      * Creates a new icon.
 323:      */
 324:     public FileChooserListViewIcon() 
 325:     {
 326:       // Nothing to do here.
 327:     }
 328:     
 329:     /**
 330:      * Returns the width of the icon, in pixels.
 331:      * 
 332:      * @return The width of the icon.
 333:      */
 334:     public int getIconWidth() 
 335:     {
 336:       return 18;
 337:     }
 338:     
 339:     /**
 340:      * Returns the height of the icon, in pixels.
 341:      * 
 342:      * @return The height of the icon.
 343:      */
 344:     public int getIconHeight() 
 345:     {
 346:       return 18;
 347:     }
 348:     
 349:     /**
 350:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 351:      * 
 352:      * @param c  the component (ignored).
 353:      * @param g  the graphics device.
 354:      * @param x  the x-coordinate for the top-left of the icon.
 355:      * @param y  the y-coordinate for the top-left of the icon.
 356:      */
 357:     public void paintIcon(Component c, Graphics g, int x, int y) 
 358:     {
 359:       Color savedColor = g.getColor();
 360:       g.setColor(MetalLookAndFeel.getBlack());
 361: 
 362:       // file 1 outline
 363:       g.drawLine(x + 2, y + 2, x + 5, y + 2);
 364:       g.drawLine(x + 6, y + 3, x + 6, y + 7);
 365:       g.drawLine(x + 2, y + 7, x + 6, y + 7);
 366:       g.drawLine(x + 2, y + 2, x + 2, y + 7);
 367:       
 368:       // file 2 outline
 369:       g.drawLine(x + 2, y + 10, x + 5, y + 10);
 370:       g.drawLine(x + 6, y + 11, x + 6, y + 15);
 371:       g.drawLine(x + 2, y + 15, x + 6, y + 15);
 372:       g.drawLine(x + 2, y + 10, x + 2, y + 15);
 373:       
 374:       // file 3 outline
 375:       g.drawLine(x + 10, y + 2, x + 13, y + 2);
 376:       g.drawLine(x + 14, y + 3, x + 14, y + 7);
 377:       g.drawLine(x + 10, y + 7, x + 14, y + 7);
 378:       g.drawLine(x + 10, y + 2, x + 10, y + 7);
 379:       
 380:       // file 4 outline
 381:       g.drawLine(x + 10, y + 10, x + 13, y + 10);
 382:       g.drawLine(x + 14, y + 11, x + 14, y + 15);
 383:       g.drawLine(x + 10, y + 15, x + 14, y + 15);
 384:       g.drawLine(x + 10, y + 10, x + 10, y + 15);
 385:       
 386:       g.drawLine(x + 8, y + 5, x + 8, y + 5);
 387:       g.drawLine(x + 8, y + 13, x + 8, y + 13);
 388:       g.drawLine(x + 16, y + 5, x + 16, y + 5);
 389:       g.drawLine(x + 16, y + 13, x + 16, y + 13);
 390:       
 391:       // fill files
 392:       g.setColor(MetalLookAndFeel.getPrimaryControl());
 393:       g.fillRect(x + 3, y + 3, 3, 4);
 394:       g.fillRect(x + 3, y + 11, 3, 4);
 395:       g.fillRect(x + 11, y + 3, 3, 4);
 396:       g.fillRect(x + 11, y + 11, 3, 4);
 397:       
 398:       // highlight files
 399:       g.setColor(MetalLookAndFeel.getPrimaryControlHighlight());
 400:       g.drawLine(x + 4, y + 4, x + 4, y + 5);
 401:       g.drawLine(x + 4, y + 12, x + 4, y + 13);
 402:       g.drawLine(x + 12, y + 4, x + 12, y + 5);
 403:       g.drawLine(x + 12, y + 12, x + 12, y + 13);
 404: 
 405:       g.setColor(savedColor);
 406:     }        
 407:   }
 408:     
 409:   /**
 410:    * An icon used for the "new folder" button on a {@link JFileChooser} under
 411:    * the {@link MetalLookAndFeel}.
 412:    * 
 413:    * @see MetalIconFactory#getFileChooserNewFolderIcon()
 414:    */
 415:   private static class FileChooserNewFolderIcon  implements Icon, Serializable
 416:   {
 417:     /** 
 418:      * Creates a new icon.
 419:      */
 420:     public FileChooserNewFolderIcon() 
 421:     {
 422:       // Nothing to do here.
 423:     }
 424:     
 425:     /**
 426:      * Returns the width of the icon, in pixels.
 427:      * 
 428:      * @return The width of the icon.
 429:      */
 430:     public int getIconWidth() 
 431:     {
 432:       return 18;
 433:     }
 434:     
 435:     /**
 436:      * Returns the height of the icon, in pixels.
 437:      * 
 438:      * @return The height of the icon.
 439:      */
 440:     public int getIconHeight() 
 441:     {
 442:       return 18;
 443:     }
 444:     
 445:     /**
 446:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 447:      * 
 448:      * @param c  the component (ignored).
 449:      * @param g  the graphics device.
 450:      * @param x  the x-coordinate for the top-left of the icon.
 451:      * @param y  the y-coordinate for the top-left of the icon.
 452:      */
 453:     public void paintIcon(Component c, Graphics g, int x, int y) 
 454:     {      
 455:       Color savedColor = g.getColor();
 456:       g.setColor(MetalLookAndFeel.getBlack());
 457:       
 458:       g.drawLine(x + 2, y + 5, x + 9, y + 5);
 459:       g.drawLine(x + 10, y + 6, x + 15, y + 6);
 460:       g.drawLine(x + 15, y + 5, x + 15, y + 14);
 461:       g.drawLine(x + 2, y + 14, x + 15, y + 14);
 462:       g.drawLine(x + 1, y + 6, x + 1, y + 14);
 463:       
 464:       g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
 465:       g.drawLine(x + 11, y + 3, x + 15, y + 3);
 466:       g.drawLine(x + 10, y + 4, x + 15, y + 4);
 467:       
 468:       g.setColor(MetalLookAndFeel.getPrimaryControl());
 469:       g.fillRect(x + 3, y + 7, 7, 7);
 470:       g.fillRect(x + 10, y + 8, 5, 6);
 471:       g.drawLine(x + 10, y + 5, x + 14, y + 5);
 472:       
 473:       g.setColor(MetalLookAndFeel.getPrimaryControlHighlight());
 474:       g.drawLine(x + 10, y + 7, x + 14, y + 7);
 475:       g.drawLine(x + 2, y + 6, x + 9, y + 6);
 476:       g.drawLine(x + 2, y + 6, x + 2, y + 13);
 477:       g.setColor(savedColor);
 478:     }        
 479:   }
 480: 
 481:   /**
 482:    * An icon used for the "up folder" button on a {@link JFileChooser} under
 483:    * the {@link MetalLookAndFeel}.
 484:    * 
 485:    * @see MetalIconFactory#getFileChooserNewFolderIcon()
 486:    */
 487:   private static class FileChooserUpFolderIcon extends FileChooserNewFolderIcon
 488:     implements Icon, Serializable 
 489:   {
 490:     /**
 491:      * Creates a new icon.
 492:      */
 493:     public FileChooserUpFolderIcon() 
 494:     {
 495:       // Nothing to do here.
 496:     }
 497:     
 498:     /**
 499:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 500:      * 
 501:      * @param c  the component (ignored).
 502:      * @param g  the graphics device.
 503:      * @param x  the x-coordinate for the top-left of the icon.
 504:      * @param y  the y-coordinate for the top-left of the icon.
 505:      */
 506:     public void paintIcon(Component c, Graphics g, int x, int y) 
 507:     {
 508:       Color savedColor = g.getColor();
 509: 
 510:       // draw the folder
 511:       super.paintIcon(c, g, x, y);
 512:       
 513:       // now draw the up arrow
 514:       g.setColor(MetalLookAndFeel.getBlack());
 515:       g.drawLine(x + 8, y + 9, x + 8, y + 16);
 516:       int xx = x + 8;
 517:       for (int i = 0; i < 4; i++)
 518:         g.drawLine(xx - i, y + 9 + i, xx + i, y + 9 + i);
 519:       g.setColor(savedColor);
 520:     }        
 521:   }
 522: 
 523:   /**
 524:    * An icon representing a file (drawn as a piece of paper with the top-right
 525:    * corner turned down).
 526:    */
 527:   public static class FileIcon16 implements Icon, Serializable 
 528:   {
 529:     /**
 530:      * Returns the width of the icon, in pixels.
 531:      * 
 532:      * @return The width of the icon.
 533:      */
 534:     public int getIconWidth() 
 535:     {
 536:       return 16;
 537:     }
 538: 
 539:     /**
 540:      * Returns the height of the icon, in pixels.  The height returned is 
 541:      * <code>16</code> plus the value returned by 
 542:      * {@link #getAdditionalHeight()}.
 543:      * 
 544:      * @return The height of the icon.
 545:      */
 546:     public int getIconHeight() 
 547:     {
 548:       return 16 + getAdditionalHeight();
 549:     }
 550:     
 551:     /**
 552:      * Paints the icon at the location (x, y).
 553:      * 
 554:      * @param c  the component.
 555:      * @param g  the graphics context.
 556:      * @param x  the x coordinate.
 557:      * @param y  the y coordinate.
 558:      */
 559:     public void paintIcon(Component c, Graphics g, int x, int y) 
 560:     {
 561:       // TODO: pick up appropriate UI colors
 562:       g.setColor(Color.black);
 563:       g.drawLine(x, y, x + 9, y);            
 564:       g.drawLine(x, y + 1, x, y + 15);            
 565:       g.drawLine(x, y + 15, x + 12, y + 15);            
 566:       g.drawLine(x + 12, y + 15, x + 12, y + 6);            
 567:       g.drawLine(x + 12, y + 6, x + 9, y);           
 568: 
 569:       g.drawLine(x + 7, y + 2, x + 11, y + 6);
 570:       g.drawLine(x + 8, y + 1, x + 9, y + 1);
 571: 
 572:       g.setColor(new Color(204, 204, 255));
 573:       g.drawLine(x + 1, y + 1, x + 7, y + 1);            
 574:       g.drawLine(x + 1, y + 1, x + 1, y + 14);            
 575:       g.drawLine(x + 1, y + 14, x + 11, y + 14);            
 576:       g.drawLine(x + 11, y + 14, x + 11, y + 7);            
 577:       g.drawLine(x + 8, y + 2, x + 10, y + 4);
 578:     }
 579:     
 580:     /**
 581:      * Returns the additional height for the icon.  The 
 582:      * {@link #getIconHeight()} method adds this value to the icon height it
 583:      * returns.  Subclasses can override this method to adjust the icon height.
 584:      * 
 585:      * @return The additional height (<code>0</code> unless overridden).
 586:      */
 587:     public int getAdditionalHeight() 
 588:     {
 589:       return 0;
 590:     }
 591:         
 592:     /**
 593:      * Returns the shift (???).
 594:      * 
 595:      * @return The shift.
 596:      */
 597:     public int getShift() 
 598:     {
 599:       return 0;
 600:     }
 601:         
 602:   }
 603:     
 604:   /**
 605:    * An icon representing a folder.
 606:    */
 607:   public static class FolderIcon16 implements Icon, Serializable 
 608:   {
 609:     /**
 610:      * Returns the width of the icon, in pixels.
 611:      * 
 612:      * @return The width of the icon.
 613:      */
 614:     public int getIconWidth() {
 615:       return 16;
 616:     }
 617:     
 618:     /**
 619:      * Returns the height of the icon, in pixels.  The height returned is 
 620:      * <code>16</code> plus the value returned by 
 621:      * {@link #getAdditionalHeight()}.
 622:      * 
 623:      * @return The height of the icon.
 624:      */
 625:     public int getIconHeight() 
 626:     {
 627:       return 16 + getAdditionalHeight();
 628:     }
 629: 
 630:     /**
 631:      * Paints the icon at the location (x, y).
 632:      * 
 633:      * @param c  the component.
 634:      * @param g  the graphics device.
 635:      * @param x  the x coordinate.
 636:      * @param y  the y coordinate.
 637:      */
 638:     public void paintIcon(Component c, Graphics g, int x, int y) 
 639:     {
 640:       // TODO: pick up appropriate UI colors
 641:       g.setColor(Color.black);
 642:       g.drawLine(x, y + 3, x, y + 12);
 643:       g.drawLine(x, y + 12, x + 15, y + 12);
 644:       g.drawLine(x + 15, y + 12, x + 15, y + 2);
 645:       g.drawLine(x + 14, y + 3, x + 9, y + 3);
 646:       g.drawLine(x + 8, y + 2, x + 1, y + 2);
 647:       g.setColor(new Color(204, 204, 255));
 648:       g.fillRect(x + 2, y + 4, 7, 8);
 649:       g.fillRect(x + 9, y + 5, 6, 7);
 650:       g.setColor(new Color(102, 102, 153));
 651:       g.drawLine(x + 9, y + 2, x + 14, y + 2);
 652:       g.setColor(new Color(50, 50, 120));
 653:       g.drawLine(x + 9, y + 1, x + 15, y + 1);
 654:       g.drawLine(x + 10, y, x + 15, y);
 655:     }
 656:     
 657:     /**
 658:      * Returns the additional height for the icon.  The 
 659:      * {@link #getIconHeight()} method adds this value to the icon height it
 660:      * returns.  Subclasses can override this method to adjust the icon height.
 661:      * 
 662:      * @return The additional height (<code>0</code> unless overridden).
 663:      */
 664:     public int getAdditionalHeight() 
 665:     {
 666:       return 0;
 667:     }
 668:     
 669:     /**
 670:      * Returns the shift (???).
 671:      * 
 672:      * @return The shift.
 673:      */
 674:     public int getShift() 
 675:     {
 676:       return 0;
 677:     }
 678:         
 679:   }
 680: 
 681:   /**
 682:    * An icon used by the {@link MetalInternalFrameUI} class when the frame
 683:    * is displayed as a palette.
 684:    * 
 685:    * @since 1.3
 686:    */
 687:   public static class PaletteCloseIcon
 688:     implements Icon, Serializable, UIResource
 689:   {
 690:     /**
 691:      * Returns the width of the icon, in pixels.
 692:      * 
 693:      * @return The width of the icon.
 694:      */
 695:     public int getIconWidth() 
 696:     {
 697:       return 7;
 698:     }
 699:     
 700:     /**
 701:      * Returns the height of the icon, in pixels.
 702:      * 
 703:      * @return The height of the icon.
 704:      */
 705:     public int getIconHeight() 
 706:     {
 707:       return 7;
 708:     }
 709:     
 710:     /**
 711:      * Paints the icon using colors from the {@link MetalLookAndFeel}.
 712:      * 
 713:      * @param c  the component (ignored).
 714:      * @param g  the graphics device.
 715:      * @param x  the x-coordinate for the top-left of the icon.
 716:      * @param y  the y-coordinate for the top-left of the icon.
 717:      */
 718:     public void paintIcon(Component c, Graphics g, int x, int y) 
 719:     {
 720:       Color savedColor = g.getColor();
 721:       AbstractButton button = (AbstractButton) c;
 722:       if (button.getModel().isPressed())
 723:         g.setColor(MetalLookAndFeel.getBlack());
 724:       else
 725:         g.setColor(MetalLookAndFeel.getControlDarkShadow());
 726:       g.fillRect(x + 2, y + 2, 3, 3);
 727:       g.drawLine(x + 1, y, x + 1, y + 2);
 728:       g.drawLine(x, y + 1, x + 2, y + 1);
 729:       g.drawLine(x + 5, y, x + 5, y + 2);
 730:       g.drawLine(x + 4, y + 1, x + 6, y + 1);
 731:       g.drawLine(x + 1, y + 4, x + 1, y + 6);
 732:       g.drawLine(x, y + 5, x + 2, y + 5);
 733:       g.drawLine(x + 5, y + 4, x + 5, y + 6);
 734:       g.drawLine(x + 4, y + 5, x + 6, y + 5);
 735:       g.setColor(MetalLookAndFeel.getControlHighlight());
 736:       g.drawLine(x + 2, y + 6, x + 3, y + 5);
 737:       g.drawLine(x + 5, y + 3, x + 6, y + 2);
 738:       g.drawLine(x + 6, y + 6, x + 6, y + 6);
 739:       g.setColor(savedColor);
 740:     }        
 741:   }
 742:   
 743:   /**
 744:    * An {@link Icon} implementation for {@link JCheckBox}es in the
 745:    * Metal Look &amp; Feel.
 746:    *
 747:    * @author Roman Kennke (roman@kennke.org)
 748:    */
 749:   static class RadioButtonIcon implements Icon, UIResource, Serializable
 750:   {
 751: 
 752:     /**
 753:      * Returns the width of the icon in pixels.
 754:      *
 755:      * @return the width of the icon in pixels
 756:      */
 757:     public int getIconWidth()
 758:     {
 759:       return 13;
 760:     }
 761: 
 762:     /**
 763:      * Returns the height of the icon in pixels.
 764:      *
 765:      * @return the height of the icon in pixels
 766:      */
 767:     public int getIconHeight()
 768:     {
 769:       return 13;
 770:     }
 771: 
 772:     /**
 773:      * Paints the icon, taking into account whether or not the component is
 774:      * enabled, selected and/or armed.
 775:      *
 776:      * @param c the Component to draw on (must be an instance of 
 777:      *          {@link JRadioButton})
 778:      * @param g the Graphics context to draw with
 779:      * @param x the X position
 780:      * @param y the Y position
 781:      */
 782:     public void paintIcon(Component c, Graphics g, int x, int y) 
 783:     {
 784:       if (UIManager.get("RadioButton.gradient") != null)
 785:         MetalUtils.paintGradient(g, x, y, getIconWidth(), getIconHeight(),
 786:                               SwingConstants.VERTICAL, "RadioButton.gradient");
 787: 
 788:       Color savedColor = g.getColor();
 789:       JRadioButton b = (JRadioButton) c;
 790:       
 791:       // draw outer circle
 792:       if (b.isEnabled())
 793:         g.setColor(MetalLookAndFeel.getControlDarkShadow());
 794:       else
 795:         g.setColor(MetalLookAndFeel.getControlDisabled());
 796:       g.drawLine(x + 2, y + 1, x + 3, y + 1);
 797:       g.drawLine(x + 4, y, x + 7, y);
 798:       g.drawLine(x + 8, y + 1, x + 9, y + 1);
 799:       g.drawLine(x + 10, y + 2, x + 10, y + 3);
 800:       g.drawLine(x + 11, y + 4, x + 11, y + 7);
 801:       g.drawLine(x + 10, y + 8, x + 10, y + 9);
 802:       g.drawLine(x + 8, y + 10, x + 9, y + 10);
 803:       g.drawLine(x + 4, y + 11, x + 7, y + 11);
 804:       g.drawLine(x + 2, y + 10, x + 3, y + 10);
 805:       g.drawLine(x + 1, y + 9, x + 1, y + 8);
 806:       g.drawLine(x, y + 7, x, y + 4);
 807:       g.drawLine(x + 1, y + 2, x + 1, y + 3);
 808: 
 809:       if (b.getModel().isArmed())
 810:         {
 811:           g.setColor(MetalLookAndFeel.getControlShadow());
 812:           g.drawLine(x + 4, y + 1, x + 7, y + 1);
 813:           g.drawLine(x + 4, y + 10, x + 7, y + 10);
 814:           g.drawLine(x + 1, y + 4, x + 1, y + 7);
 815:           g.drawLine(x + 10, y + 4, x + 10, y + 7);
 816:           g.fillRect(x + 2, y + 2, 8, 8);
 817:         }
 818:       else 
 819:         {
 820:           // only draw inner highlight if not filled
 821:           if (b.isEnabled())
 822:             {
 823:               g.setColor(MetalLookAndFeel.getWhite());
 824:           
 825:               g.drawLine(x + 2, y + 8, x + 2, y + 9);
 826:               g.drawLine(x + 1, y + 4, x + 1, y + 7);
 827:               g.drawLine(x + 2, y + 2, x + 2, y + 3);
 828:               g.drawLine(x + 3, y + 2, x + 3, y + 2);
 829:               g.drawLine(x + 4, y + 1, x + 7, y + 1);
 830:               g.drawLine(x + 8, y + 2, x + 9, y + 2);
 831:             }
 832:         }
 833: 
 834:       // draw outer highlight
 835:       if (b.isEnabled())
 836:         {
 837:           g.setColor(MetalLookAndFeel.getWhite());
 838:           
 839:           // outer
 840:           g.drawLine(x + 10, y + 1, x + 10, y + 1);
 841:           g.drawLine(x + 11, y + 2, x + 11, y + 3);
 842:           g.drawLine(x + 12, y + 4, x + 12, y + 7);
 843:           g.drawLine(x + 11, y + 8, x + 11, y + 9);
 844:           g.drawLine(x + 10, y + 10, x + 10, y + 10);
 845:           g.drawLine(x + 8, y + 11, x + 9, y + 11);
 846:           g.drawLine(x + 4, y + 12, x + 7, y + 12);
 847:           g.drawLine(x + 2, y + 11, x + 3, y + 11);
 848:         }
 849:       
 850:       if (b.isSelected())
 851:         {
 852:           if (b.isEnabled())
 853:             g.setColor(MetalLookAndFeel.getBlack());
 854:           else
 855:             g.setColor(MetalLookAndFeel.getControlDisabled());
 856:           g.drawLine(x + 4, y + 3, x + 7, y + 3);
 857:           g.fillRect(x + 3, y + 4, 6, 4);
 858:           g.drawLine(x + 4, y + 8, x + 7, y + 8);
 859:         }
 860:       g.setColor(savedColor);
 861:     }        
 862:   }
 863: 
 864:   /**
 865:    * An icon displayed for {@link JRadioButtonMenuItem} components.
 866:    */
 867:   private static class RadioButtonMenuItemIcon implements Icon, Serializable 
 868:   {
 869:     /**
 870:      * Creates a new icon instance.
 871:      */
 872:     public RadioButtonMenuItemIcon() 
 873:     {
 874:       // Nothing to do here.
 875:     }
 876: 
 877:     /**
 878:      * Returns the width of the icon, in pixels.
 879:      * 
 880:      * @return The width of the icon.
 881:      */
 882:     public int getIconWidth() 
 883:     {
 884:       return 10;
 885:     }
 886: 
 887:     /**
 888:      * Returns the height of the icon, in pixels.
 889:      * 
 890:      * @return The height of the icon.
 891:      */
 892:     public int getIconHeight()   
 893:     {
 894:       return 10;
 895:     }
 896: 
 897:     /**
 898:      * Paints the icon.
 899:      * 
 900:      * @param c  the component.
 901:      * @param g  the graphics device.
 902:      * @param x  the x-coordinate.
 903:      * @param y  the y-coordinate.
 904:      */
 905:     public void paintIcon(Component c, Graphics g, int x, int y) 
 906:     {
 907:       Color savedColor = g.getColor();
 908:       JRadioButtonMenuItem item = (JRadioButtonMenuItem) c;
 909:       g.setColor(MetalLookAndFeel.getBlack());
 910:       g.drawLine(x + 2, y, x + 6, y);
 911:       g.drawLine(x + 7, y + 1, x + 7, y + 1);
 912:       g.drawLine(x + 8, y + 2, x + 8, y + 6);
 913:       g.drawLine(x + 7, y + 7, x + 7, y + 7);
 914:       g.drawLine(x + 2, y + 8, x + 6, y + 8);
 915:       g.drawLine(x + 1, y + 7, x + 1, y + 7);
 916:       g.drawLine(x, y + 2, x, y + 6);
 917:       g.drawLine(x + 1, y + 1, x + 1, y + 1);
 918:       
 919:       if (item.isSelected())
 920:         {
 921:           g.drawLine(x + 3, y + 2, x + 5, y + 2);
 922:           g.fillRect(x + 2, y + 3, 5, 3);
 923:           g.drawLine(x + 3, y + 6, x + 5, y + 6);
 924:         }
 925: 
 926:       // highlight
 927:       g.setColor(MetalLookAndFeel.getControlHighlight());
 928:       g.drawLine(x + 3, y + 1, x + 6, y + 1);
 929:       g.drawLine(x + 8, y + 1, x + 8, y + 1);
 930:       g.drawLine(x + 9, y + 2, x + 9, y + 7);
 931:       g.drawLine(x + 8, y + 8, x + 8, y + 8);
 932:       g.drawLine(x + 2, y + 9, x + 7, y + 9);
 933:       g.drawLine(x + 1, y + 8, x + 1, y + 8);
 934:       g.drawLine(x + 1, y + 3, x + 1, y + 6);
 935:       g.drawLine(x + 2, y + 2, x + 2, y + 2);
 936:       g.setColor(savedColor);
 937:     }        
 938:   }
 939: 
 940:   /**
 941:    * The icon used to display the thumb control on a horizontally oriented
 942:    * {@link JSlider} component.
 943:    */
 944:   private static class HorizontalSliderThumbIcon  implements Icon, Serializable
 945:   {
 946: 
 947:     /**
 948:      * Creates a new instance.
 949:      */
 950:     public HorizontalSliderThumbIcon() 
 951:     {
 952:       // Nothing to do here.
 953:     }
 954:     
 955:     /**
 956:      * Returns the width of the icon, in pixels.
 957:      * 
 958:      * @return The width of the icon.
 959:      */
 960:     public int getIconWidth() 
 961:     {
 962:       return 15;
 963:     }
 964:     
 965:     /**
 966:      * Returns the height of the icon, in pixels.
 967:      * 
 968:      * @return The height of the icon.
 969:      */
 970:     public int getIconHeight() 
 971:     {
 972:       return 16;
 973:     }
 974:     
 975:     /**
 976:      * Paints the icon, taking into account whether or not the component has 
 977:      * the focus.
 978:      * 
 979:      * @param c  the component.
 980:      * @param g  the graphics device.
 981:      * @param x  the x-coordinate.
 982:      * @param y  the y-coordinate.
 983:      */
 984:     public void paintIcon(Component c, Graphics g, int x, int y) 
 985:     {
 986:       boolean enabled = false;
 987:       boolean focus = false;
 988:       if (c != null)
 989:         {
 990:           enabled = c.isEnabled();
 991:           focus = c.hasFocus();    
 992:         }
 993:       
 994:       // draw the outline
 995:       if (enabled) 
 996:         g.setColor(MetalLookAndFeel.getBlack());
 997:       else
 998:         g.setColor(MetalLookAndFeel.getControlDarkShadow());
 999:       g.drawLine(x + 1, y, x + 13, y);
1000:       g.drawLine(x + 14, y + 1, x + 14, y + 7);
1001:       g.drawLine(x + 14, y + 8, x + 7, y + 15);
1002:       g.drawLine(x + 6, y + 14, x, y + 8);
1003:       g.drawLine(x, y + 7, x, y + 1);
1004:       
1005:       // fill the icon
1006:       if (focus)
1007:         g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1008:       else
1009:         g.setColor(MetalLookAndFeel.getControl());
1010:       g.fillRect(x + 1, y + 2, 13, 7);
1011:       g.drawLine(x + 2, y + 9, x + 12, y + 9);
1012:       g.drawLine(x + 3, y + 10, x + 11, y + 10);
1013:       g.drawLine(x + 4, y + 11, x + 10, y + 11);
1014:       g.drawLine(x + 5, y + 12, x + 9, y + 12);
1015:       g.drawLine(x + 6, y + 13, x + 8, y + 13);
1016:       g.drawLine(x + 7, y + 14, x + 7, y + 14);
1017:       
1018:       // if the slider is enabled, draw dots and highlights
1019:       if (c.isEnabled())
1020:         {
1021:           if (focus)
1022:             g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1023:           else
1024:             g.setColor(MetalLookAndFeel.getBlack());
1025:           g.drawLine(x + 3, y + 3, x + 3, y + 3);
1026:           g.drawLine(x + 7, y + 3, x + 7, y + 3);
1027:           g.drawLine(x + 11, y + 3, x + 11, y + 3);
1028: 
1029:           g.drawLine(x + 5, y + 5, x + 5, y + 5);
1030:           g.drawLine(x + 9, y + 5, x + 9, y + 5);
1031: 
1032:           g.drawLine(x + 3, y + 7, x + 3, y + 7);
1033:           g.drawLine(x + 7, y + 7, x + 7, y + 7);
1034:           g.drawLine(x + 11, y + 7, x + 11, y + 7);
1035: 
1036:           // draw highlights
1037:           if (focus)
1038:             g.setColor(MetalLookAndFeel.getPrimaryControl());
1039:           else
1040:             g.setColor(MetalLookAndFeel.getWhite());
1041:           g.drawLine(x + 1, y + 1, x + 13, y + 1);
1042:           g.drawLine(x + 1, y + 2, x + 1, y + 8);
1043:           g.drawLine(x + 2, y + 2, x + 2, y + 2);
1044:           g.drawLine(x + 6, y + 2, x + 6, y + 2);
1045:           g.drawLine(x + 10, y + 2, x + 10, y + 2);
1046:           
1047:           g.drawLine(x + 4, y + 4, x + 4, y + 4);
1048:           g.drawLine(x + 8, y + 4, x + 8, y + 4);
1049: 
1050:           g.drawLine(x + 2, y + 6, x + 2, y + 6);
1051:           g.drawLine(x + 6, y + 6, x + 6, y + 6);
1052:           g.drawLine(x + 10, y + 6, x + 10, y + 6);
1053:         }
1054: 
1055:     }        
1056:   }
1057:   
1058:   /**
1059:    * An icon used for the 'close' button in the title frame of a 
1060:    * {@link JInternalFrame}.
1061:    */
1062:   private static class InternalFrameCloseIcon implements Icon, Serializable
1063:   {
1064:     /** The icon size in pixels. */
1065:     private int size;
1066:     
1067:     /**
1068:      * Creates a new icon.
1069:      * 
1070:      * @param size  the icon size (width and height) in pixels.
1071:      */
1072:     public InternalFrameCloseIcon(int size) 
1073:     {
1074:       this.size = size;
1075:     }
1076:     
1077:     /**
1078:      * Returns the width of the icon, in pixels.
1079:      * 
1080:      * @return The width of the icon.
1081:      */
1082:     public int getIconWidth() 
1083:     {
1084:       return size;
1085:     }
1086:     
1087:     /**
1088:      * Returns the height of the icon, in pixels.
1089:      * 
1090:      * @return The height of the icon.
1091:      */
1092:     public int getIconHeight() 
1093:     {
1094:       return size;
1095:     }
1096:     
1097:     /**
1098:      * Paints the icon.
1099:      * 
1100:      * @param c  the component (an {@link JInternalFrame} is expected).
1101:      * @param g  the graphics device.
1102:      * @param x  the x-coordinate.
1103:      * @param y  the y-coordinate.
1104:      */
1105:     public void paintIcon(Component c, Graphics g, int x, int y) 
1106:     {
1107:       Color savedColor = g.getColor();
1108:       AbstractButton b = (AbstractButton) c;
1109:       
1110:       // fill the interior
1111:       if (b.getModel().isPressed())
1112:         // FIXME: also need to take into account whether the internal frame is
1113:         // selected
1114:         g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1115:       else
1116:         g.setColor(MetalLookAndFeel.getPrimaryControl());
1117:       g.fillRect(x + 2, y + 2, 10, 10);
1118:       
1119:       // draw the outline box and the cross
1120:       if (b.getModel().isPressed())
1121:         g.setColor(MetalLookAndFeel.getBlack());
1122:       else
1123:         {
1124:           // FIXME: also need to take into account whether the internal frame is
1125:           // selected
1126:           boolean selected = true;
1127:           if (selected)
1128:             g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1129:           else
1130:             g.setColor(MetalLookAndFeel.getControlDarkShadow());
1131:         }
1132:       g.drawLine(x + 1, y + 1, x + 13, y + 1);
1133:       g.drawLine(x + 1, y + 2, x + 1, y + 12);
1134:       g.drawLine(x + 1, y + 13, x + 13, y + 13);
1135:       g.drawLine(x + 13, y + 2, x + 13, y + 12);
1136:       g.drawLine(x + 2, y + 12, x + 2, y + 12);
1137:       g.drawLine(x + 12, y + 2, x + 12, y + 2);
1138:       
1139:       g.fillRect(x + 4, y + 4, 2, 2);
1140:       g.fillRect(x + 5, y + 5, 4, 4);
1141:       g.drawLine(x + 9, y + 4, x + 10, y + 4);
1142:       g.drawLine(x + 9, y + 4, x + 9, y + 5);
1143:       g.drawLine(x + 4, y + 9, x + 4, y + 10);
1144:       g.drawLine(x + 4, y + 9, x + 5, y + 9);
1145:       g.drawLine(x + 9, y + 8, x + 9, y + 10);
1146:       g.drawLine(x + 8, y + 9, x + 10, y + 9);
1147:       
1148:       g.setColor(MetalLookAndFeel.getBlack());
1149:       g.drawLine(x, y, x + 13, y);
1150:       g.drawLine(x, y + 1, x, y + 13);
1151:       g.drawLine(x + 3, y + 4, x + 4, y + 3);
1152:       g.drawLine(x + 3, y + 9, x + 5, y + 7);
1153:       g.drawLine(x + 7, y + 5, x + 9, y + 3);
1154:       
1155:       g.drawLine(x + 12, y + 3, x + 12, y + 11);
1156:       g.drawLine(x + 3, y + 12, x + 12, y + 12);
1157:       
1158:       g.setColor(MetalLookAndFeel.getWhite());
1159:       g.drawLine(x + 1, y + 14, x + 14, y + 14);
1160:       g.drawLine(x + 14, y + 1, x + 14, y + 14);
1161:       
1162:       if (!b.getModel().isPressed())
1163:         {
1164:           g.drawLine(x + 5, y + 10, x + 5, y + 10);
1165:           g.drawLine(x + 6, y + 9, x + 7, y + 9);
1166:           g.drawLine(x + 10, y + 5, x + 10, y + 5);
1167:           g.drawLine(x + 9, y + 6, x + 9, y + 7);
1168:           g.drawLine(x + 10, y + 10, x + 11, y + 10);
1169:           g.drawLine(x + 10, y + 11, x + 10, y + 11);
1170:         }
1171:       g.setColor(savedColor);
1172:     }        
1173:   }
1174: 
1175:   /**
1176:    * The icon displayed at the top-left corner of a {@link JInternalFrame}.
1177:    */
1178:   private static class InternalFrameDefaultMenuIcon
1179:     implements Icon, Serializable 
1180:   {
1181:        
1182:     /**
1183:      * Creates a new instance.
1184:      */
1185:     public InternalFrameDefaultMenuIcon() 
1186:     {
1187:       // Nothing to do here.
1188:     }
1189:     
1190:     /**
1191:      * Returns the width of the icon, in pixels.
1192:      * 
1193:      * @return The width of the icon.
1194:      */
1195:     public int getIconWidth() 
1196:     {
1197:       return 16;
1198:     }
1199:     
1200:     /**
1201:      * Returns the height of the icon, in pixels.
1202:      * 
1203:      * @return The height of the icon.
1204:      */
1205:     public int getIconHeight() 
1206:     {
1207:       return 16;
1208:     }
1209:     
1210:     /**
1211:      * Paints the icon at the specified location.
1212:      * 
1213:      * @param c  the component.
1214:      * @param g  the graphics device.
1215:      * @param x  the x coordinate.
1216:      * @param y  the y coordinate.
1217:      */
1218:     public void paintIcon(Component c, Graphics g, int x, int y) 
1219:     {
1220:       g.setColor(new Color(102, 102, 153));
1221:       g.fillRect(x + 1, y, 14, 2);
1222:       g.fillRect(x, y + 1, 2, 14);
1223:       g.fillRect(x + 1, y + 14, 14, 2);
1224:       g.fillRect(x + 14, y + 1, 2, 14);
1225:       g.drawLine(x + 2, y + 5, x + 14, y + 5);
1226:       
1227:       g.setColor(new Color(204, 204, 255));
1228:       g.fillRect(x + 2, y + 2, 12, 3);
1229:       
1230:       g.setColor(new Color(102, 102, 153));
1231:       g.drawLine(x + 3, y + 3, x + 3, y + 3);
1232:       g.drawLine(x + 6, y + 3, x + 6, y + 3);
1233:       g.drawLine(x + 9, y + 3, x + 9, y + 3);
1234:       g.drawLine(x + 12, y + 3, x + 12, y + 3);
1235: 
1236:       g.setColor(Color.white);
1237:       g.fillRect(x + 2, y + 6, 12, 8);
1238:       g.drawLine(x + 2, y + 2, x + 2, y + 2);
1239:       g.drawLine(x + 5, y + 2, x + 5, y + 2);
1240:       g.drawLine(x + 8, y + 2, x + 8, y + 2);
1241:       g.drawLine(x + 11, y + 2, x + 11, y + 2);
1242:     }        
1243:   }
1244: 
1245:   /**
1246:    * An icon used in the title frame of a {@link JInternalFrame}.  When you 
1247:    * maximise an internal frame, this icon will replace the 'maximise' icon to
1248:    * provide a 'restore' option.
1249:    */
1250:   private static class InternalFrameAltMaximizeIcon
1251:     implements Icon, Serializable 
1252:   {
1253:     /** The icon size in pixels. */
1254:     private int size;
1255:     
1256:     /**
1257:      * Creates a new icon.
1258:      * 
1259:      * @param size  the icon size in pixels.
1260:      */
1261:     public InternalFrameAltMaximizeIcon(int size) 
1262:     {
1263:       this.size = size;
1264:     }
1265:     
1266:     /**
1267:      * Returns the width of the icon, in pixels.
1268:      * 
1269:      * @return The width of the icon.
1270:      */
1271:     public int getIconWidth() 
1272:     {
1273:       return size;
1274:     }
1275:     
1276:     /**
1277:      * Returns the height of the icon, in pixels.
1278:      * 
1279:      * @return The height of the icon.
1280:      */
1281:     public int getIconHeight() 
1282:     {
1283:       return size;
1284:     }
1285:     
1286:     /**
1287:      * Paints the icon at the specified location.
1288:      * 
1289:      * @param c  the component.
1290:      * @param g  the graphics device.
1291:      * @param x  the x coordinate.
1292:      * @param y  the y coordinate.
1293:      */
1294:     public void paintIcon(Component c, Graphics g, int x, int y) 
1295:     {
1296:       Color savedColor = g.getColor();
1297: 
1298:       AbstractButton b = (AbstractButton) c;
1299: 
1300:       // fill the small box interior
1301:       if (b.getModel().isPressed())
1302:         g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1303:       else
1304:         g.setColor(MetalLookAndFeel.getPrimaryControl());
1305:       g.fillRect(x + 2, y + 6, 7, 7);
1306:       
1307:       
1308:       if (b.getModel().isPressed())
1309:         g.setColor(MetalLookAndFeel.getBlack());
1310:       else
1311:         g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1312:         
1313:       g.drawLine(x + 12, y + 1, x + 13, y + 1);
1314:       g.drawLine(x + 11, y + 2, x + 12, y + 2);
1315:       g.drawLine(x + 10, y + 3, x + 11, y + 3);
1316:       g.drawLine(x + 8, y + 2, x + 8, y + 3);
1317:       g.fillRect(x + 8, y + 4, 3, 3);
1318:       g.drawLine(x + 11, y + 6, x + 12, y + 6);
1319:       
1320:       g.drawLine(x + 1, y + 5, x + 5, y + 5);
1321:       g.drawLine(x + 1, y + 6, x + 1, y + 12);
1322:       g.drawLine(x + 9, y + 9, x + 9, y + 12);
1323:       g.drawLine(x + 1, y + 13, x + 9, y + 13);
1324:       
1325:       g.drawLine(x + 2, y + 12, x + 2, y + 12);
1326:       
1327:       g.setColor(MetalLookAndFeel.getBlack());
1328:       g.drawLine(x + 12, y, x + 9, y + 3);
1329:       g.drawLine(x + 7, y + 1, x + 8, y + 1);
1330:       g.drawLine(x + 7, y + 2, x + 7, y + 6);
1331:       g.drawLine(x + 11, y + 5, x + 12, y + 5);
1332:       g.drawLine(x, y + 4, x + 5, y + 4);
1333:       g.drawLine(x, y + 5, x, y + 13);
1334:       g.drawLine(x + 3, y + 12, x + 8, y + 12);
1335:       g.drawLine(x + 8, y + 8, x + 8, y + 11);
1336:       g.drawLine(x + 9, y + 8, x + 9, y + 8);
1337:       
1338:       g.setColor(MetalLookAndFeel.getWhite());
1339:       g.drawLine(x + 9, y + 2, x + 9, y + 2);
1340:       g.drawLine(x + 11, y + 4, x + 13, y + 2);
1341:       g.drawLine(x + 13, y + 6, x + 13, y + 6);
1342:       g.drawLine(x + 8, y + 7, x + 13, y + 7);
1343:       g.drawLine(x + 6, y + 5, x + 6, y + 5);
1344:       g.drawLine(x + 10, y + 8, x + 10, y + 13);
1345:       g.drawLine(x + 1, y + 14, x + 10, y + 14);
1346:       
1347:       if (!b.getModel().isPressed())
1348:         {
1349:           g.drawLine(x + 2, y + 6, x + 6, y + 6);
1350:           g.drawLine(x + 2, y + 6, x + 2, y + 11);
1351:         }
1352:       
1353:       g.setColor(savedColor);
1354:     }        
1355:   }
1356:   
1357:   /**
1358:    * An icon used for the 'maximize' button in the title frame of a 
1359:    * {@link JInternalFrame}.
1360:    */
1361:   private static class InternalFrameMaximizeIcon implements Icon, Serializable
1362:   {
1363:     
1364:     /**
1365:      * Creates a new instance.
1366:      */
1367:     public InternalFrameMaximizeIcon() 
1368:     {
1369:       // Nothing to do here.
1370:     }
1371:     
1372:     /**
1373:      * Returns the width of the icon, in pixels.
1374:      * 
1375:      * @return The width of the icon.
1376:      */
1377:     public int getIconWidth() 
1378:     {
1379:       return 16;
1380:     }
1381:     
1382:     /**
1383:      * Returns the height of the icon, in pixels.
1384:      * 
1385:      * @return The height of the icon.
1386:      */
1387:     public int getIconHeight() 
1388:     {
1389:       return 16;
1390:     }
1391:     
1392:     /**
1393:      * Paints the icon at the specified location.
1394:      * 
1395:      * @param c  the component.
1396:      * @param g  the graphics device.
1397:      * @param x  the x coordinate.
1398:      * @param y  the y coordinate.
1399:      */
1400:     public void paintIcon(Component c, Graphics g, int x, int y) 
1401:     {
1402:       Color savedColor = g.getColor();
1403:       
1404:       AbstractButton b = (AbstractButton) c;
1405:       
1406:       // fill the interior
1407:       if (b.getModel().isPressed())
1408:         g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1409:       else
1410:         g.setColor(MetalLookAndFeel.getPrimaryControl());
1411:       g.fillRect(x + 2, y + 6, 7, 7);
1412: 
1413:       if (b.getModel().isPressed())
1414:         g.setColor(MetalLookAndFeel.getBlack());
1415:       else
1416:         g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1417:           
1418:       g.drawLine(x + 9, y + 1, x + 10, y + 1);
1419:       g.fillRect(x + 11, y + 1, 3, 3);
1420:       g.fillRect(x + 12, y + 4, 2, 2);
1421:       g.drawLine(x + 10, y + 3, x + 10, y + 3);
1422:       g.drawLine(x + 9, y + 4, x + 10, y + 4);
1423:       g.drawLine(x + 1, y + 5, x + 9, y + 5);
1424:       g.drawLine(x + 1, y + 6, x + 1, y + 12);
1425:       g.drawLine(x + 9, y + 6, x + 9, y + 12);
1426:       g.drawLine(x + 1, y + 13, x + 9, y + 13);
1427:       
1428:       // fill
1429:       g.drawLine(x + 7, y + 6, x + 8, y + 6);
1430:       g.drawLine(x + 6, y + 7, x + 8, y + 7);
1431:       g.drawLine(x + 5, y + 8, x + 6, y + 8);
1432:       g.drawLine(x + 4, y + 9, x + 5, y + 9);
1433:       g.drawLine(x + 3, y + 10, x + 4, y + 10);
1434:       g.drawLine(x + 2, y + 11, x + 3, y + 11);
1435:       g.drawLine(x + 2, y + 12, x + 4, y + 12);
1436:       g.drawLine(x + 8, y + 8, x + 8, y + 8);
1437:       
1438:       // draw black
1439:       g.setColor(MetalLookAndFeel.getBlack());
1440:       g.drawLine(x + 8, y, x + 13, y);
1441:       g.drawLine(x + 8, y + 1, x + 8, y + 1);
1442:       g.drawLine(x + 10, y + 2, x + 9, y + 3);
1443:       g.drawLine(x, y + 4, x + 8, y + 4);
1444:       g.drawLine(x, y + 5, x, y + 13);
1445:       
1446:       g.drawLine(x + 2, y + 10, x + 6, y + 6);
1447:       g.drawLine(x + 8, y + 9, x + 8, y + 11);
1448:       g.drawLine(x + 5, y + 12, x + 8, y + 12);
1449:       
1450:       // draw white
1451:       g.setColor(MetalLookAndFeel.getWhite());
1452:       if (!b.getModel().isPressed())
1453:         {
1454:           g.drawLine(x + 2, y + 6, x + 5, y + 6);
1455:           g.drawLine(x + 2, y + 7, x + 2, y + 9);
1456:           g.drawLine(x + 4, y + 11, x + 7, y + 8);
1457:         }
1458:       
1459:       g.drawLine(x + 1, y + 14, x + 10, y + 14);
1460:       g.drawLine(x + 10, y + 5, x + 10, y + 13);
1461:       
1462:       g.drawLine(x + 9, y + 2, x + 9, y + 2);
1463:       g.drawLine(x + 11, y + 4, x + 11, y + 5);
1464:       g.drawLine(x + 13, y + 6, x + 14, y + 6);
1465:       g.drawLine(x + 14, y + 1, x + 14, y + 5);
1466:       g.setColor(savedColor);
1467:     }        
1468:   }
1469: 
1470:   /**
1471:    * An icon used in the title frame of a {@link JInternalFrame}.
1472:    */
1473:   private static class InternalFrameMinimizeIcon implements Icon, Serializable
1474:   {
1475:   
1476:     /**
1477:      * Creates a new instance.
1478:      */
1479:     public InternalFrameMinimizeIcon() 
1480:     {
1481:       // Nothing to do here.
1482:     }
1483:     
1484:     /**
1485:      * Returns the width of the icon, in pixels.
1486:      * 
1487:      * @return The width of the icon.
1488:      */
1489:     public int getIconWidth() 
1490:     {
1491:       return 16;
1492:     }
1493:     
1494:     /**
1495:      * Returns the height of the icon, in pixels.
1496:      * 
1497:      * @return The height of the icon.
1498:      */
1499:     public int getIconHeight() 
1500:     {
1501:       return 16;
1502:     }
1503:     
1504:     /**
1505:      * Paints the icon at the specified location.
1506:      * 
1507:      * @param c  the component.
1508:      * @param g  the graphics device.
1509:      * @param x  the x coordinate.
1510:      * @param y  the y coordinate.
1511:      */
1512:     public void paintIcon(Component c, Graphics g, int x, int y) 
1513:     {
1514:       Color savedColor = g.getColor();
1515:       
1516:       AbstractButton b = (AbstractButton) c;
1517:       
1518:       if (b.getModel().isPressed())
1519:         g.setColor(MetalLookAndFeel.getBlack());
1520:       else
1521:         // FIXME: here the color depends on whether or not the internal frame 
1522:         // is selected 
1523:         g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1524:       
1525:       g.drawLine(x + 12, y + 1, x + 13, y + 1);
1526:       g.drawLine(x + 11, y + 2, x + 12, y + 2);
1527:       g.drawLine(x + 10, y + 3, x + 11, y + 3);
1528:       g.drawLine(x + 8, y + 2, x + 8, y + 3);
1529:       g.fillRect(x + 8, y + 4, 3, 3);
1530:       g.drawLine(x + 11, y + 6, x + 12, y + 6);
1531:       
1532:       g.drawLine(x + 1, y + 8, x + 6, y + 8);
1533:       g.drawLine(x + 1, y + 9, x + 1, y + 12);
1534:       g.drawLine(x + 6, y + 9, x + 6, y + 12);
1535:       g.drawLine(x + 1, y + 13, x + 6, y + 13);
1536:       
1537:       g.drawLine(x + 5, y + 9, x + 5, y + 9);
1538:       g.drawLine(x + 2, y + 12, x + 2, y + 12);
1539:       
1540:       g.setColor(MetalLookAndFeel.getBlack());
1541:       g.drawLine(x + 12, y, x + 9, y + 3);
1542:       g.drawLine(x + 7, y + 1, x + 8, y + 1);
1543:       g.drawLine(x + 7, y + 2, x + 7, y + 6);
1544:       g.drawLine(x, y + 7, x + 6, y + 7);
1545:       g.drawLine(x, y + 8, x, y + 13);
1546:       g.drawLine(x + 3, y + 12, x + 5, y + 12);
1547:       g.drawLine(x + 5, y + 10, x + 5, y + 11);
1548:       g.drawLine(x + 11, y + 5, x + 12, y + 5);
1549:       
1550:       g.setColor(MetalLookAndFeel.getWhite());
1551:       g.drawLine(x + 9, y + 2, x + 9, y + 2);
1552:       g.drawLine(x + 11, y + 4, x + 13, y + 2);
1553:       g.drawLine(x + 13, y + 6, x + 13, y + 6);
1554:       g.drawLine(x + 8, y + 7, x + 13, y + 7);
1555:       g.drawLine(x + 7, y + 9, x + 7, y + 13);
1556:       g.drawLine(x + 1, y + 14, x + 7, y + 14);
1557: 
1558:       if (b.getModel().isPressed())
1559:         {
1560:           g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1561:           g.fillRect(x + 2, y + 9, 3, 3);
1562:         }
1563:       else
1564:         {
1565:           g.drawLine(x + 2, y + 9, x + 4, y + 9);
1566:           g.drawLine(x + 2, y + 10, x + 2, y + 11);
1567:         }
1568: 
1569:       g.setColor(savedColor);
1570:     }        
1571:   }
1572: 
1573:   /**
1574:    * The icon used to display the thumb control on a horizontally oriented
1575:    * {@link JSlider} component.
1576:    */
1577:   private static class VerticalSliderThumbIcon implements Icon, Serializable
1578:   {
1579:     /**
1580:      * Creates a new instance.
1581:      */
1582:     public VerticalSliderThumbIcon() 
1583:     {
1584:       // Nothing to do here.
1585:     }
1586:     
1587:     /**
1588:      * Returns the width of the icon, in pixels.
1589:      * 
1590:      * @return The width of the icon.
1591:      */
1592:     public int getIconWidth() 
1593:     {
1594:       return 16;
1595:     }
1596:     
1597:     /**
1598:      * Returns the height of the icon, in pixels.
1599:      * 
1600:      * @return The height of the icon.
1601:      */
1602:     public int getIconHeight() 
1603:     {
1604:       return 15;
1605:     }
1606:     
1607:     /**
1608:      * Paints the icon taking into account whether the slider control has the
1609:      * focus or not.
1610:      * 
1611:      * @param c  the slider (must be a non-<code>null</code> instance of
1612:      *           {@link JSlider}.
1613:      * @param g  the graphics device.
1614:      * @param x  the x-coordinate.
1615:      * @param y  the y-coordinate.
1616:      */
1617:     public void paintIcon(Component c, Graphics g, int x, int y) 
1618:     {
1619:       boolean enabled = false;
1620:       boolean focus = false;
1621:       if (c != null)
1622:         {
1623:           enabled = c.isEnabled();
1624:           focus = c.hasFocus();    
1625:         }
1626:       
1627:       // draw the outline
1628:       if (enabled) 
1629:         g.setColor(MetalLookAndFeel.getBlack());
1630:       else
1631:         g.setColor(MetalLookAndFeel.getControlDarkShadow());
1632:       g.drawLine(x + 1, y, x + 7, y);
1633:       g.drawLine(x + 8, y, x + 15, y + 7);
1634:       g.drawLine(x + 14, y + 8, x + 8, y + 14);
1635:       g.drawLine(x + 8, y + 14, x + 1, y + 14);
1636:       g.drawLine(x, y + 13, x, y + 1);
1637:       
1638:       // fill the icon
1639:       if (focus)
1640:         g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
1641:       else
1642:         g.setColor(MetalLookAndFeel.getControl());
1643:       g.fillRect(x + 2, y + 1, 7, 13);
1644:       g.drawLine(x + 9, y + 2, x + 9, y + 12);
1645:       g.drawLine(x + 10, y + 3, x + 10, y + 11);
1646:       g.drawLine(x + 11, y + 4, x + 11, y + 10);
1647:       g.drawLine(x + 12, y + 5, x + 12, y + 9);
1648:       g.drawLine(x + 13, y + 6, x + 13, y + 8);
1649:       g.drawLine(x + 14, y + 7, x + 14, y + 7);
1650:       
1651:       // if the slider is enabled, draw dots and highlights
1652:       if (enabled)
1653:         {
1654:           if (focus)
1655:             g.setColor(MetalLookAndFeel.getPrimaryControlDarkShadow());
1656:           else
1657:             g.setColor(MetalLookAndFeel.getBlack());
1658:           g.drawLine(x + 3, y + 3, x + 3, y + 3);
1659:           g.drawLine(x + 3, y + 7, x + 3, y + 7);
1660:           g.drawLine(x + 3, y + 11, x + 3, y + 11);
1661: 
1662:           g.drawLine(x + 5, y + 5, x + 5, y + 5);
1663:           g.drawLine(x + 5, y + 9, x + 5, y + 9);
1664: 
1665:           g.drawLine(x + 7, y + 3, x + 7, y + 3);
1666:           g.drawLine(x + 7, y + 7, x + 7, y + 7);
1667:           g.drawLine(x + 7, y + 11, x + 7, y + 11);
1668: 
1669:           // draw highlights
1670:           if (focus)
1671:             g.setColor(MetalLookAndFeel.getPrimaryControl());
1672:           else
1673:             g.setColor(MetalLookAndFeel.getWhite());
1674:           g.drawLine(x + 1, y + 1, x + 8, y + 1);
1675:           g.drawLine(x + 1, y + 2, x + 1, y + 13);
1676:           g.drawLine(x + 2, y + 2, x + 2, y + 2);
1677:           g.drawLine(x + 2, y + 6, x + 2, y + 6);
1678:           g.drawLine(x + 2, y + 10, x + 2, y + 10);
1679: 
1680:           g.drawLine(x + 4, y + 4, x + 4, y + 4);
1681:           g.drawLine(x + 4, y + 8, x + 4, y + 8);
1682: 
1683:           g.drawLine(x + 6, y + 2, x + 6, y + 2);
1684:           g.drawLine(x + 6, y + 6, x + 6, y + 6);
1685:           g.drawLine(x + 6, y + 10, x + 6, y + 10);
1686:         
1687:         }
1688:     }        
1689:   }
1690:     
1691:   /**
1692:    * A tree control icon.  This icon can be in one of two states: expanded and
1693:    * collapsed.
1694:    */
1695:   public static class TreeControlIcon implements Icon, Serializable
1696:   {
1697:     
1698:     /** ???. */
1699:     protected boolean isLight;
1700:     
1701:     /** A flag that controls whether or not the icon is collapsed. */
1702:     private boolean collapsed;
1703:     
1704:     /**
1705:      * Creates a new icon.
1706:      * 
1707:      * @param isCollapsed  a flag that controls whether the icon is in the
1708:      *                     collapsed state or the expanded state.
1709:      */
1710:     public TreeControlIcon(boolean isCollapsed) 
1711:     {
1712:       collapsed = isCollapsed;
1713:     }
1714:     
1715:     /**
1716:      * Returns the width of the icon, in pixels.
1717:      * 
1718:      * @return The width of the icon.
1719:      */
1720:     public int getIconWidth() 
1721:     {
1722:       return 18;
1723:     }
1724:     /**
1725:      * Returns the height of the icon, in pixels.
1726:      * 
1727:      * @return The height of the icon.
1728:      */
1729:     public int getIconHeight() 
1730:     {
1731:       return 18;
1732:     }
1733:     
1734:     /**
1735:      * Paints the icon at the location (x, y).
1736:      * 
1737:      * @param c  the component.
1738:      * @param g  the graphics device.
1739:      * @param x  the x coordinate.
1740:      * @param y  the y coordinate.
1741:      */
1742:     public void paintIcon(Component c, Graphics g, int x, int y) 
1743:     {
1744:       x = x + 5;
1745:       y = y + 5;
1746:       if (collapsed) 
1747:       {
1748:         // TODO: pick up appropriate UI colors
1749:         g.setColor(Color.black);
1750:         g.drawLine(x + 2, y, x + 5, y);
1751:         g.drawLine(x + 6, y + 1, x + 7, y + 2);
1752:         g.fillRect(x + 7, y + 3, 5, 2);
1753:         g.drawLine(x + 7, y + 5, x + 6, y + 6);
1754:         g.drawLine(x + 1, y + 1, x + 1, y + 1);
1755:         g.drawLine(x, y + 2, x, y + 5);
1756:         g.drawLine(x + 1, y + 6, x + 1, y + 6);
1757:         g.drawLine(x + 2, y + 7, x + 5, y + 7);
1758:         g.fillRect(x + 3, y + 3, 2, 2);
1759: 
1760:         g.setColor(new Color(204, 204, 255));
1761:         g.drawLine(x + 3, y + 2, x + 4, y + 2);
1762:         g.drawLine(x + 2, y + 3, x + 2, y + 4);
1763:         g.drawLine(x + 3, y + 5, x + 3, y + 5);
1764:         g.drawLine(x + 5, y + 3, x + 5, y + 3);
1765:         
1766:         g.setColor(new Color(153, 153, 204));
1767:         g.drawLine(x + 2, y + 2, x + 2, y + 2);
1768:         g.drawLine(x + 2, y + 5, x + 2, y + 5);
1769:         g.drawLine(x + 2, y + 6, x + 5, y + 6);
1770:         g.drawLine(x + 5, y + 2, x + 5, y + 2);
1771:         g.drawLine(x + 6, y + 2, x + 6, y + 5);
1772:         
1773:         g.setColor(new Color(102, 102, 153));
1774:         g.drawLine(x + 2, y + 1, x + 5, y + 1);
1775:         g.drawLine(x + 1, y + 2, x + 1, y + 5);
1776:       }
1777:       else
1778:       {
1779:         // TODO: pick up appropriate UI colors
1780:         g.setColor(Color.black);
1781:         g.drawLine(x + 2, y, x + 5, y);
1782:         g.drawLine(x + 6, y + 1, x + 7, y + 2);
1783:         g.drawLine(x + 7, y + 2, x + 7, y + 5);
1784:         g.fillRect(x + 3, y + 7, 2, 5);
1785:         g.drawLine(x + 7, y + 5, x + 6, y + 6);
1786:         g.drawLine(x + 1, y + 1, x + 1, y + 1);
1787:         g.drawLine(x, y + 2, x, y + 5);
1788:         g.drawLine(x + 1, y + 6, x + 1, y + 6);
1789:         g.drawLine(x + 2, y + 7, x + 5, y + 7);
1790:         g.fillRect(x + 3, y + 3, 2, 2);
1791: 
1792:         g.setColor(new Color(204, 204, 255));
1793:         g.drawLine(x + 3, y + 2, x + 4, y + 2);
1794:         g.drawLine(x + 2, y + 3, x + 2, y + 4);
1795:         g.drawLine(x + 3, y + 5, x + 3, y + 5);
1796:         g.drawLine(x + 5, y + 3, x + 5, y + 3);
1797:         
1798:         g.setColor(new Color(153, 153, 204));
1799:         g.drawLine(x + 2, y + 2, x + 2, y + 2);
1800:         g.drawLine(x + 2, y + 5, x + 2, y + 5);
1801:         g.drawLine(x + 2, y + 6, x + 5, y + 6);
1802:         g.drawLine(x + 5, y + 2, x + 5, y + 2);
1803:         g.drawLine(x + 6, y + 2, x + 6, y + 5);
1804:         
1805:         g.setColor(new Color(102, 102, 153));
1806:         g.drawLine(x + 2, y + 1, x + 5, y + 1);
1807:         g.drawLine(x + 1, y + 2, x + 1, y + 5);
1808:       }
1809:     } 
1810:     
1811:     /**
1812:      * Simply calls {@link #paintIcon(Component, Graphics, int, int)}.
1813:      * 
1814:      * @param c  the component.
1815:      * @param g  the graphics device.
1816:      * @param x  the x coordinate.
1817:      * @param y  the y coordinate.
1818:      */
1819:     public void paintMe(Component c, Graphics g, int x, int y) 
1820:     {
1821:       paintIcon(c, g, x, y);  
1822:     }
1823:   }
1824:     
1825:   /**
1826:    * A tree folder icon.
1827:    */
1828:   public static class TreeFolderIcon extends FolderIcon16
1829:   {
1830:     /**
1831:      * Creates a new instance.
1832:      */
1833:     public TreeFolderIcon() 
1834:     {
1835:       // Nothing to do here.
1836:     }
1837:     
1838:     /**
1839:      * Returns the additional height for this icon, in this case <code>2</code>
1840:      * pixels.
1841:      * 
1842:      * @return <code>2</code>.
1843:      */
1844:     public int getAdditionalHeight() 
1845:     {
1846:       return 2;
1847:     }
1848:     
1849:     /**
1850:      * Returns the shift (???).
1851:      * 
1852:      * @return The shift.
1853:      */
1854:     public int getShift() 
1855:     {
1856:       return -1;
1857:     }
1858:   }
1859:     
1860:   /**
1861:    * A tree leaf icon.
1862:    */
1863:   public static class TreeLeafIcon extends FileIcon16
1864:   {
1865:     /**
1866:      * Creates a new instance.
1867:      */
1868:     public TreeLeafIcon() 
1869:     {
1870:       // Nothing to do here.
1871:     }
1872:     
1873:     /**
1874:      * Returns the additional height for this icon, in this case <code>4</code>
1875:      * pixels.
1876:      * 
1877:      * @return <code>4</code>.
1878:      */
1879:     public int getAdditionalHeight() 
1880:     {
1881:       return 4;
1882:     }
1883:     
1884:     /**
1885:      * Returns the shift (???).
1886:      * 
1887:      * @return The shift.
1888:      */
1889:     public int getShift() 
1890:     {
1891:       return 2;
1892:     }
1893:   }
1894: 
1895:   /**
1896:    * An icon representing a hard disk.
1897:    * 
1898:    * @see MetalIconFactory#getTreeHardDriveIcon()
1899:    */
1900:   private static class TreeHardDriveIcon implements Icon, Serializable
1901:   {
1902: 
1903:     /**
1904:      * Creates a new icon instance.
1905:      */
1906:     public TreeHardDriveIcon() 
1907:     {
1908:       // Nothing to do here.
1909:     }
1910: 
1911:     /**
1912:      * Returns the width of the icon, in pixels.
1913:      * 
1914:      * @return <code>16</code>.
1915:      */
1916:     public int getIconWidth() 
1917:     { 
1918:       return 16;
1919:     }
1920: 
1921:     /**
1922:      * Returns the height of the icon, in pixels.
1923:      * 
1924:      * @return <code>16</code>.
1925:      */
1926:     public int getIconHeight()   
1927:     {
1928:       return 16;
1929:     }
1930: 
1931:     /**
1932:      * Paints the icon at the specified location, using colors from the 
1933:      * current theme.
1934:      * 
1935:      * @param c  the component (ignored).
1936:      * @param g  the graphics device.
1937:      * @param x  the x-coordinate for the top-left of the icon.
1938:      * @param y  the y-coordinate for the top-left of the icon.
1939:      */
1940:     public void paintIcon(Component c, Graphics g, int x, int y) 
1941:     {
1942:       Color saved = g.getColor();
1943:       g.setColor(MetalLookAndFeel.getBlack());
1944:       g.drawLine(x + 1, y + 4, x + 1, y + 5);
1945:       g.drawLine(x + 14, y + 4, x + 14, y + 5);
1946:       g.drawLine(x + 1, y + 7, x + 1, y + 8);
1947:       g.drawLine(x + 14, y + 7, x + 14, y + 8);
1948:       g.drawLine(x + 1, y + 10, x + 1, y + 11);
1949:       g.drawLine(x + 14, y + 10, x + 14, y + 11);
1950:       
1951:       g.drawLine(x + 2, y + 3, x + 3, y + 3);
1952:       g.drawLine(x + 12, y + 3, x + 13, y + 3);
1953:       g.drawLine(x + 2, y + 6, x + 3, y + 6);
1954:       g.drawLine(x + 12, y + 6, x + 13, y + 6);
1955:       g.drawLine(x + 2, y + 9, x + 3, y + 9);
1956:       g.drawLine(x + 12, y + 9, x + 13, y + 9);
1957:       g.drawLine(x + 2, y + 12, x + 3, y + 12);
1958:       g.drawLine(x + 12, y + 12, x + 13, y + 12);
1959:       
1960:       g.drawLine(x + 4, y + 2, x + 11, y + 2);
1961:       g.drawLine(x + 4, y + 7, x + 11, y + 7);
1962:       g.drawLine(x + 4, y + 10, x + 11, y + 10);
1963:       g.drawLine(x + 4, y + 13, x + 11, y + 13);
1964:       
1965:       g.setColor(MetalLookAndFeel.getWhite());
1966:       g.fillRect(x + 4, y + 3, 2, 2);
1967:       g.drawLine(x + 6, y + 4, x + 6, y + 4);
1968:       g.drawLine(x + 7, y + 3, x + 9, y + 3);
1969:       g.drawLine(x + 8, y + 4, x + 8, y + 4);
1970:       g.drawLine(x + 11, y + 3, x + 11, y + 3);
1971:       g.fillRect(x + 2, y + 4, 2, 2); 
1972:       g.fillRect(x + 2, y + 7, 2, 2); 
1973:       g.fillRect(x + 2, y + 10, 2, 2); 
1974:       g.drawLine(x + 4, y + 6, x + 4, y + 6);
1975:       g.drawLine(x + 4, y + 9, x + 4, y + 9);
1976:       g.drawLine(x + 4, y + 12, x + 4, y + 12);
1977:       
1978:       g.setColor(MetalLookAndFeel.getControlShadow());
1979:       g.drawLine(x + 13, y + 4, x + 13, y + 4);
1980:       g.drawLine(x + 12, y + 5, x + 13, y + 5);
1981:       g.drawLine(x + 13, y + 7, x + 13, y + 7);
1982:       g.drawLine(x + 12, y + 8, x + 13, y + 8);
1983:       g.drawLine(x + 13, y + 10, x + 13, y + 10);
1984:       g.drawLine(x + 12, y + 11, x + 13, y + 11);
1985:       
1986:       g.drawLine(x + 10, y + 5, x + 10, y + 5);
1987:       g.drawLine(x + 7, y + 6, x + 7, y + 6);
1988:       g.drawLine(x + 9, y + 6, x + 9, y + 6);
1989:       g.drawLine(x + 11, y + 6, x + 11, y + 6);
1990: 
1991:       g.drawLine(x + 10, y + 8, x + 10, y + 8);
1992:       g.drawLine(x + 7, y + 9, x + 7, y + 9);
1993:       g.drawLine(x + 9, y + 9, x + 9, y + 9);
1994:       g.drawLine(x + 11, y + 9, x + 11, y + 9);
1995: 
1996:       g.drawLine(x + 10, y + 11, x + 10, y + 11);
1997:       g.drawLine(x + 7, y + 12, x + 7, y + 12);
1998:       g.drawLine(x + 9, y + 12, x + 9, y + 12);
1999:       g.drawLine(x + 11, y + 12, x + 11, y + 12);
2000: 
2001:       g.setColor(saved);
2002:     }        
2003:   }  
2004:   
2005:   /**
2006:    * An icon representing a floppy disk.
2007:    * 
2008:    * @see MetalIconFactory#getTreeFloppyDriveIcon()
2009:    */
2010:   private static class TreeFloppyDriveIcon implements Icon, Serializable
2011:   {
2012: 
2013:     /**
2014:      * Creates a new icon instance.
2015:      */
2016:     public TreeFloppyDriveIcon() 
2017:     {
2018:       // Nothing to do here.
2019:     }
2020: 
2021:     /**
2022:      * Returns the width of the icon, in pixels.
2023:      * 
2024:      * @return <code>16</code>.
2025:      */
2026:     public int getIconWidth() 
2027:     { 
2028:       return 16;
2029:     }
2030: 
2031:     /**
2032:      * Returns the height of the icon, in pixels.
2033:      * 
2034:      * @return <code>16</code>.
2035:      */
2036:     public int getIconHeight()   
2037:     {
2038:       return 16;
2039:     }
2040: 
2041:     /**
2042:      * Paints the icon at the specified location, using colors from the 
2043:      * current theme.
2044:      * 
2045:      * @param c  the component (ignored).
2046:      * @param g  the graphics device.
2047:      * @param x  the x-coordinate for the top-left of the icon.
2048:      * @param y  the y-coordinate for the top-left of the icon.
2049:      */
2050:     public void paintIcon(Component c, Graphics g, int x, int y) 
2051:     {
2052:       Color saved = g.getColor();
2053:       
2054:       g.setColor(MetalLookAndFeel.getBlack());
2055:       g.drawLine(x + 1, y + 1, x + 13, y + 1);
2056:       g.drawLine(x + 1, y + 1, x + 1, y + 14);
2057:       g.drawLine(x + 1, y + 14, x + 14, y + 14);
2058:       g.drawLine(x + 14, y + 2, x + 14, y + 14);
2059:       
2060:       g.setColor(MetalLookAndFeel.getPrimaryControl());
2061:       g.fillRect(x + 2, y + 2, 12, 12);
2062:       
2063:       g.setColor(MetalLookAndFeel.getControlShadow());
2064:       g.fillRect(x + 5, y + 2, 6, 5);
2065:       g.drawLine(x + 4, y + 8, x + 11, y + 8);
2066:       g.drawLine(x + 3, y + 9, x + 3, y + 13);
2067:       g.drawLine(x + 12, y + 9, x + 12, y + 13);
2068:       
2069:       g.setColor(MetalLookAndFeel.getWhite());
2070:       g.fillRect(x + 8, y + 3, 2, 3);
2071:       g.fillRect(x + 4, y + 9, 8, 5);
2072:       
2073:       g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
2074:       g.drawLine(x + 5, y + 10, x + 9, y + 10);
2075:       g.drawLine(x + 5, y + 12, x + 8, y + 12);
2076: 
2077:       g.setColor(saved);
2078:     }        
2079:   }  
2080: 
2081:   /**
2082:    * An icon representing a computer.
2083:    * 
2084:    * @see MetalIconFactory#getTreeComputerIcon()
2085:    */
2086:   private static class TreeComputerIcon implements Icon, Serializable
2087:   {
2088: 
2089:     /**
2090:      * Creates a new icon instance.
2091:      */
2092:     public TreeComputerIcon() 
2093:     {
2094:       // Nothing to do here.
2095:     }
2096: 
2097:     /**
2098:      * Returns the width of the icon, in pixels.
2099:      * 
2100:      * @return <code>16</code>.
2101:      */
2102:     public int getIconWidth() 
2103:     { 
2104:       return 16;
2105:     }
2106: 
2107:     /**
2108:      * Returns the height of the icon, in pixels.
2109:      * 
2110:      * @return <code>16</code>.
2111:      */
2112:     public int getIconHeight()   
2113:     {
2114:       return 16;
2115:     }
2116: 
2117:     /**
2118:      * Paints the icon at the specified location, using colors from the 
2119:      * current theme.
2120:      * 
2121:      * @param c  the component (ignored).
2122:      * @param g  the graphics device.
2123:      * @param x  the x-coordinate for the top-left of the icon.
2124:      * @param y  the y-coordinate for the top-left of the icon.
2125:      */
2126:     public void paintIcon(Component c, Graphics g, int x, int y) 
2127:     {
2128:       Color saved = g.getColor();
2129:       
2130:       g.setColor(MetalLookAndFeel.getBlack());
2131:       g.drawLine(x + 3, y + 1, x + 12, y + 1);
2132:       g.drawLine(x + 2, y + 2, x + 2, y + 8);
2133:       g.drawLine(x + 13, y + 2, x + 13, y + 8);
2134:       g.drawLine(x + 3, y + 9, x + 3, y + 9);
2135:       g.drawLine(x + 12, y + 9, x + 12, y + 9);
2136:       g.drawRect(x + 1, y + 10, 13, 4);
2137:       g.drawLine(x + 5, y + 3, x + 10, y + 3);
2138:       g.drawLine(x + 5, y + 8, x + 10, y + 8);
2139:       g.drawLine(x + 4, y + 4, x + 4, y + 7);
2140:       g.drawLine(x + 11, y + 4, x + 11, y + 7);
2141: 
2142:       g.setColor(MetalLookAndFeel.getPrimaryControl());
2143:       g.fillRect(x + 5, y + 4, 6, 4);
2144:       
2145:       g.setColor(MetalLookAndFeel.getControlShadow());
2146:       g.drawLine(x + 6, y + 12, x + 8, y + 12);
2147:       g.drawLine(x + 10, y + 12, x + 12, y + 12);
2148:       g.setColor(saved);
2149:     }        
2150:   }  
2151:     
2152:   /** The icon returned by {@link #getCheckBoxIcon()}. */
2153:   private static Icon checkBoxIcon;
2154:   
2155:   /** The icon returned by {@link #getCheckBoxMenuItemIcon()}. */
2156:   private static Icon checkBoxMenuItemIcon;
2157:   
2158:   /** The icon returned by {@link #getFileChooserDetailViewIcon()}. */
2159:   private static Icon fileChooserDetailViewIcon;
2160: 
2161:   /** The icon returned by {@link #getFileChooserHomeFolderIcon()}. */
2162:   private static Icon fileChooserHomeFolderIcon;
2163: 
2164:   /** The icon returned by {@link #getFileChooserListViewIcon()}. */
2165:   private static Icon fileChooserListViewIcon;
2166: 
2167:   /** The icon returned by {@link #getFileChooserNewFolderIcon()}. */
2168:   private static Icon fileChooserNewFolderIcon;
2169: 
2170:   /** The icon returned by {@link #getFileChooserUpFolderIcon()}. */
2171:   private static Icon fileChooserUpFolderIcon;
2172: 
2173:   /** The cached RadioButtonIcon instance. */
2174:   private static RadioButtonIcon radioButtonIcon;
2175: 
2176:   /** The icon returned by {@link #getRadioButtonMenuItemIcon()}. */
2177:   private static Icon radioButtonMenuItemIcon;
2178: 
2179:   /** The icon returned by {@link #getInternalFrameDefaultMenuIcon()}. */
2180:   private static Icon internalFrameDefaultMenuIcon;
2181: 
2182:   /** The icon returned by {@link #getTreeComputerIcon()}. */
2183:   private static Icon treeComputerIcon;
2184:   
2185:   /** The icon instance returned by {@link #getTreeFloppyDriveIcon()}. */
2186:   private static Icon treeFloppyDriveIcon;
2187:   
2188:   /** The icon instance returned by {@link #getTreeHardDriveIcon()}. */
2189:   private static Icon treeHardDriveIcon;
2190:   
2191:   /**
2192:    * Creates a new instance.  All the methods are static, so creating an 
2193:    * instance isn't necessary.
2194:    */
2195:   public MetalIconFactory() 
2196:   {
2197:     // Nothing to do here.
2198:   }
2199: 
2200:   /**
2201:    * Returns an icon for use when rendering the {@link JCheckBox} component.
2202:    * 
2203:    * @return A check box icon.
2204:    * 
2205:    * @since 1.3
2206:    */
2207:   public static Icon getCheckBoxIcon() 
2208:   {
2209:     if (checkBoxIcon == null)
2210:       checkBoxIcon = new MetalCheckBoxIcon();
2211:     return checkBoxIcon;
2212:   }
2213:   
2214:   /**
2215:    * Returns an icon for use when rendering the {@link JCheckBoxMenuItem} 
2216:    * component.
2217:    * 
2218:    * @return An icon.
2219:    */
2220:   public static Icon getCheckBoxMenuItemIcon() 
2221:   {
2222:     if (checkBoxMenuItemIcon == null)
2223:       checkBoxMenuItemIcon = new CheckBoxMenuItemIcon();
2224:     return checkBoxMenuItemIcon;
2225:   }
2226: 
2227:   /**
2228:    * Returns an icon for use by the {@link JFileChooser} component.
2229:    * 
2230:    * @return An icon.
2231:    */
2232:   public static Icon getFileChooserDetailViewIcon() 
2233:   {
2234:     if (fileChooserDetailViewIcon == null)
2235:       fileChooserDetailViewIcon = new FileChooserDetailViewIcon();
2236:     return fileChooserDetailViewIcon;
2237:   }
2238:     
2239:   /**
2240:    * Returns an icon for use by the {@link JFileChooser} component.
2241:    * 
2242:    * @return An icon.
2243:    */
2244:   public static Icon getFileChooserHomeFolderIcon() 
2245:   {
2246:     if (fileChooserHomeFolderIcon == null)
2247:       fileChooserHomeFolderIcon = new FileChooserHomeFolderIcon();
2248:     return fileChooserHomeFolderIcon;        
2249:   }
2250:     
2251:   /**
2252:    * Returns an icon for use by the {@link JFileChooser} component.
2253:    * 
2254:    * @return An icon.
2255:    */
2256:   public static Icon getFileChooserListViewIcon() 
2257:   {
2258:     if (fileChooserListViewIcon == null)
2259:       fileChooserListViewIcon = new FileChooserListViewIcon();
2260:     return fileChooserListViewIcon;
2261:   }
2262:     
2263:   /**
2264:    * Returns an icon for use by the {@link JFileChooser} component.
2265:    * 
2266:    * @return An icon.
2267:    */
2268:   public static Icon getFileChooserNewFolderIcon() 
2269:   {
2270:     if (fileChooserNewFolderIcon == null)
2271:       fileChooserNewFolderIcon = new FileChooserNewFolderIcon();
2272:     return fileChooserNewFolderIcon;
2273:   }
2274:     
2275:   /**
2276:    * Returns an icon for use by the {@link JFileChooser} component.
2277:    * 
2278:    * @return An icon.
2279:    */
2280:   public static Icon getFileChooserUpFolderIcon() 
2281:   {
2282:     if (fileChooserUpFolderIcon == null)
2283:       fileChooserUpFolderIcon = new FileChooserUpFolderIcon();
2284:     return fileChooserUpFolderIcon;
2285:   }
2286: 
2287:   /**
2288:    * Returns an icon for RadioButtons in the Metal L&amp;F.
2289:    *
2290:    * @return an icon for RadioButtons in the Metal L&amp;F
2291:    */
2292:   public static Icon getRadioButtonIcon()
2293:   {
2294:     if (radioButtonIcon == null)
2295:       radioButtonIcon = new RadioButtonIcon();
2296:     return radioButtonIcon;
2297:   }
2298: 
2299:   /**
2300:    * Creates a new instance of the icon used in a {@link JRadioButtonMenuItem}.
2301:    * 
2302:    * @return A new icon instance.
2303:    */
2304:   public static Icon getRadioButtonMenuItemIcon() 
2305:   {
2306:     if (radioButtonMenuItemIcon == null)
2307:       radioButtonMenuItemIcon = new RadioButtonMenuItemIcon();
2308:     return radioButtonMenuItemIcon;
2309:   }
2310: 
2311:   /**
2312:    * Returns the icon used to display the thumb for a horizontally oriented
2313:    * {@link JSlider}.
2314:    * 
2315:    * @return The icon.
2316:    */
2317:   public static Icon getHorizontalSliderThumbIcon() 
2318:   {
2319:     return new HorizontalSliderThumbIcon();
2320:   }
2321:     
2322:   /**
2323:    * Creates a new icon used to represent the 'close' button in the title
2324:    * pane of a {@link JInternalFrame}.
2325:    * 
2326:    * @param size  the icon size.
2327:    * 
2328:    * @return A close icon.
2329:    */
2330:   public static Icon getInternalFrameCloseIcon(int size) 
2331:   {
2332:     return new InternalFrameCloseIcon(size);
2333:   }
2334: 
2335:   /**
2336:    * Creates a new icon for the menu in a {@link JInternalFrame}.  This is the
2337:    * icon displayed at the top left of the frame.
2338:    * 
2339:    * @return A menu icon.
2340:    */
2341:   public static Icon getInternalFrameDefaultMenuIcon() 
2342:   {
2343:     if (internalFrameDefaultMenuIcon == null)
2344:       internalFrameDefaultMenuIcon = new InternalFrameDefaultMenuIcon();
2345:     return internalFrameDefaultMenuIcon;
2346:   }
2347:   
2348:   /**
2349:    * Creates a new icon for the 'maximize' button in a {@link JInternalFrame}.
2350:    * 
2351:    * @param size  the icon size in pixels.
2352:    * 
2353:    * @return The icon.
2354:    * 
2355:    * @see #getInternalFrameAltMaximizeIcon(int)
2356:    */
2357:   public static Icon getInternalFrameMaximizeIcon(int size) 
2358:   {
2359:     return new InternalFrameMaximizeIcon();
2360:   }
2361:     
2362:   /**
2363:    * Returns the icon used for the minimize button in the frame title for a
2364:    * {@link JInternalFrame}.
2365:    * 
2366:    * @param size  the icon size in pixels (ignored by this implementation).
2367:    * 
2368:    * @return The icon.
2369:    */
2370:   public static Icon getInternalFrameMinimizeIcon(int size) 
2371:   {
2372:     return new InternalFrameMinimizeIcon();
2373:   }
2374: 
2375:   /**
2376:    * Creates a new icon for the 'restore' button in a {@link JInternalFrame}
2377:    * that has been maximised.
2378:    * 
2379:    * @param size  the icon size in pixels.
2380:    * 
2381:    * @return The icon.
2382:    * 
2383:    * @see #getInternalFrameMaximizeIcon(int)
2384:    */
2385:   public static Icon getInternalFrameAltMaximizeIcon(int size) 
2386:   {
2387:     return new InternalFrameAltMaximizeIcon(size);
2388:   }
2389:   
2390:   /**
2391:    * Returns the icon used to display the thumb for a vertically oriented
2392:    * {@link JSlider}.
2393:    * 
2394:    * @return The icon.
2395:    */
2396:   public static Icon getVerticalSliderThumbIcon() 
2397:   {
2398:     return new VerticalSliderThumbIcon();
2399:   }
2400:     
2401:   /**
2402:    * Creates and returns a new tree folder icon.
2403:    * 
2404:    * @return A new tree folder icon.
2405:    */  
2406:   public static Icon getTreeFolderIcon() 
2407:   {
2408:     return new TreeFolderIcon();
2409:   }
2410:     
2411:   /**
2412:    * Creates and returns a new tree leaf icon.
2413:    * 
2414:    * @return A new tree leaf icon.
2415:    */
2416:   public static Icon getTreeLeafIcon() 
2417:   {
2418:     return new TreeLeafIcon();
2419:   }
2420:   
2421:   /**
2422:    * Creates and returns a tree control icon.
2423:    * 
2424:    * @param isCollapsed  a flag that controls whether the icon is in the 
2425:    *                     collapsed or expanded state.
2426:    * 
2427:    * @return A tree control icon.
2428:    */
2429:   public static Icon getTreeControlIcon(boolean isCollapsed) 
2430:   {
2431:     return new TreeControlIcon(isCollapsed);
2432:   }
2433: 
2434:   /**
2435:    * Returns a <code>16x16</code> icon representing a computer.
2436:    * 
2437:    * @return The icon.
2438:    */
2439:   public static Icon getTreeComputerIcon() 
2440:   {
2441:     if (treeComputerIcon == null)
2442:       treeComputerIcon = new TreeComputerIcon();
2443:     return treeComputerIcon;        
2444:   }
2445:     
2446:   /**
2447:    * Returns a <code>16x16</code> icon representing a floppy disk.
2448:    * 
2449:    * @return The icon.
2450:    */
2451:   public static Icon getTreeFloppyDriveIcon() 
2452:   {
2453:     if (treeFloppyDriveIcon == null)
2454:       treeFloppyDriveIcon = new TreeFloppyDriveIcon();
2455:     return treeFloppyDriveIcon;
2456:   }
2457:     
2458:   /**
2459:    * Returns a <code>16x16</code> icon representing a hard disk.
2460:    * 
2461:    * @return The icon.
2462:    */
2463:   public static Icon getTreeHardDriveIcon() 
2464:   {
2465:     if (treeHardDriveIcon == null)
2466:       treeHardDriveIcon = new TreeHardDriveIcon();
2467:     return treeHardDriveIcon;
2468:   }
2469: 
2470: }