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: import ;
59: import ;
60:
61: import ;
62: import ;
63:
64:
76: public class Container extends Component
77: {
78:
81: private static final long serialVersionUID = 4613797578919906343L;
82:
83:
84: int ncomponents;
85: Component[] component;
86: LayoutManager layoutMgr;
87:
88: LightweightDispatcher dispatcher;
89:
90: Dimension maxSize;
91:
92:
95: boolean focusCycleRoot;
96:
97: int containerSerializedDataVersion;
98:
99:
100: transient ContainerListener containerListener;
101: transient PropertyChangeSupport changeSupport;
102:
103:
105: private FocusTraversalPolicy focusTraversalPolicy;
106:
107:
116: transient Set[] focusTraversalKeys;
117:
118:
121: public Container()
122: {
123: }
124:
125:
130: public int getComponentCount()
131: {
132: return countComponents ();
133: }
134:
135:
142: public int countComponents()
143: {
144: return ncomponents;
145: }
146:
147:
156: public Component getComponent(int n)
157: {
158: synchronized (getTreeLock ())
159: {
160: if (n < 0 || n >= ncomponents)
161: throw new ArrayIndexOutOfBoundsException("no such component");
162:
163: return component[n];
164: }
165: }
166:
167:
172: public Component[] getComponents()
173: {
174: synchronized (getTreeLock ())
175: {
176: Component[] result = new Component[ncomponents];
177:
178: if (ncomponents > 0)
179: System.arraycopy(component, 0, result, 0, ncomponents);
180:
181: return result;
182: }
183: }
184:
185:
188:
189: protected void swapComponents (int i, int j)
190: {
191: synchronized (getTreeLock ())
192: {
193: if (i < 0
194: || i >= component.length
195: || j < 0
196: || j >= component.length)
197: throw new ArrayIndexOutOfBoundsException ();
198: Component tmp = component[i];
199: component[i] = component[j];
200: component[j] = tmp;
201: }
202: }
203:
204:
210: public Insets getInsets()
211: {
212: return insets ();
213: }
214:
215:
222: public Insets insets()
223: {
224: if (peer == null)
225: return new Insets (0, 0, 0, 0);
226:
227: return ((ContainerPeer) peer).getInsets ();
228: }
229:
230:
238: public Component add(Component comp)
239: {
240: addImpl(comp, null, -1);
241: return comp;
242: }
243:
244:
256: public Component add(String name, Component comp)
257: {
258: addImpl(comp, name, -1);
259: return comp;
260: }
261:
262:
274: public Component add(Component comp, int index)
275: {
276: addImpl(comp, null, index);
277: return comp;
278: }
279:
280:
288: public void add(Component comp, Object constraints)
289: {
290: addImpl(comp, constraints, -1);
291: }
292:
293:
305: public void add(Component comp, Object constraints, int index)
306: {
307: addImpl(comp, constraints, index);
308: }
309:
310:
325: protected void addImpl(Component comp, Object constraints, int index)
326: {
327: synchronized (getTreeLock ())
328: {
329: if (index > ncomponents
330: || (index < 0 && index != -1)
331: || comp instanceof Window
332: || (comp instanceof Container
333: && ((Container) comp).isAncestorOf(this)))
334: throw new IllegalArgumentException();
335:
336:
337:
338: if (comp.parent != null)
339: comp.parent.remove(comp);
340: comp.parent = this;
341: if (peer != null)
342: {
343: if (comp.isLightweight ())
344: {
345: enableEvents (comp.eventMask);
346: if (!isLightweight ())
347: enableEvents (AWTEvent.PAINT_EVENT_MASK);
348: }
349: }
350:
351: invalidate();
352:
353: if (component == null)
354: component = new Component[4];
355:
356:
357:
358: if (ncomponents >= component.length)
359: {
360: int nl = component.length * 2;
361: Component[] c = new Component[nl];
362: System.arraycopy(component, 0, c, 0, ncomponents);
363: component = c;
364: }
365:
366: if (index == -1)
367: component[ncomponents++] = comp;
368: else
369: {
370: System.arraycopy(component, index, component, index + 1,
371: ncomponents - index);
372: component[index] = comp;
373: ++ncomponents;
374: }
375:
376:
377: if (layoutMgr != null)
378: {
379: if (layoutMgr instanceof LayoutManager2)
380: {
381: LayoutManager2 lm2 = (LayoutManager2) layoutMgr;
382: lm2.addLayoutComponent(comp, constraints);
383: }
384: else if (constraints instanceof String)
385: layoutMgr.addLayoutComponent((String) constraints, comp);
386: else
387: layoutMgr.addLayoutComponent(null, comp);
388: }
389:
390: if (isShowing ())
391: {
392:
393: ContainerEvent ce = new ContainerEvent(this,
394: ContainerEvent.COMPONENT_ADDED,
395: comp);
396: getToolkit().getSystemEventQueue().postEvent(ce);
397: }
398: }
399: }
400:
401:
406: public void remove(int index)
407: {
408: synchronized (getTreeLock ())
409: {
410: Component r = component[index];
411:
412: r.removeNotify();
413:
414: System.arraycopy(component, index + 1, component, index,
415: ncomponents - index - 1);
416: component[--ncomponents] = null;
417:
418: invalidate();
419:
420: if (layoutMgr != null)
421: layoutMgr.removeLayoutComponent(r);
422:
423: r.parent = null;
424:
425: if (isShowing ())
426: {
427:
428: ContainerEvent ce = new ContainerEvent(this,
429: ContainerEvent.COMPONENT_REMOVED,
430: r);
431: getToolkit().getSystemEventQueue().postEvent(ce);
432: }
433: }
434: }
435:
436:
441: public void remove(Component comp)
442: {
443: synchronized (getTreeLock ())
444: {
445: for (int i = 0; i < ncomponents; ++i)
446: {
447: if (component[i] == comp)
448: {
449: remove(i);
450: break;
451: }
452: }
453: }
454: }
455:
456:
459: public void removeAll()
460: {
461: synchronized (getTreeLock ())
462: {
463: while (ncomponents > 0)
464: remove(0);
465: }
466: }
467:
468:
473: public LayoutManager getLayout()
474: {
475: return layoutMgr;
476: }
477:
478:
484: public void setLayout(LayoutManager mgr)
485: {
486: layoutMgr = mgr;
487: invalidate();
488: }
489:
490:
493: public void doLayout()
494: {
495: layout ();
496: }
497:
498:
503: public void layout()
504: {
505: if (layoutMgr != null)
506: layoutMgr.layoutContainer (this);
507: }
508:
509:
513: public void invalidate()
514: {
515: super.invalidate();
516: }
517:
518:
521: public void validate()
522: {
523: synchronized (getTreeLock ())
524: {
525: if (! isValid() && peer != null)
526: {
527: validateTree();
528: }
529: }
530: }
531:
532:
535: void invalidateTree()
536: {
537: for (int i = 0; i < ncomponents; i++)
538: {
539: Component comp = component[i];
540: comp.invalidate();
541: if (comp instanceof Container)
542: ((Container) comp).invalidateTree();
543: }
544: }
545:
546:
550: protected void validateTree()
551: {
552: if (valid)
553: return;
554:
555: ContainerPeer cPeer = null;
556: if (peer != null && ! (peer instanceof LightweightPeer))
557: {
558: cPeer = (ContainerPeer) peer;
559: cPeer.beginValidate();
560: }
561:
562: for (int i = 0; i < ncomponents; ++i)
563: {
564: Component comp = component[i];
565:
566: if (comp.getPeer () == null)
567: comp.addNotify();
568: }
569:
570: doLayout ();
571: for (int i = 0; i < ncomponents; ++i)
572: {
573: Component comp = component[i];
574:
575: if (! comp.isValid())
576: {
577: if (comp instanceof Container)
578: {
579: ((Container) comp).validateTree();
580: }
581: else
582: {
583: component[i].validate();
584: }
585: }
586: }
587:
588:
591: valid = true;
592:
593: if (cPeer != null)
594: cPeer.endValidate();
595: }
596:
597: public void setFont(Font f)
598: {
599: super.setFont(f);
600:
601:
602:
603: invalidateTree();
604: }
605:
606:
611: public Dimension getPreferredSize()
612: {
613: return preferredSize ();
614: }
615:
616:
623: public Dimension preferredSize()
624: {
625: if (layoutMgr != null)
626: return layoutMgr.preferredLayoutSize (this);
627: else
628: return super.preferredSize ();
629: }
630:
631:
636: public Dimension getMinimumSize()
637: {
638: return minimumSize ();
639: }
640:
641:
648: public Dimension minimumSize()
649: {
650: if (layoutMgr != null)
651: return layoutMgr.minimumLayoutSize (this);
652: else
653: return super.minimumSize ();
654: }
655:
656:
661: public Dimension getMaximumSize()
662: {
663: if (layoutMgr != null && layoutMgr instanceof LayoutManager2)
664: {
665: LayoutManager2 lm2 = (LayoutManager2) layoutMgr;
666: return lm2.maximumLayoutSize(this);
667: }
668: else
669: return super.getMaximumSize();
670: }
671:
672:
679: public float getAlignmentX()
680: {
681: if (layoutMgr instanceof LayoutManager2)
682: {
683: LayoutManager2 lm2 = (LayoutManager2) layoutMgr;
684: return lm2.getLayoutAlignmentX(this);
685: }
686: else
687: return super.getAlignmentX();
688: }
689:
690:
697: public float getAlignmentY()
698: {
699: if (layoutMgr instanceof LayoutManager2)
700: {
701: LayoutManager2 lm2 = (LayoutManager2) layoutMgr;
702: return lm2.getLayoutAlignmentY(this);
703: }
704: else
705: return super.getAlignmentY();
706: }
707:
708:
717: public void paint(Graphics g)
718: {
719: if (!isShowing())
720: return;
721:
722: super.paint(g);
723:
724:
725: visitChildren(g, GfxPaintVisitor.INSTANCE, false);
726: }
727:
728:
737: public void update(Graphics g)
738: {
739: super.update(g);
740: }
741:
742:
751: public void print(Graphics g)
752: {
753: super.print(g);
754: visitChildren(g, GfxPrintVisitor.INSTANCE, true);
755: }
756:
757:
762: public void paintComponents(Graphics g)
763: {
764: super.paint(g);
765: visitChildren(g, GfxPaintAllVisitor.INSTANCE, true);
766: }
767:
768:
773: public void printComponents(Graphics g)
774: {
775: super.paint(g);
776: visitChildren(g, GfxPrintAllVisitor.INSTANCE, true);
777: }
778:
779:
785: public synchronized void addContainerListener(ContainerListener listener)
786: {
787: containerListener = AWTEventMulticaster.add(containerListener, listener);
788: }
789:
790:
796: public synchronized void removeContainerListener(ContainerListener listener)
797: {
798: containerListener = AWTEventMulticaster.remove(containerListener, listener);
799: }
800:
801:
804: public synchronized ContainerListener[] getContainerListeners()
805: {
806: return (ContainerListener[])
807: AWTEventMulticaster.getListeners(containerListener,
808: ContainerListener.class);
809: }
810:
811:
821: public EventListener[] getListeners(Class listenerType)
822: {
823: if (listenerType == ContainerListener.class)
824: return getContainerListeners();
825: return super.getListeners(listenerType);
826: }
827:
828:
836: protected void processEvent(AWTEvent e)
837: {
838: if (e instanceof ContainerEvent)
839: processContainerEvent((ContainerEvent) e);
840: else
841: super.processEvent(e);
842: }
843:
844:
850: protected void processContainerEvent(ContainerEvent e)
851: {
852: if (containerListener == null)
853: return;
854: switch (e.id)
855: {
856: case ContainerEvent.COMPONENT_ADDED:
857: containerListener.componentAdded(e);
858: break;
859:
860: case ContainerEvent.COMPONENT_REMOVED:
861: containerListener.componentRemoved(e);
862: break;
863: }
864: }
865:
866:
873: public void deliverEvent(Event e)
874: {
875: if (!handleEvent (e))
876: {
877: synchronized (getTreeLock ())
878: {
879: Component parent = getParent ();
880:
881: if (parent != null)
882: parent.deliverEvent (e);
883: }
884: }
885: }
886:
887:
901: public Component getComponentAt(int x, int y)
902: {
903: return locate (x, y);
904: }
905:
906:
922: public Component locate(int x, int y)
923: {
924: synchronized (getTreeLock ())
925: {
926: if (!contains (x, y))
927: return null;
928: for (int i = 0; i < ncomponents; ++i)
929: {
930:
931: if (!component[i].isVisible ())
932: continue;
933:
934: int x2 = x - component[i].x;
935: int y2 = y - component[i].y;
936: if (component[i].contains (x2, y2))
937: return component[i];
938: }
939: return this;
940: }
941: }
942:
943:
955: public Component getComponentAt(Point p)
956: {
957: return getComponentAt (p.x, p.y);
958: }
959:
960: public Component findComponentAt(int x, int y)
961: {
962: synchronized (getTreeLock ())
963: {
964: if (! contains(x, y))
965: return null;
966:
967: for (int i = 0; i < ncomponents; ++i)
968: {
969:
970: if (!component[i].isVisible())
971: continue;
972:
973: int x2 = x - component[i].x;
974: int y2 = y - component[i].y;
975:
976:
977: if (component[i] instanceof Container)
978: {
979: Container k = (Container) component[i];
980: Component r = k.findComponentAt(x2, y2);
981: if (r != null)
982: return r;
983: }
984: else if (component[i].contains(x2, y2))
985: return component[i];
986: }
987:
988: return this;
989: }
990: }
991:
992: public Component findComponentAt(Point p)
993: {
994: return findComponentAt(p.x, p.y);
995: }
996:
997:
1002: public void addNotify()
1003: {
1004: super.addNotify();
1005: addNotifyContainerChildren();
1006: }
1007:
1008:
1013: public void removeNotify()
1014: {
1015: synchronized (getTreeLock ())
1016: {
1017: for (int i = 0; i < ncomponents; ++i)
1018: component[i].removeNotify();
1019: super.removeNotify();
1020: }
1021: }
1022:
1023:
1032: public boolean isAncestorOf(Component comp)
1033: {
1034: synchronized (getTreeLock ())
1035: {
1036: while (true)
1037: {
1038: if (comp == null)
1039: return false;
1040: if (comp == this)
1041: return true;
1042: comp = comp.getParent();
1043: }
1044: }
1045: }
1046:
1047:
1053: protected String paramString()
1054: {
1055: if (layoutMgr == null)
1056: return super.paramString();
1057:
1058: StringBuffer sb = new StringBuffer();
1059: sb.append(super.paramString());
1060: sb.append(",layout=");
1061: sb.append(layoutMgr.getClass().getName());
1062: return sb.toString();
1063: }
1064:
1065:
1072: public void list(PrintStream out, int indent)
1073: {
1074: synchronized (getTreeLock ())
1075: {
1076: super.list(out, indent);
1077: for (int i = 0; i < ncomponents; ++i)
1078: component[i].list(out, indent + 2);
1079: }
1080: }
1081:
1082:
1089: public void list(PrintWriter out, int indent)
1090: {
1091: synchronized (getTreeLock ())
1092: {
1093: super.list(out, indent);
1094: for (int i = 0; i < ncomponents; ++i)
1095: component[i].list(out, indent + 2);
1096: }
1097: }
1098:
1099:
1115: public void setFocusTraversalKeys(int id, Set keystrokes)
1116: {
1117: if (id != KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS &&
1118: id != KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS &&
1119: id != KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS &&
1120: id != KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS)
1121: throw new IllegalArgumentException ();
1122:
1123: if (keystrokes == null)
1124: {
1125: Container parent = getParent ();
1126:
1127: while (parent != null)
1128: {
1129: if (parent.areFocusTraversalKeysSet (id))
1130: {
1131: keystrokes = parent.getFocusTraversalKeys (id);
1132: break;
1133: }
1134: parent = parent.getParent ();
1135: }
1136:
1137: if (keystrokes == null)
1138: keystrokes = KeyboardFocusManager.getCurrentKeyboardFocusManager ().
1139: getDefaultFocusTraversalKeys (id);
1140: }
1141:
1142: Set sa;
1143: Set sb;
1144: Set sc;
1145: String name;
1146: switch (id)
1147: {
1148: case KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS:
1149: sa = getFocusTraversalKeys
1150: (KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS);
1151: sb = getFocusTraversalKeys
1152: (KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS);
1153: sc = getFocusTraversalKeys
1154: (KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS);
1155: name = "forwardFocusTraversalKeys";
1156: break;
1157: case KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS:
1158: sa = getFocusTraversalKeys
1159: (KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS);
1160: sb = getFocusTraversalKeys
1161: (KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS);
1162: sc = getFocusTraversalKeys
1163: (KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS);
1164: name = "backwardFocusTraversalKeys";
1165: break;
1166: case KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS:
1167: sa = getFocusTraversalKeys
1168: (KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS);
1169: sb = getFocusTraversalKeys
1170: (KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS);
1171: sc = getFocusTraversalKeys
1172: (KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS);
1173: name = "upCycleFocusTraversalKeys";
1174: break;
1175: case KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS:
1176: sa = getFocusTraversalKeys
1177: (KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS);
1178: sb = getFocusTraversalKeys
1179: (KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS);
1180: sc = getFocusTraversalKeys
1181: (KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS);
1182: name = "downCycleFocusTraversalKeys";
1183: break;
1184: default:
1185: throw new IllegalArgumentException ();
1186: }
1187:
1188: int i = keystrokes.size ();
1189: Iterator iter = keystrokes.iterator ();
1190:
1191: while (--i >= 0)
1192: {
1193: Object o = iter.next ();
1194: if (!(o instanceof AWTKeyStroke)
1195: || sa.contains (o) || sb.contains (o) || sc.contains (o)
1196: || ((AWTKeyStroke) o).keyCode == KeyEvent.VK_UNDEFINED)
1197: throw new IllegalArgumentException ();
1198: }
1199:
1200: if (focusTraversalKeys == null)
1201: focusTraversalKeys = new Set[3];
1202:
1203: keystrokes = Collections.unmodifiableSet (new HashSet (keystrokes));
1204: firePropertyChange (name, focusTraversalKeys[id], keystrokes);
1205:
1206: focusTraversalKeys[id] = keystrokes;
1207: }
1208:
1209:
1221: public Set getFocusTraversalKeys (int id)
1222: {
1223: if (id != KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS &&
1224: id != KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS &&
1225: id != KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS &&
1226: id != KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS)
1227: throw new IllegalArgumentException ();
1228:
1229: Set s = null;
1230:
1231: if (focusTraversalKeys != null)
1232: s = focusTraversalKeys[id];
1233:
1234: if (s == null && parent != null)
1235: s = parent.getFocusTraversalKeys (id);
1236:
1237: return s == null ? (KeyboardFocusManager.getCurrentKeyboardFocusManager()
1238: .getDefaultFocusTraversalKeys(id)) : s;
1239: }
1240:
1241:
1255: public boolean areFocusTraversalKeysSet (int id)
1256: {
1257: if (id != KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS &&
1258: id != KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS &&
1259: id != KeyboardFocusManager.UP_CYCLE_TRAVERSAL_KEYS &&
1260: id != KeyboardFocusManager.DOWN_CYCLE_TRAVERSAL_KEYS)
1261: throw new IllegalArgumentException ();
1262:
1263: return focusTraversalKeys != null && focusTraversalKeys[id] != null;
1264: }
1265:
1266:
1281: public boolean isFocusCycleRoot (Container c)
1282: {
1283: if (this == c
1284: && isFocusCycleRoot ())
1285: return true;
1286:
1287: Container ancestor = getFocusCycleRootAncestor ();
1288:
1289: if (c == ancestor)
1290: return true;
1291:
1292: return false;
1293: }
1294:
1295:
1307: public void setFocusTraversalPolicy (FocusTraversalPolicy policy)
1308: {
1309: focusTraversalPolicy = policy;
1310: }
1311:
1312:
1323: public FocusTraversalPolicy getFocusTraversalPolicy ()
1324: {
1325: if (!isFocusCycleRoot ())
1326: return null;
1327:
1328: if (focusTraversalPolicy == null)
1329: {
1330: Container ancestor = getFocusCycleRootAncestor ();
1331:
1332: if (ancestor != this)
1333: return ancestor.getFocusTraversalPolicy ();
1334: else
1335: {
1336: KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
1337:
1338: return manager.getDefaultFocusTraversalPolicy ();
1339: }
1340: }
1341: else
1342: return focusTraversalPolicy;
1343: }
1344:
1345:
1353: public boolean isFocusTraversalPolicySet ()
1354: {
1355: return focusTraversalPolicy == null;
1356: }
1357:
1358:
1374: public void setFocusCycleRoot (boolean focusCycleRoot)
1375: {
1376: this.focusCycleRoot = focusCycleRoot;
1377: }
1378:
1379:
1386: public boolean isFocusCycleRoot ()
1387: {
1388: return focusCycleRoot;
1389: }
1390:
1391:
1400: public void transferFocusDownCycle ()
1401: {
1402: KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
1403:
1404: manager.downFocusCycle (this);
1405: }
1406:
1407:
1415: public void applyComponentOrientation (ComponentOrientation orientation)
1416: {
1417: if (orientation == null)
1418: throw new NullPointerException ();
1419: }
1420:
1421: public void addPropertyChangeListener (PropertyChangeListener listener)
1422: {
1423: if (listener == null)
1424: return;
1425:
1426: if (changeSupport == null)
1427: changeSupport = new PropertyChangeSupport (this);
1428:
1429: changeSupport.addPropertyChangeListener (listener);
1430: }
1431:
1432: public void addPropertyChangeListener (String name,
1433: PropertyChangeListener listener)
1434: {
1435: if (listener == null)
1436: return;
1437:
1438: if (changeSupport == null)
1439: changeSupport = new PropertyChangeSupport (this);
1440:
1441: changeSupport.addPropertyChangeListener (name, listener);
1442: }
1443:
1444:
1445:
1446:
1460: private void visitChildren(Graphics gfx, GfxVisitor visitor,
1461: boolean lightweightOnly)
1462: {
1463: synchronized (getTreeLock ())
1464: {
1465: for (int i = ncomponents - 1; i >= 0; --i)
1466: {
1467: Component comp = component[i];
1468:
1469:
1470:
1471: boolean applicable = comp.isVisible()
1472: && (comp.isLightweight()
1473: || !lightweightOnly && ! (comp instanceof Container));
1474:
1475: if (applicable)
1476: visitChild(gfx, visitor, comp);
1477: }
1478: }
1479: }
1480:
1481:
1494: private void visitChild(Graphics gfx, GfxVisitor visitor,
1495: Component comp)
1496: {
1497: Rectangle bounds = comp.getBounds();
1498: Rectangle oldClip = gfx.getClipBounds();
1499: if (oldClip == null)
1500: oldClip = bounds;
1501:
1502: Rectangle clip = oldClip.intersection(bounds);
1503:
1504: if (clip.isEmpty()) return;
1505:
1506: boolean clipped = false;
1507: boolean translated = false;
1508: try
1509: {
1510: gfx.setClip(clip.x, clip.y, clip.width, clip.height);
1511: clipped = true;
1512: gfx.translate(bounds.x, bounds.y);
1513: translated = true;
1514: visitor.visit(comp, gfx);
1515: }
1516: finally
1517: {
1518: if (translated)
1519: gfx.translate (-bounds.x, -bounds.y);
1520: if (clipped)
1521: gfx.setClip (oldClip.x, oldClip.y, oldClip.width, oldClip.height);
1522: }
1523: }
1524:
1525: void dispatchEventImpl(AWTEvent e)
1526: {
1527:
1528: if (eventTypeEnabled (e.id)
1529: && dispatcher != null
1530: && dispatcher.handleEvent (e))
1531: return;
1532:
1533: if ((e.id <= ContainerEvent.CONTAINER_LAST
1534: && e.id >= ContainerEvent.CONTAINER_FIRST)
1535: && (containerListener != null
1536: || (eventMask & AWTEvent.CONTAINER_EVENT_MASK) != 0))
1537: processEvent(e);
1538: else
1539: super.dispatchEventImpl(e);
1540: }
1541:
1542:
1543: Component findNextFocusComponent(Component child)
1544: {
1545: synchronized (getTreeLock ())
1546: {
1547: int start, end;
1548: if (child != null)
1549: {
1550: for (start = 0; start < ncomponents; ++start)
1551: {
1552: if (component[start] == child)
1553: break;
1554: }
1555: end = start;
1556:
1557: if (end == 0)
1558: end = ncomponents;
1559: ++start;
1560: }
1561: else
1562: {
1563: start = 0;
1564: end = ncomponents;
1565: }
1566:
1567: for (int j = start; j != end; ++j)
1568: {
1569: if (j >= ncomponents)
1570: {
1571:
1572:
1573:
1574:
1575: if (parent != null)
1576: return parent.findNextFocusComponent(this);
1577: j -= ncomponents;
1578: }
1579: if (component[j] instanceof Container)
1580: {
1581: Component c = component[j];
1582: c = c.findNextFocusComponent(null);
1583: if (c != null)
1584: return c;
1585: }
1586: else if (component[j].isFocusTraversable())
1587: return component[j];
1588: }
1589:
1590: return null;
1591: }
1592: }
1593:
1594: private void addNotifyContainerChildren()
1595: {
1596: synchronized (getTreeLock ())
1597: {
1598: for (int i = ncomponents; --i >= 0; )
1599: {
1600: component[i].addNotify();
1601: if (component[i].isLightweight ())
1602: {
1603:
1604:
1605:
1606: if (! this.isLightweight())
1607: {
1608: if (dispatcher == null)
1609: dispatcher = new LightweightDispatcher (this);
1610: }
1611:
1612:
1613: enableEvents(component[i].eventMask);
1614: if (peer != null && !isLightweight ())
1615: enableEvents (AWTEvent.PAINT_EVENT_MASK);
1616: }
1617: }
1618: }
1619: }
1620:
1621:
1636: private void readObject (ObjectInputStream s)
1637: throws ClassNotFoundException, IOException
1638: {
1639: s.defaultReadObject ();
1640: String key = (String) s.readObject ();
1641: while (key != null)
1642: {
1643: Object object = s.readObject ();
1644: if ("containerL".equals (key))
1645: addContainerListener((ContainerListener) object);
1646:
1647: else if ("focusTraversalPolicy".equals (key))
1648: setFocusTraversalPolicy ((FocusTraversalPolicy) object);
1649:
1650: key = (String) s.readObject();
1651: }
1652: }
1653:
1654:
1666: private void writeObject (ObjectOutputStream s) throws IOException
1667: {
1668: s.defaultWriteObject ();
1669: AWTEventMulticaster.save (s, "containerL", containerListener);
1670: if (focusTraversalPolicy instanceof Serializable)
1671: s.writeObject (focusTraversalPolicy);
1672: else
1673: s.writeObject (null);
1674: }
1675:
1676:
1677:
1678:
1681:
1682: abstract static class GfxVisitor
1683: {
1684: public abstract void visit(Component c, Graphics gfx);
1685: }
1686:
1687: static class GfxPaintVisitor extends GfxVisitor
1688: {
1689: public static final GfxVisitor INSTANCE = new GfxPaintVisitor();
1690:
1691: public void visit(Component c, Graphics gfx)
1692: {
1693: c.paint(gfx);
1694: }
1695: }
1696:
1697: static class GfxPrintVisitor extends GfxVisitor
1698: {
1699: public static final GfxVisitor INSTANCE = new GfxPrintVisitor();
1700:
1701: public void visit(Component c, Graphics gfx)
1702: {
1703: c.print(gfx);
1704: }
1705: }
1706:
1707: static class GfxPaintAllVisitor extends GfxVisitor
1708: {
1709: public static final GfxVisitor INSTANCE = new GfxPaintAllVisitor();
1710:
1711: public void visit(Component c, Graphics gfx)
1712: {
1713: c.paintAll(gfx);
1714: }
1715: }
1716:
1717: static class GfxPrintAllVisitor extends GfxVisitor
1718: {
1719: public static final GfxVisitor INSTANCE = new GfxPrintAllVisitor();
1720:
1721: public void visit(Component c, Graphics gfx)
1722: {
1723: c.printAll(gfx);
1724: }
1725: }
1726:
1727:
1734: protected class AccessibleAWTContainer extends AccessibleAWTComponent
1735: {
1736:
1739: private static final long serialVersionUID = 5081320404842566097L;
1740:
1741:
1746: protected ContainerListener accessibleContainerHandler
1747: = new AccessibleContainerHandler();
1748:
1749:
1752: protected AccessibleAWTContainer()
1753: {
1754: Container.this.addContainerListener(accessibleContainerHandler);
1755: }
1756:
1757:
1763: public int getAccessibleChildrenCount()
1764: {
1765: synchronized (getTreeLock ())
1766: {
1767: int count = 0;
1768: int i = component == null ? 0 : component.length;
1769: while (--i >= 0)
1770: if (component[i] instanceof Accessible)
1771: count++;
1772: return count;
1773: }
1774: }
1775:
1776:
1782: public Accessible getAccessibleChild(int i)
1783: {
1784: synchronized (getTreeLock ())
1785: {
1786: if (component == null)
1787: return null;
1788: int index = -1;
1789: while (i >= 0 && ++index < component.length)
1790: if (component[index] instanceof Accessible)
1791: i--;
1792: if (i < 0)
1793: return (Accessible) component[index];
1794: return null;
1795: }
1796: }
1797:
1798:
1808: public Accessible getAccessibleAt(Point p)
1809: {
1810: Component c = getComponentAt(p.x, p.y);
1811: return c != Container.this && c instanceof Accessible ? (Accessible) c
1812: : null;
1813: }
1814:
1815:
1823: protected class AccessibleContainerHandler implements ContainerListener
1824: {
1825:
1828: protected AccessibleContainerHandler()
1829: {
1830: }
1831:
1832:
1838: public void componentAdded(ContainerEvent e)
1839: {
1840: AccessibleAWTContainer.this.firePropertyChange
1841: (ACCESSIBLE_CHILD_PROPERTY, null, e.getChild());
1842: }
1843:
1844:
1850: public void componentRemoved(ContainerEvent e)
1851: {
1852: AccessibleAWTContainer.this.firePropertyChange
1853: (ACCESSIBLE_CHILD_PROPERTY, e.getChild(), null);
1854: }
1855: }
1856: }
1857: }
1858:
1859:
1865:
1866: class LightweightDispatcher implements Serializable
1867: {
1868: private static final long serialVersionUID = 5184291520170872969L;
1869: private Container nativeContainer;
1870: private Cursor nativeCursor;
1871: private long eventMask;
1872:
1873: private transient Component mouseEventTarget;
1874: private transient Component pressedComponent;
1875: private transient Component lastComponentEntered;
1876: private transient Component tempComponent;
1877: private transient int pressCount;
1878:
1879: LightweightDispatcher(Container c)
1880: {
1881: nativeContainer = c;
1882: }
1883:
1884: void acquireComponentForMouseEvent(MouseEvent me)
1885: {
1886: int x = me.getX ();
1887: int y = me.getY ();
1888:
1889:
1890: Component parent = nativeContainer;
1891: Component candidate = null;
1892: Point p = me.getPoint();
1893: while (candidate == null && parent != null)
1894: {
1895: candidate =
1896: SwingUtilities.getDeepestComponentAt(parent, p.x, p.y);
1897: if (candidate == null || (candidate.eventMask & me.getID()) == 0)
1898: {
1899: candidate = null;
1900: p = SwingUtilities.convertPoint(parent, p.x, p.y, parent.parent);
1901: parent = parent.parent;
1902: }
1903: }
1904:
1905:
1906:
1907:
1908: if (candidate == nativeContainer)
1909: candidate = null;
1910:
1911:
1912: if (lastComponentEntered != null
1913: && lastComponentEntered.isShowing()
1914: && lastComponentEntered != candidate)
1915: {
1916:
1917:
1918: if (SwingUtilities.isDescendingFrom(lastComponentEntered, nativeContainer))
1919: {
1920: Point tp =
1921: SwingUtilities.convertPoint(nativeContainer,
1922: x, y, lastComponentEntered);
1923: MouseEvent exited = new MouseEvent (lastComponentEntered,
1924: MouseEvent.MOUSE_EXITED,
1925: me.getWhen (),
1926: me.getModifiersEx (),
1927: tp.x, tp.y,
1928: me.getClickCount (),
1929: me.isPopupTrigger (),
1930: me.getButton ());
1931: tempComponent = lastComponentEntered;
1932: lastComponentEntered = null;
1933: tempComponent.dispatchEvent(exited);
1934: }
1935: lastComponentEntered = null;
1936: }
1937:
1938: if (candidate != null)
1939: {
1940: mouseEventTarget = candidate;
1941: if (candidate.isLightweight()
1942: && candidate.isShowing()
1943: && candidate != nativeContainer
1944: && candidate != lastComponentEntered)
1945: {
1946: lastComponentEntered = mouseEventTarget;
1947: Point cp = SwingUtilities.convertPoint(nativeContainer,
1948: x, y, lastComponentEntered);
1949: MouseEvent entered = new MouseEvent (lastComponentEntered,
1950: MouseEvent.MOUSE_ENTERED,
1951: me.getWhen (),
1952: me.getModifiersEx (),
1953: cp.x, cp.y,
1954: me.getClickCount (),
1955: me.isPopupTrigger (),
1956: me.getButton ());
1957: lastComponentEntered.dispatchEvent (entered);
1958: }
1959: }
1960:
1961: if (me.getID() == MouseEvent.MOUSE_RELEASED
1962: || me.getID() == MouseEvent.MOUSE_PRESSED && pressCount > 0
1963: || me.getID() == MouseEvent.MOUSE_DRAGGED)
1964:
1965:
1966:
1967:
1968:
1969:
1970: if (SwingUtilities.isDescendingFrom(pressedComponent, nativeContainer))
1971: mouseEventTarget = pressedComponent;
1972: else if (me.getID() == MouseEvent.MOUSE_CLICKED)
1973: {
1974:
1975:
1976: if (candidate != pressedComponent)
1977: mouseEventTarget = null;
1978: else if (pressCount == 0)
1979: pressedComponent = null;
1980: }
1981: }
1982:
1983: boolean handleEvent(AWTEvent e)
1984: {
1985: if (e instanceof MouseEvent)
1986: {
1987: MouseEvent me = (MouseEvent) e;
1988:
1989: acquireComponentForMouseEvent(me);
1990:
1991:
1992: if (mouseEventTarget != null
1993: && mouseEventTarget.isShowing()
1994: && e.getID() != MouseEvent.MOUSE_ENTERED
1995: && e.getID() != MouseEvent.MOUSE_EXITED)
1996: {
1997: MouseEvent newEvt =
1998: SwingUtilities.convertMouseEvent(nativeContainer, me,
1999: mouseEventTarget);
2000: mouseEventTarget.dispatchEvent(newEvt);
2001:
2002: switch (e.getID())
2003: {
2004: case MouseEvent.MOUSE_PRESSED:
2005: if (pressCount++ == 0)
2006: pressedComponent = mouseEventTarget;
2007: break;
2008:
2009: case MouseEvent.MOUSE_RELEASED:
2010:
2011:
2012:
2013: if (--pressCount == 0
2014: && mouseEventTarget != pressedComponent)
2015: pressedComponent = null;
2016: break;
2017: }
2018: if (newEvt.isConsumed())
2019: e.consume();
2020: }
2021: }
2022:
2023: return e.isConsumed();
2024: }
2025:
2026: }