1:
37:
38:
39: package ;
40:
41: import ;
42: import ;
43: import ;
44: import ;
45: import ;
46: import ;
47: import ;
48: import ;
49: import ;
50: import ;
51: import ;
52: import ;
53: import ;
54: import ;
55: import ;
56: import ;
57: import ;
58:
59: import ;
60: import ;
61: import ;
62: import ;
63: import ;
64: import ;
65: import ;
66: import ;
67: import ;
68: import ;
69: import ;
70: import ;
71: import ;
72:
73:
77: public class BasicProgressBarUI extends ProgressBarUI
78: {
79:
87: public class ChangeHandler implements ChangeListener
88: {
89:
94: public void stateChanged(ChangeEvent e)
95: {
96:
97: progressBar.repaint();
98: }
99: }
100:
101:
105: private class PropertyChangeHandler implements PropertyChangeListener
106: {
107:
113: public void propertyChange(PropertyChangeEvent e)
114: {
115:
116:
117: if (e.getPropertyName().equals("indeterminate"))
118: if (((Boolean) e.getNewValue()).booleanValue()
119: && progressBar.isShowing())
120: startAnimationTimer();
121: else
122: stopAnimationTimer();
123: }
124: }
125:
126:
132: private class AncestorHandler implements AncestorListener
133: {
134:
135:
141: public void ancestorAdded(AncestorEvent event)
142: {
143: if (progressBar.isIndeterminate())
144: startAnimationTimer();
145: }
146:
147:
153: public void ancestorRemoved(AncestorEvent event)
154: {
155: stopAnimationTimer();
156: }
157:
158:
162: public void ancestorMoved(AncestorEvent event)
163: {
164:
165: }
166:
167: }
168:
169:
174: private class Animator implements ActionListener
175: {
176:
182: public void actionPerformed(ActionEvent e)
183: {
184:
185:
186: incrementAnimationIndex();
187: }
188: }
189:
190:
197: private class ComponentHandler extends ComponentAdapter
198: {
199:
206: public void componentResized(ComponentEvent e)
207: {
208: boxDependent = -1;
209: boxIndependent = -1;
210: incr = -1;
211: }
212: }
213:
214:
219: protected Rectangle boxRect;
220:
221:
222: private transient Timer animationTimer;
223:
224:
225:
226:
227:
228:
229:
230:
231:
232:
233:
234:
235: private transient int animationIndex;
236:
237:
238: private transient int numFrames;
239:
240:
241: private transient Animator animation;
242:
243:
244: private transient PropertyChangeHandler propertyListener;
245:
246:
247: protected ChangeListener changeListener;
248:
249:
250: protected JProgressBar progressBar;
251:
252:
253:
258: transient double boxDependent = - 1;
259:
260:
265: transient int boxIndependent = - 1;
266:
267:
271: transient double incr = -1;
272:
273:
274: private transient int cellLength;
275:
276:
277: private transient int cellSpacing;
278:
279:
280: private transient Color selectionBackground;
281:
282:
283: private transient Color selectionForeground;
284:
285:
289: private AncestorListener ancestorListener;
290:
291:
295: private ComponentListener componentListener;
296:
297:
300: public BasicProgressBarUI()
301: {
302: super();
303: }
304:
305:
312: public static ComponentUI createUI(JComponent x)
313: {
314: return new BasicProgressBarUI();
315: }
316:
317:
328: protected int getAmountFull(Insets b, int width, int height)
329: {
330: double percentDone = progressBar.getPercentComplete();
331: if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
332: return (int) (percentDone * (width - b.left - b.right));
333: else
334: return (int) (percentDone * (height - b.top - b.bottom));
335: }
336:
337:
342: protected int getAnimationIndex()
343: {
344: return animationIndex;
345: }
346:
347:
357: protected Rectangle getBox(Rectangle r)
358: {
359: if (!progressBar.isIndeterminate())
360: return null;
361: if (r == null)
362: r = new Rectangle();
363:
364: Rectangle vr = new Rectangle();
365: SwingUtilities.calculateInnerArea(progressBar, vr);
366:
367:
368: if (incr == -1 || boxDependent == -1 || boxIndependent == -1)
369: {
370:
371: int iterations = numFrames / 2;
372: if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
373: {
374: boxDependent = vr.width / 6.;
375: incr = ((double) (vr.width - boxDependent)) / (double) iterations;
376: boxIndependent = vr.height;
377: }
378: else
379: {
380: boxDependent = vr.height / 6.;
381: incr = ((double) (vr.height - boxDependent)) / (double) iterations;
382: boxIndependent = vr.width;
383: }
384: }
385:
386: int index = getAnimationIndex();
387: if (animationIndex > numFrames / 2)
388: index = numFrames - getAnimationIndex();
389:
390: if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
391: {
392: r.x = vr.x + (int) (incr * index);
393: r.y = vr.y;
394: r.width = (int) boxDependent;
395: r.height = (int) boxIndependent;
396: }
397: else
398: {
399: r.x = vr.x;
400: r.y = vr.height - (int) (incr * index) + vr.y - (int) boxDependent;
401: r.width = (int) boxIndependent;
402: r.height = (int) boxDependent;
403: }
404: return r;
405: }
406:
407:
412: protected int getCellLength()
413: {
414: return cellLength;
415: }
416:
417:
422: protected int getCellSpacing()
423: {
424: return cellSpacing;
425: }
426:
427:
436: public Dimension getMaximumSize(JComponent c)
437: {
438: Insets insets = c.getInsets();
439: Dimension ret;
440: int orientation = progressBar.getOrientation();
441: if (orientation == JProgressBar.VERTICAL)
442: {
443: ret = getPreferredInnerVertical();
444: ret.height = Short.MAX_VALUE;
445: ret.width += insets.left + insets.right;
446: }
447: else
448: {
449: ret = getPreferredInnerHorizontal();
450: ret.width = Short.MAX_VALUE;
451: ret.height += insets.top + insets.bottom;
452: }
453: return ret;
454: }
455:
456:
465: public Dimension getMinimumSize(JComponent c)
466: {
467: Insets insets = c.getInsets();
468: Dimension ret;
469: int orientation = progressBar.getOrientation();
470: if (orientation == JProgressBar.VERTICAL)
471: {
472: ret = getPreferredInnerVertical();
473: ret.height = 10;
474: ret.width += insets.left + insets.right;
475: }
476: else
477: {
478: ret = getPreferredInnerHorizontal();
479: ret.width = 10;
480: ret.height += insets.top + insets.bottom;
481: }
482: return ret;
483: }
484:
485:
493: protected Dimension getPreferredInnerHorizontal()
494: {
495: Font font = progressBar.getFont();
496: FontMetrics fm = progressBar.getFontMetrics(font);
497:
498: int stringWidth = 0;
499: String str = progressBar.getString();
500: if (str != null)
501: stringWidth = fm.stringWidth(progressBar.getString());
502: Insets i = progressBar.getInsets();
503: int prefWidth = Math.max(200 - i.left - i.right, stringWidth);
504:
505: int stringHeight = 0;
506: if (str != null)
507: stringHeight = fm.getHeight();
508: int prefHeight = Math.max(16 - i.top - i.bottom, stringHeight);
509:
510: return new Dimension(prefWidth, prefHeight);
511: }
512:
513:
521: protected Dimension getPreferredInnerVertical()
522: {
523: Font font = progressBar.getFont();
524: FontMetrics fm = progressBar.getFontMetrics(font);
525:
526: int stringWidth = 0;
527: String str = progressBar.getString();
528: if (str != null)
529: stringWidth = fm.stringWidth(progressBar.getString());
530: Insets i = progressBar.getInsets();
531: int prefHeight = Math.max(200 - i.left - i.right, stringWidth);
532:
533: int stringHeight = 0;
534: if (str != null)
535: stringHeight = fm.getHeight();
536: int prefWidth = Math.max(16 - i.top - i.bottom, stringHeight);
537:
538: return new Dimension(prefWidth, prefHeight);
539: }
540:
541:
550: public Dimension getPreferredSize(JComponent c)
551: {
552: Insets insets = c.getInsets();
553: Dimension ret;
554: int orientation = progressBar.getOrientation();
555: if (orientation == JProgressBar.VERTICAL)
556: ret = getPreferredInnerVertical();
557: else
558: ret = getPreferredInnerHorizontal();
559: ret.width += insets.left + insets.right;
560: ret.height += insets.top + insets.bottom;
561: return ret;
562: }
563:
564:
570: protected Color getSelectionBackground()
571: {
572: return selectionBackground;
573: }
574:
575:
581: protected Color getSelectionForeground()
582: {
583: return selectionForeground;
584: }
585:
586:
599: protected Point getStringPlacement(Graphics g, String progressString, int x,
600: int y, int width, int height)
601: {
602: Rectangle tr = new Rectangle();
603: Rectangle vr = new Rectangle(x, y, width, height);
604: Rectangle ir = new Rectangle();
605:
606: Font f = g.getFont();
607: FontMetrics fm = g.getFontMetrics(f);
608:
609: SwingUtilities.layoutCompoundLabel(progressBar, fm, progressString, null,
610: SwingConstants.CENTER,
611: SwingConstants.CENTER,
612: SwingConstants.CENTER,
613: SwingConstants.CENTER, vr, ir, tr, 0);
614: return new Point(tr.x, tr.y);
615: }
616:
617:
620: protected void incrementAnimationIndex()
621: {
622: animationIndex++;
623:
624: if (animationIndex >= numFrames)
625: animationIndex = 0;
626: progressBar.repaint();
627: }
628:
629:
636: public void paint(Graphics g, JComponent c)
637: {
638: if (! progressBar.isIndeterminate())
639: paintDeterminate(g, c);
640: else
641: paintIndeterminate(g, c);
642: }
643:
644:
651: protected void paintDeterminate(Graphics g, JComponent c)
652: {
653: Color saved = g.getColor();
654: int space = getCellSpacing();
655: int len = getCellLength();
656: int max = progressBar.getMaximum();
657: int min = progressBar.getMinimum();
658: int value = progressBar.getValue();
659:
660: Rectangle vr = SwingUtilities.calculateInnerArea(c, new Rectangle());
661: Rectangle or = progressBar.getBounds();
662: Insets insets = c.getInsets();
663:
664: int amountFull = getAmountFull(insets, or.width, or.height);
665:
666: if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
667: {
668: g.setColor(c.getForeground());
669: g.fillRect(vr.x, vr.y, amountFull, vr.height);
670: }
671: else
672: {
673: g.setColor(c.getForeground());
674: g.fillRect(vr.x, vr.y + vr.height - amountFull, vr.width,
675: amountFull);
676: }
677:
678: if (progressBar.isStringPainted() && !progressBar.getString().equals(""))
679: paintString(g, 0, 0, or.width, or.height, amountFull, insets);
680: g.setColor(saved);
681: }
682:
683:
690: protected void paintIndeterminate(Graphics g, JComponent c)
691: {
692:
693:
694: Color saved = g.getColor();
695: Insets insets = c.getInsets();
696:
697: Rectangle or = c.getBounds();
698: Rectangle vr = new Rectangle();
699: SwingUtilities.calculateInnerArea(c, vr);
700:
701: g.setColor(c.getBackground());
702: g.fillRect(vr.x, vr.y, vr.width, vr.height);
703:
704: boxRect = getBox(boxRect);
705:
706: g.setColor(c.getForeground());
707: g.fillRect(boxRect.x, boxRect.y, boxRect.width, boxRect.height);
708:
709: if (progressBar.isStringPainted() && !progressBar.getString().equals(""))
710: paintString(g, 0, 0, or.width, or.height,
711: getAmountFull(insets, or.width, or.height), insets);
712:
713: g.setColor(saved);
714: }
715:
716:
727: protected void paintString(Graphics g, int x, int y, int width, int height,
728: int amountFull, Insets b)
729: {
730: String str = progressBar.getString();
731: int full = getAmountFull(b, width, height);
732: Point placement = getStringPlacement(g, progressBar.getString(),
733: x + b.left, y + b.top,
734: width - b.left - b.right,
735: height - b.top - b.bottom);
736: Color savedColor = g.getColor();
737: Shape savedClip = g.getClip();
738: FontMetrics fm = g.getFontMetrics(progressBar.getFont());
739:
740: if (progressBar.getOrientation() == JProgressBar.VERTICAL)
741: {
742: AffineTransform rotate = AffineTransform.getRotateInstance(Math.PI / 2);
743: g.setFont(progressBar.getFont().deriveFont(rotate));
744: }
745:
746: g.setColor(getSelectionForeground());
747: g.setClip(0, 0, full + b.left, height);
748: g.drawString(str, placement.x, placement.y + fm.getAscent());
749: g.setColor(getSelectionBackground());
750: g.setClip(full + b.left, 0, width - full, height);
751: g.drawString(str, placement.x, placement.y + fm.getAscent());
752: g.setClip(savedClip);
753: g.setColor(savedColor);
754: }
755:
756:
762: protected void setAnimationIndex(int newValue)
763: {
764: animationIndex = (newValue <= numFrames) ? newValue : 0;
765: progressBar.repaint();
766: }
767:
768:
773: protected void setCellLength(int cellLen)
774: {
775: cellLength = cellLen;
776: }
777:
778:
783: protected void setCellSpacing(int cellSpace)
784: {
785: cellSpacing = cellSpace;
786: }
787:
788:
795: protected void startAnimationTimer()
796: {
797: if (animationTimer != null)
798: animationTimer.start();
799: }
800:
801:
808: protected void stopAnimationTimer()
809: {
810: if (animationTimer != null)
811: animationTimer.stop();
812: setAnimationIndex(0);
813: }
814:
815:
819: protected void installDefaults()
820: {
821: LookAndFeel.installColorsAndFont(progressBar, "ProgressBar.background",
822: "ProgressBar.foreground",
823: "ProgressBar.font");
824: LookAndFeel.installBorder(progressBar, "ProgressBar.border");
825: progressBar.setOpaque(true);
826:
827: selectionForeground = UIManager.getColor("ProgressBar.selectionForeground");
828: selectionBackground = UIManager.getColor("ProgressBar.selectionBackground");
829: cellLength = UIManager.getInt("ProgressBar.cellLength");
830: cellSpacing = UIManager.getInt("ProgressBar.cellSpacing");
831:
832: int repaintInterval = UIManager.getInt("ProgressBar.repaintInterval");
833: int cycleTime = UIManager.getInt("ProgressBar.cycleTime");
834:
835: if (cycleTime % repaintInterval != 0
836: && (cycleTime / repaintInterval) % 2 != 0)
837: {
838: int div = (cycleTime / repaintInterval) + 2;
839: div /= 2;
840: div *= 2;
841: cycleTime = div * repaintInterval;
842: }
843: setAnimationIndex(0);
844: numFrames = cycleTime / repaintInterval;
845: animationTimer.setDelay(repaintInterval);
846: }
847:
848:
852: protected void uninstallDefaults()
853: {
854: progressBar.setFont(null);
855: progressBar.setForeground(null);
856: progressBar.setBackground(null);
857:
858: selectionForeground = null;
859: selectionBackground = null;
860: }
861:
862:
866: protected void installListeners()
867: {
868: changeListener = new ChangeHandler();
869: propertyListener = new PropertyChangeHandler();
870: animation = new Animator();
871:
872: progressBar.addChangeListener(changeListener);
873: progressBar.addPropertyChangeListener(propertyListener);
874: animationTimer.addActionListener(animation);
875:
876: ancestorListener = new AncestorHandler();
877: progressBar.addAncestorListener(ancestorListener);
878:
879: componentListener = new ComponentHandler();
880: progressBar.addComponentListener(componentListener);
881: }
882:
883:
887: protected void uninstallListeners()
888: {
889: progressBar.removeChangeListener(changeListener);
890: progressBar.removePropertyChangeListener(propertyListener);
891: animationTimer.removeActionListener(animation);
892:
893: changeListener = null;
894: propertyListener = null;
895: animation = null;
896:
897: if (ancestorListener != null)
898: progressBar.removeAncestorListener(ancestorListener);
899: ancestorListener = null;
900:
901: if (componentListener != null)
902: progressBar.removeComponentListener(componentListener);
903: componentListener = null;
904: }
905:
906:
914: public void installUI(JComponent c)
915: {
916: super.installUI(c);
917: if (c instanceof JProgressBar)
918: {
919: progressBar = (JProgressBar) c;
920:
921: animationTimer = new Timer(200, null);
922: animationTimer.setRepeats(true);
923:
924: installDefaults();
925: installListeners();
926: }
927: if (progressBar.isIndeterminate())
928: startAnimationTimer();
929: }
930:
931:
938: public void uninstallUI(JComponent c)
939: {
940: super.uninstallUI(c);
941: uninstallListeners();
942: uninstallDefaults();
943:
944: animationTimer = null;
945: progressBar = null;
946: }
947:
948: }