1:
206:
207: package ;
208:
209: import ;
210: import ;
211: import ;
212: import ;
213: import ;
214: import ;
215: import ;
216: import ;
217: import ;
218: import ;
219: import ;
220: import ;
221: import ;
222: import ;
223: import ;
224: import ;
225: import ;
226: import ;
227: import ;
228: import ;
229: import ;
230: import ;
231: import ;
232: import ;
233: import ;
234:
235: import ;
236: import ;
237: import ;
238: import ;
239: import ;
240: import ;
241: import ;
242: import ;
243: import ;
244: import ;
245: import ;
246: import ;
247: import ;
248: import ;
249: import ;
250: import ;
251: import ;
252: import ;
253: import ;
254: import ;
255: import ;
256: import ;
257: import ;
258: import ;
259: import ;
260: import ;
261: import ;
262: import ;
263: import ;
264: import ;
265: import ;
266:
267:
278: public class XYPlot extends Plot implements ValueAxisPlot, Zoomable,
279: RendererChangeListener, Cloneable, PublicCloneable, Serializable {
280:
281:
282: private static final long serialVersionUID = 7044148245716569264L;
283:
284:
285: public static final Stroke DEFAULT_GRIDLINE_STROKE = new BasicStroke(0.5f,
286: BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL, 0.0f,
287: new float[] {2.0f, 2.0f}, 0.0f);
288:
289:
290: public static final Paint DEFAULT_GRIDLINE_PAINT = Color.lightGray;
291:
292:
293: public static final boolean DEFAULT_CROSSHAIR_VISIBLE = false;
294:
295:
296: public static final Stroke DEFAULT_CROSSHAIR_STROKE
297: = DEFAULT_GRIDLINE_STROKE;
298:
299:
300: public static final Paint DEFAULT_CROSSHAIR_PAINT = Color.blue;
301:
302:
303: protected static ResourceBundle localizationResources
304: = ResourceBundle.getBundle(
305: "org.jfree.chart.plot.LocalizationBundle");
306:
307:
308: private PlotOrientation orientation;
309:
310:
311: private RectangleInsets axisOffset;
312:
313:
314: private ObjectList domainAxes;
315:
316:
317: private ObjectList domainAxisLocations;
318:
319:
320: private ObjectList rangeAxes;
321:
322:
323: private ObjectList rangeAxisLocations;
324:
325:
326: private ObjectList datasets;
327:
328:
329: private ObjectList renderers;
330:
331:
336: private Map datasetToDomainAxisMap;
337:
338:
343: private Map datasetToRangeAxisMap;
344:
345:
346: private transient Point2D quadrantOrigin = new Point2D.Double(0.0, 0.0);
347:
348:
349: private transient Paint[] quadrantPaint
350: = new Paint[] {null, null, null, null};
351:
352:
353: private boolean domainGridlinesVisible;
354:
355:
356: private transient Stroke domainGridlineStroke;
357:
358:
359: private transient Paint domainGridlinePaint;
360:
361:
362: private boolean rangeGridlinesVisible;
363:
364:
365: private transient Stroke rangeGridlineStroke;
366:
367:
368: private transient Paint rangeGridlinePaint;
369:
370:
376: private boolean domainZeroBaselineVisible;
377:
378:
383: private transient Stroke domainZeroBaselineStroke;
384:
385:
390: private transient Paint domainZeroBaselinePaint;
391:
392:
396: private boolean rangeZeroBaselineVisible;
397:
398:
399: private transient Stroke rangeZeroBaselineStroke;
400:
401:
402: private transient Paint rangeZeroBaselinePaint;
403:
404:
405: private boolean domainCrosshairVisible;
406:
407:
408: private double domainCrosshairValue;
409:
410:
411: private transient Stroke domainCrosshairStroke;
412:
413:
414: private transient Paint domainCrosshairPaint;
415:
416:
420: private boolean domainCrosshairLockedOnData = true;
421:
422:
423: private boolean rangeCrosshairVisible;
424:
425:
426: private double rangeCrosshairValue;
427:
428:
429: private transient Stroke rangeCrosshairStroke;
430:
431:
432: private transient Paint rangeCrosshairPaint;
433:
434:
438: private boolean rangeCrosshairLockedOnData = true;
439:
440:
441: private Map foregroundDomainMarkers;
442:
443:
444: private Map backgroundDomainMarkers;
445:
446:
447: private Map foregroundRangeMarkers;
448:
449:
450: private Map backgroundRangeMarkers;
451:
452:
457: private List annotations;
458:
459:
460: private transient Paint domainTickBandPaint;
461:
462:
463: private transient Paint rangeTickBandPaint;
464:
465:
466: private AxisSpace fixedDomainAxisSpace;
467:
468:
469: private AxisSpace fixedRangeAxisSpace;
470:
471:
475: private DatasetRenderingOrder datasetRenderingOrder
476: = DatasetRenderingOrder.REVERSE;
477:
478:
482: private SeriesRenderingOrder seriesRenderingOrder
483: = SeriesRenderingOrder.REVERSE;
484:
485:
489: private int weight;
490:
491:
495: private LegendItemCollection fixedLegendItems;
496:
497:
501: public XYPlot() {
502: this(null, null, null, null);
503: }
504:
505:
516: public XYPlot(XYDataset dataset,
517: ValueAxis domainAxis,
518: ValueAxis rangeAxis,
519: XYItemRenderer renderer) {
520:
521: super();
522:
523: this.orientation = PlotOrientation.VERTICAL;
524: this.weight = 1;
525: this.axisOffset = RectangleInsets.ZERO_INSETS;
526:
527:
528: this.domainAxes = new ObjectList();
529: this.domainAxisLocations = new ObjectList();
530: this.foregroundDomainMarkers = new HashMap();
531: this.backgroundDomainMarkers = new HashMap();
532:
533: this.rangeAxes = new ObjectList();
534: this.rangeAxisLocations = new ObjectList();
535: this.foregroundRangeMarkers = new HashMap();
536: this.backgroundRangeMarkers = new HashMap();
537:
538: this.datasets = new ObjectList();
539: this.renderers = new ObjectList();
540:
541: this.datasetToDomainAxisMap = new TreeMap();
542: this.datasetToRangeAxisMap = new TreeMap();
543:
544: this.datasets.set(0, dataset);
545: if (dataset != null) {
546: dataset.addChangeListener(this);
547: }
548:
549: this.renderers.set(0, renderer);
550: if (renderer != null) {
551: renderer.setPlot(this);
552: renderer.addChangeListener(this);
553: }
554:
555: this.domainAxes.set(0, domainAxis);
556: this.mapDatasetToDomainAxis(0, 0);
557: if (domainAxis != null) {
558: domainAxis.setPlot(this);
559: domainAxis.addChangeListener(this);
560: }
561: this.domainAxisLocations.set(0, AxisLocation.BOTTOM_OR_LEFT);
562:
563: this.rangeAxes.set(0, rangeAxis);
564: this.mapDatasetToRangeAxis(0, 0);
565: if (rangeAxis != null) {
566: rangeAxis.setPlot(this);
567: rangeAxis.addChangeListener(this);
568: }
569: this.rangeAxisLocations.set(0, AxisLocation.BOTTOM_OR_LEFT);
570:
571: configureDomainAxes();
572: configureRangeAxes();
573:
574: this.domainGridlinesVisible = true;
575: this.domainGridlineStroke = DEFAULT_GRIDLINE_STROKE;
576: this.domainGridlinePaint = DEFAULT_GRIDLINE_PAINT;
577:
578: this.domainZeroBaselineVisible = false;
579: this.domainZeroBaselinePaint = Color.black;
580: this.domainZeroBaselineStroke = new BasicStroke(0.5f);
581:
582: this.rangeGridlinesVisible = true;
583: this.rangeGridlineStroke = DEFAULT_GRIDLINE_STROKE;
584: this.rangeGridlinePaint = DEFAULT_GRIDLINE_PAINT;
585:
586: this.rangeZeroBaselineVisible = false;
587: this.rangeZeroBaselinePaint = Color.black;
588: this.rangeZeroBaselineStroke = new BasicStroke(0.5f);
589:
590: this.domainCrosshairVisible = false;
591: this.domainCrosshairValue = 0.0;
592: this.domainCrosshairStroke = DEFAULT_CROSSHAIR_STROKE;
593: this.domainCrosshairPaint = DEFAULT_CROSSHAIR_PAINT;
594:
595: this.rangeCrosshairVisible = false;
596: this.rangeCrosshairValue = 0.0;
597: this.rangeCrosshairStroke = DEFAULT_CROSSHAIR_STROKE;
598: this.rangeCrosshairPaint = DEFAULT_CROSSHAIR_PAINT;
599:
600: this.annotations = new java.util.ArrayList();
601:
602: }
603:
604:
609: public String getPlotType() {
610: return localizationResources.getString("XY_Plot");
611: }
612:
613:
620: public PlotOrientation getOrientation() {
621: return this.orientation;
622: }
623:
624:
632: public void setOrientation(PlotOrientation orientation) {
633: if (orientation == null) {
634: throw new IllegalArgumentException("Null 'orientation' argument.");
635: }
636: if (orientation != this.orientation) {
637: this.orientation = orientation;
638: fireChangeEvent();
639: }
640: }
641:
642:
649: public RectangleInsets getAxisOffset() {
650: return this.axisOffset;
651: }
652:
653:
661: public void setAxisOffset(RectangleInsets offset) {
662: if (offset == null) {
663: throw new IllegalArgumentException("Null 'offset' argument.");
664: }
665: this.axisOffset = offset;
666: fireChangeEvent();
667: }
668:
669:
679: public ValueAxis getDomainAxis() {
680: return getDomainAxis(0);
681: }
682:
683:
692: public ValueAxis getDomainAxis(int index) {
693: ValueAxis result = null;
694: if (index < this.domainAxes.size()) {
695: result = (ValueAxis) this.domainAxes.get(index);
696: }
697: if (result == null) {
698: Plot parent = getParent();
699: if (parent instanceof XYPlot) {
700: XYPlot xy = (XYPlot) parent;
701: result = xy.getDomainAxis(index);
702: }
703: }
704: return result;
705: }
706:
707:
716: public void setDomainAxis(ValueAxis axis) {
717: setDomainAxis(0, axis);
718: }
719:
720:
730: public void setDomainAxis(int index, ValueAxis axis) {
731: setDomainAxis(index, axis, true);
732: }
733:
734:
744: public void setDomainAxis(int index, ValueAxis axis, boolean notify) {
745: ValueAxis existing = getDomainAxis(index);
746: if (existing != null) {
747: existing.removeChangeListener(this);
748: }
749: if (axis != null) {
750: axis.setPlot(this);
751: }
752: this.domainAxes.set(index, axis);
753: if (axis != null) {
754: axis.configure();
755: axis.addChangeListener(this);
756: }
757: if (notify) {
758: fireChangeEvent();
759: }
760: }
761:
762:
770: public void setDomainAxes(ValueAxis[] axes) {
771: for (int i = 0; i < axes.length; i++) {
772: setDomainAxis(i, axes[i], false);
773: }
774: fireChangeEvent();
775: }
776:
777:
784: public AxisLocation getDomainAxisLocation() {
785: return (AxisLocation) this.domainAxisLocations.get(0);
786: }
787:
788:
796: public void setDomainAxisLocation(AxisLocation location) {
797:
798: setDomainAxisLocation(0, location, true);
799: }
800:
801:
810: public void setDomainAxisLocation(AxisLocation location, boolean notify) {
811:
812: setDomainAxisLocation(0, location, notify);
813: }
814:
815:
824: public RectangleEdge getDomainAxisEdge() {
825: return Plot.resolveDomainAxisLocation(getDomainAxisLocation(),
826: this.orientation);
827: }
828:
829:
836: public int getDomainAxisCount() {
837: return this.domainAxes.size();
838: }
839:
840:
846: public void clearDomainAxes() {
847: for (int i = 0; i < this.domainAxes.size(); i++) {
848: ValueAxis axis = (ValueAxis) this.domainAxes.get(i);
849: if (axis != null) {
850: axis.removeChangeListener(this);
851: }
852: }
853: this.domainAxes.clear();
854: fireChangeEvent();
855: }
856:
857:
860: public void configureDomainAxes() {
861: for (int i = 0; i < this.domainAxes.size(); i++) {
862: ValueAxis axis = (ValueAxis) this.domainAxes.get(i);
863: if (axis != null) {
864: axis.configure();
865: }
866: }
867: }
868:
869:
880: public AxisLocation getDomainAxisLocation(int index) {
881: AxisLocation result = null;
882: if (index < this.domainAxisLocations.size()) {
883: result = (AxisLocation) this.domainAxisLocations.get(index);
884: }
885: if (result == null) {
886: result = AxisLocation.getOpposite(getDomainAxisLocation());
887: }
888: return result;
889: }
890:
891:
901: public void setDomainAxisLocation(int index, AxisLocation location) {
902:
903: setDomainAxisLocation(index, location, true);
904: }
905:
906:
920: public void setDomainAxisLocation(int index, AxisLocation location,
921: boolean notify) {
922:
923: if (index == 0 && location == null) {
924: throw new IllegalArgumentException(
925: "Null 'location' for index 0 not permitted.");
926: }
927: this.domainAxisLocations.set(index, location);
928: if (notify) {
929: fireChangeEvent();
930: }
931: }
932:
933:
942: public RectangleEdge getDomainAxisEdge(int index) {
943: AxisLocation location = getDomainAxisLocation(index);
944: RectangleEdge result = Plot.resolveDomainAxisLocation(location,
945: this.orientation);
946: if (result == null) {
947: result = RectangleEdge.opposite(getDomainAxisEdge());
948: }
949: return result;
950: }
951:
952:
962: public ValueAxis getRangeAxis() {
963: return getRangeAxis(0);
964: }
965:
966:
975: public void setRangeAxis(ValueAxis axis) {
976:
977: if (axis != null) {
978: axis.setPlot(this);
979: }
980:
981:
982: ValueAxis existing = getRangeAxis();
983: if (existing != null) {
984: existing.removeChangeListener(this);
985: }
986:
987: this.rangeAxes.set(0, axis);
988: if (axis != null) {
989: axis.configure();
990: axis.addChangeListener(this);
991: }
992: fireChangeEvent();
993:
994: }
995:
996:
1003: public AxisLocation getRangeAxisLocation() {
1004: return (AxisLocation) this.rangeAxisLocations.get(0);
1005: }
1006:
1007:
1015: public void setRangeAxisLocation(AxisLocation location) {
1016:
1017: setRangeAxisLocation(0, location, true);
1018: }
1019:
1020:
1029: public void setRangeAxisLocation(AxisLocation location, boolean notify) {
1030:
1031: setRangeAxisLocation(0, location, notify);
1032: }
1033:
1034:
1042: public RectangleEdge getRangeAxisEdge() {
1043: return Plot.resolveRangeAxisLocation(getRangeAxisLocation(),
1044: this.orientation);
1045: }
1046:
1047:
1056: public ValueAxis getRangeAxis(int index) {
1057: ValueAxis result = null;
1058: if (index < this.rangeAxes.size()) {
1059: result = (ValueAxis) this.rangeAxes.get(index);
1060: }
1061: if (result == null) {
1062: Plot parent = getParent();
1063: if (parent instanceof XYPlot) {
1064: XYPlot xy = (XYPlot) parent;
1065: result = xy.getRangeAxis(index);
1066: }
1067: }
1068: return result;
1069: }
1070:
1071:
1080: public void setRangeAxis(int index, ValueAxis axis) {
1081: setRangeAxis(index, axis, true);
1082: }
1083:
1084:
1094: public void setRangeAxis(int index, ValueAxis axis, boolean notify) {
1095: ValueAxis existing = getRangeAxis(index);
1096: if (existing != null) {
1097: existing.removeChangeListener(this);
1098: }
1099: if (axis != null) {
1100: axis.setPlot(this);
1101: }
1102: this.rangeAxes.set(index, axis);
1103: if (axis != null) {
1104: axis.configure();
1105: axis.addChangeListener(this);
1106: }
1107: if (notify) {
1108: fireChangeEvent();
1109: }
1110: }
1111:
1112:
1120: public void setRangeAxes(ValueAxis[] axes) {
1121: for (int i = 0; i < axes.length; i++) {
1122: setRangeAxis(i, axes[i], false);
1123: }
1124: fireChangeEvent();
1125: }
1126:
1127:
1134: public int getRangeAxisCount() {
1135: return this.rangeAxes.size();
1136: }
1137:
1138:
1144: public void clearRangeAxes() {
1145: for (int i = 0; i < this.rangeAxes.size(); i++) {
1146: ValueAxis axis = (ValueAxis) this.rangeAxes.get(i);
1147: if (axis != null) {
1148: axis.removeChangeListener(this);
1149: }
1150: }
1151: this.rangeAxes.clear();
1152: fireChangeEvent();
1153: }
1154:
1155:
1160: public void configureRangeAxes() {
1161: for (int i = 0; i < this.rangeAxes.size(); i++) {
1162: ValueAxis axis = (ValueAxis) this.rangeAxes.get(i);
1163: if (axis != null) {
1164: axis.configure();
1165: }
1166: }
1167: }
1168:
1169:
1180: public AxisLocation getRangeAxisLocation(int index) {
1181: AxisLocation result = null;
1182: if (index < this.rangeAxisLocations.size()) {
1183: result = (AxisLocation) this.rangeAxisLocations.get(index);
1184: }
1185: if (result == null) {
1186: result = AxisLocation.getOpposite(getRangeAxisLocation());
1187: }
1188: return result;
1189: }
1190:
1191:
1200: public void setRangeAxisLocation(int index, AxisLocation location) {
1201:
1202: setRangeAxisLocation(index, location, true);
1203: }
1204:
1205:
1219: public void setRangeAxisLocation(int index, AxisLocation location,
1220: boolean notify) {
1221:
1222: if (index == 0 && location == null) {
1223: throw new IllegalArgumentException(
1224: "Null 'location' for index 0 not permitted.");
1225: }
1226: this.rangeAxisLocations.set(index, location);
1227: if (notify) {
1228: fireChangeEvent();
1229: }
1230: }
1231:
1232:
1242: public RectangleEdge getRangeAxisEdge(int index) {
1243: AxisLocation location = getRangeAxisLocation(index);
1244: RectangleEdge result = Plot.resolveRangeAxisLocation(location,
1245: this.orientation);
1246: if (result == null) {
1247: result = RectangleEdge.opposite(getRangeAxisEdge());
1248: }
1249: return result;
1250: }
1251:
1252:
1260: public XYDataset getDataset() {
1261: return getDataset(0);
1262: }
1263:
1264:
1273: public XYDataset getDataset(int index) {
1274: XYDataset result = null;
1275: if (this.datasets.size() > index) {
1276: result = (XYDataset) this.datasets.get(index);
1277: }
1278: return result;
1279: }
1280:
1281:
1290: public void setDataset(XYDataset dataset) {
1291: setDataset(0, dataset);
1292: }
1293:
1294:
1302: public void setDataset(int index, XYDataset dataset) {
1303: XYDataset existing = getDataset(index);
1304: if (existing != null) {
1305: existing.removeChangeListener(this);
1306: }
1307: this.datasets.set(index, dataset);
1308: if (dataset != null) {
1309: dataset.addChangeListener(this);
1310: }
1311:
1312:
1313: DatasetChangeEvent event = new DatasetChangeEvent(this, dataset);
1314: datasetChanged(event);
1315: }
1316:
1317:
1322: public int getDatasetCount() {
1323: return this.datasets.size();
1324: }
1325:
1326:
1334: public int indexOf(XYDataset dataset) {
1335: int result = -1;
1336: for (int i = 0; i < this.datasets.size(); i++) {
1337: if (dataset == this.datasets.get(i)) {
1338: result = i;
1339: break;
1340: }
1341: }
1342: return result;
1343: }
1344:
1345:
1354: public void mapDatasetToDomainAxis(int index, int axisIndex) {
1355: this.datasetToDomainAxisMap.put(new Integer(index),
1356: new Integer(axisIndex));
1357:
1358: datasetChanged(new DatasetChangeEvent(this, getDataset(index)));
1359: }
1360:
1361:
1370: public void mapDatasetToRangeAxis(int index, int axisIndex) {
1371: this.datasetToRangeAxisMap.put(new Integer(index),
1372: new Integer(axisIndex));
1373:
1374: datasetChanged(new DatasetChangeEvent(this, getDataset(index)));
1375: }
1376:
1377:
1384: public XYItemRenderer getRenderer() {
1385: return getRenderer(0);
1386: }
1387:
1388:
1397: public XYItemRenderer getRenderer(int index) {
1398: XYItemRenderer result = null;
1399: if (this.renderers.size() > index) {
1400: result = (XYItemRenderer) this.renderers.get(index);
1401: }
1402: return result;
1403:
1404: }
1405:
1406:
1415: public void setRenderer(XYItemRenderer renderer) {
1416: setRenderer(0, renderer);
1417: }
1418:
1419:
1428: public void setRenderer(int index, XYItemRenderer renderer) {
1429: setRenderer(index, renderer, true);
1430: }
1431:
1432:
1442: public void setRenderer(int index, XYItemRenderer renderer,
1443: boolean notify) {
1444: XYItemRenderer existing = getRenderer(index);
1445: if (existing != null) {
1446: existing.removeChangeListener(this);
1447: }
1448: this.renderers.set(index, renderer);
1449: if (renderer != null) {
1450: renderer.setPlot(this);
1451: renderer.addChangeListener(this);
1452: }
1453: configureDomainAxes();
1454: configureRangeAxes();
1455: if (notify) {
1456: fireChangeEvent();
1457: }
1458: }
1459:
1460:
1466: public void setRenderers(XYItemRenderer[] renderers) {
1467: for (int i = 0; i < renderers.length; i++) {
1468: setRenderer(i, renderers[i], false);
1469: }
1470: fireChangeEvent();
1471: }
1472:
1473:
1480: public DatasetRenderingOrder getDatasetRenderingOrder() {
1481: return this.datasetRenderingOrder;
1482: }
1483:
1484:
1494: public void setDatasetRenderingOrder(DatasetRenderingOrder order) {
1495: if (order == null) {
1496: throw new IllegalArgumentException("Null 'order' argument.");
1497: }
1498: this.datasetRenderingOrder = order;
1499: fireChangeEvent();
1500: }
1501:
1502:
1509: public SeriesRenderingOrder getSeriesRenderingOrder() {
1510: return this.seriesRenderingOrder;
1511: }
1512:
1513:
1523: public void setSeriesRenderingOrder(SeriesRenderingOrder order) {
1524: if (order == null) {
1525: throw new IllegalArgumentException("Null 'order' argument.");
1526: }
1527: this.seriesRenderingOrder = order;
1528: fireChangeEvent();
1529: }
1530:
1531:
1539: public int getIndexOf(XYItemRenderer renderer) {
1540: return this.renderers.indexOf(renderer);
1541: }
1542:
1543:
1552: public XYItemRenderer getRendererForDataset(XYDataset dataset) {
1553: XYItemRenderer result = null;
1554: for (int i = 0; i < this.datasets.size(); i++) {
1555: if (this.datasets.get(i) == dataset) {
1556: result = (XYItemRenderer) this.renderers.get(i);
1557: if (result == null) {
1558: result = getRenderer();
1559: }
1560: break;
1561: }
1562: }
1563: return result;
1564: }
1565:
1566:
1574: public int getWeight() {
1575: return this.weight;
1576: }
1577:
1578:
1586: public void setWeight(int weight) {
1587: this.weight = weight;
1588: fireChangeEvent();
1589: }
1590:
1591:
1599: public boolean isDomainGridlinesVisible() {
1600: return this.domainGridlinesVisible;
1601: }
1602:
1603:
1614: public void setDomainGridlinesVisible(boolean visible) {
1615: if (this.domainGridlinesVisible != visible) {
1616: this.domainGridlinesVisible = visible;
1617: fireChangeEvent();
1618: }
1619: }
1620:
1621:
1629: public Stroke getDomainGridlineStroke() {
1630: return this.domainGridlineStroke;
1631: }
1632:
1633:
1646: public void setDomainGridlineStroke(Stroke stroke) {
1647: if (stroke == null) {
1648: throw new IllegalArgumentException("Null 'stroke' argument.");
1649: }
1650: this.domainGridlineStroke = stroke;
1651: fireChangeEvent();
1652: }
1653:
1654:
1662: public Paint getDomainGridlinePaint() {
1663: return this.domainGridlinePaint;
1664: }
1665:
1666:
1677: public void setDomainGridlinePaint(Paint paint) {
1678: if (paint == null) {
1679: throw new IllegalArgumentException("Null 'paint' argument.");
1680: }
1681: this.domainGridlinePaint = paint;
1682: fireChangeEvent();
1683: }
1684:
1685:
1693: public boolean isRangeGridlinesVisible() {
1694: return this.rangeGridlinesVisible;
1695: }
1696:
1697:
1708: public void setRangeGridlinesVisible(boolean visible) {
1709: if (this.rangeGridlinesVisible != visible) {
1710: this.rangeGridlinesVisible = visible;
1711: fireChangeEvent();
1712: }
1713: }
1714:
1715:
1723: public Stroke getRangeGridlineStroke() {
1724: return this.rangeGridlineStroke;
1725: }
1726:
1727:
1735: public void setRangeGridlineStroke(Stroke stroke) {
1736: if (stroke == null) {
1737: throw new IllegalArgumentException("Null 'stroke' argument.");
1738: }
1739: this.rangeGridlineStroke = stroke;
1740: fireChangeEvent();
1741: }
1742:
1743:
1751: public Paint getRangeGridlinePaint() {
1752: return this.rangeGridlinePaint;
1753: }
1754:
1755:
1763: public void setRangeGridlinePaint(Paint paint) {
1764: if (paint == null) {
1765: throw new IllegalArgumentException("Null 'paint' argument.");
1766: }
1767: this.rangeGridlinePaint = paint;
1768: fireChangeEvent();
1769: }
1770:
1771:
1781: public boolean isDomainZeroBaselineVisible() {
1782: return this.domainZeroBaselineVisible;
1783: }
1784:
1785:
1796: public void setDomainZeroBaselineVisible(boolean visible) {
1797: this.domainZeroBaselineVisible = visible;
1798: fireChangeEvent();
1799: }
1800:
1801:
1810: public Stroke getDomainZeroBaselineStroke() {
1811: return this.domainZeroBaselineStroke;
1812: }
1813:
1814:
1824: public void setDomainZeroBaselineStroke(Stroke stroke) {
1825: if (stroke == null) {
1826: throw new IllegalArgumentException("Null 'stroke' argument.");
1827: }
1828: this.domainZeroBaselineStroke = stroke;
1829: fireChangeEvent();
1830: }
1831:
1832:
1842: public Paint getDomainZeroBaselinePaint() {
1843: return this.domainZeroBaselinePaint;
1844: }
1845:
1846:
1856: public void setDomainZeroBaselinePaint(Paint paint) {
1857: if (paint == null) {
1858: throw new IllegalArgumentException("Null 'paint' argument.");
1859: }
1860: this.domainZeroBaselinePaint = paint;
1861: fireChangeEvent();
1862: }
1863:
1864:
1872: public boolean isRangeZeroBaselineVisible() {
1873: return this.rangeZeroBaselineVisible;
1874: }
1875:
1876:
1885: public void setRangeZeroBaselineVisible(boolean visible) {
1886: this.rangeZeroBaselineVisible = visible;
1887: fireChangeEvent();
1888: }
1889:
1890:
1897: public Stroke getRangeZeroBaselineStroke() {
1898: return this.rangeZeroBaselineStroke;
1899: }
1900:
1901:
1909: public void setRangeZeroBaselineStroke(Stroke stroke) {
1910: if (stroke == null) {
1911: throw new IllegalArgumentException("Null 'stroke' argument.");
1912: }
1913: this.rangeZeroBaselineStroke = stroke;
1914: fireChangeEvent();
1915: }
1916:
1917:
1925: public Paint getRangeZeroBaselinePaint() {
1926: return this.rangeZeroBaselinePaint;
1927: }
1928:
1929:
1937: public void setRangeZeroBaselinePaint(Paint paint) {
1938: if (paint == null) {
1939: throw new IllegalArgumentException("Null 'paint' argument.");
1940: }
1941: this.rangeZeroBaselinePaint = paint;
1942: fireChangeEvent();
1943: }
1944:
1945:
1953: public Paint getDomainTickBandPaint() {
1954: return this.domainTickBandPaint;
1955: }
1956:
1957:
1964: public void setDomainTickBandPaint(Paint paint) {
1965: this.domainTickBandPaint = paint;
1966: fireChangeEvent();
1967: }
1968:
1969:
1977: public Paint getRangeTickBandPaint() {
1978: return this.rangeTickBandPaint;
1979: }
1980:
1981:
1988: public void setRangeTickBandPaint(Paint paint) {
1989: this.rangeTickBandPaint = paint;
1990: fireChangeEvent();
1991: }
1992:
1993:
2001: public Point2D getQuadrantOrigin() {
2002: return this.quadrantOrigin;
2003: }
2004:
2005:
2013: public void setQuadrantOrigin(Point2D origin) {
2014: if (origin == null) {
2015: throw new IllegalArgumentException("Null 'origin' argument.");
2016: }
2017: this.quadrantOrigin = origin;
2018: fireChangeEvent();
2019: }
2020:
2021:
2030: public Paint getQuadrantPaint(int index) {
2031: if (index < 0 || index > 3) {
2032: throw new IllegalArgumentException("The index value (" + index
2033: + ") should be in the range 0 to 3.");
2034: }
2035: return this.quadrantPaint[index];
2036: }
2037:
2038:
2047: public void setQuadrantPaint(int index, Paint paint) {
2048: if (index < 0 || index > 3) {
2049: throw new IllegalArgumentException("The index value (" + index
2050: + ") should be in the range 0 to 3.");
2051: }
2052: this.quadrantPaint[index] = paint;
2053: fireChangeEvent();
2054: }
2055:
2056:
2068: public void addDomainMarker(Marker marker) {
2069:
2070: addDomainMarker(marker, Layer.FOREGROUND);
2071: }
2072:
2073:
2085: public void addDomainMarker(Marker marker, Layer layer) {
2086: addDomainMarker(0, marker, layer);
2087: }
2088:
2089:
2095: public void clearDomainMarkers() {
2096: if (this.backgroundDomainMarkers != null) {
2097: Set keys = this.backgroundDomainMarkers.keySet();
2098: Iterator iterator = keys.iterator();
2099: while (iterator.hasNext()) {
2100: Integer key = (Integer) iterator.next();
2101: clearDomainMarkers(key.intValue());
2102: }
2103: this.backgroundDomainMarkers.clear();
2104: }
2105: if (this.foregroundDomainMarkers != null) {
2106: Set keys = this.foregroundDomainMarkers.keySet();
2107: Iterator iterator = keys.iterator();
2108: while (iterator.hasNext()) {
2109: Integer key = (Integer) iterator.next();
2110: clearDomainMarkers(key.intValue());
2111: }
2112: this.foregroundDomainMarkers.clear();
2113: }
2114: fireChangeEvent();
2115: }
2116:
2117:
2125: public void clearDomainMarkers(int index) {
2126: Integer key = new Integer(index);
2127: if (this.backgroundDomainMarkers != null) {
2128: Collection markers
2129: = (Collection) this.backgroundDomainMarkers.get(key);
2130: if (markers != null) {
2131: Iterator iterator = markers.iterator();
2132: while (iterator.hasNext()) {
2133: Marker m = (Marker) iterator.next();
2134: m.removeChangeListener(this);
2135: }
2136: markers.clear();
2137: }
2138: }
2139: if (this.foregroundRangeMarkers != null) {
2140: Collection markers
2141: = (Collection) this.foregroundDomainMarkers.get(key);
2142: if (markers != null) {
2143: Iterator iterator = markers.iterator();
2144: while (iterator.hasNext()) {
2145: Marker m = (Marker) iterator.next();
2146: m.removeChangeListener(this);
2147: }
2148: markers.clear();
2149: }
2150: }
2151: fireChangeEvent();
2152: }
2153:
2154:
2169: public void addDomainMarker(int index, Marker marker, Layer layer) {
2170: addDomainMarker(index, marker, layer, true);
2171: }
2172:
2173:
2188: public void addDomainMarker(int index, Marker marker, Layer layer,
2189: boolean notify) {
2190: if (marker == null) {
2191: throw new IllegalArgumentException("Null 'marker' not permitted.");
2192: }
2193: if (layer == null) {
2194: throw new IllegalArgumentException("Null 'layer' not permitted.");
2195: }
2196: Collection markers;
2197: if (layer == Layer.FOREGROUND) {
2198: markers = (Collection) this.foregroundDomainMarkers.get(
2199: new Integer(index));
2200: if (markers == null) {
2201: markers = new java.util.ArrayList();
2202: this.foregroundDomainMarkers.put(new Integer(index), markers);
2203: }
2204: markers.add(marker);
2205: }
2206: else if (layer == Layer.BACKGROUND) {
2207: markers = (Collection) this.backgroundDomainMarkers.get(
2208: new Integer(index));
2209: if (markers == null) {
2210: markers = new java.util.ArrayList();
2211: this.backgroundDomainMarkers.put(new Integer(index), markers);
2212: }
2213: markers.add(marker);
2214: }
2215: marker.addChangeListener(this);
2216: if (notify) {
2217: fireChangeEvent();
2218: }
2219: }
2220:
2221:
2232: public boolean removeDomainMarker(Marker marker) {
2233: return removeDomainMarker(marker, Layer.FOREGROUND);
2234: }
2235:
2236:
2248: public boolean removeDomainMarker(Marker marker, Layer layer) {
2249: return removeDomainMarker(0, marker, layer);
2250: }
2251:
2252:
2265: public boolean removeDomainMarker(int index, Marker marker, Layer layer) {
2266: return removeDomainMarker(index, marker, layer, true);
2267: }
2268:
2269:
2283: public boolean removeDomainMarker(int index, Marker marker, Layer layer,
2284: boolean notify) {
2285: ArrayList markers;
2286: if (layer == Layer.FOREGROUND) {
2287: markers = (ArrayList) this.foregroundDomainMarkers.get(
2288: new Integer(index));
2289: }
2290: else {
2291: markers = (ArrayList) this.backgroundDomainMarkers.get(
2292: new Integer(index));
2293: }
2294: if (markers == null) {
2295: return false;
2296: }
2297: boolean removed = markers.remove(marker);
2298: if (removed && notify) {
2299: fireChangeEvent();
2300: }
2301: return removed;
2302: }
2303:
2304:
2315: public void addRangeMarker(Marker marker) {
2316: addRangeMarker(marker, Layer.FOREGROUND);
2317: }
2318:
2319:
2331: public void addRangeMarker(Marker marker, Layer layer) {
2332: addRangeMarker(0, marker, layer);
2333: }
2334:
2335:
2341: public void clearRangeMarkers() {
2342: if (this.backgroundRangeMarkers != null) {
2343: Set keys = this.backgroundRangeMarkers.keySet();
2344: Iterator iterator = keys.iterator();
2345: while (iterator.hasNext()) {
2346: Integer key = (Integer) iterator.next();
2347: clearRangeMarkers(key.intValue());
2348: }
2349: this.backgroundRangeMarkers.clear();
2350: }
2351: if (this.foregroundRangeMarkers != null) {
2352: Set keys = this.foregroundRangeMarkers.keySet();
2353: Iterator iterator = keys.iterator();
2354: while (iterator.hasNext()) {
2355: Integer key = (Integer) iterator.next();
2356: clearRangeMarkers(key.intValue());
2357: }
2358: this.foregroundRangeMarkers.clear();
2359: }
2360: fireChangeEvent();
2361: }
2362:
2363:
2377: public void addRangeMarker(int index, Marker marker, Layer layer) {
2378: addRangeMarker(index, marker, layer, true);
2379: }
2380:
2381:
2395: public void addRangeMarker(int index, Marker marker, Layer layer,
2396: boolean notify) {
2397: Collection markers;
2398: if (layer == Layer.FOREGROUND) {
2399: markers = (Collection) this.foregroundRangeMarkers.get(
2400: new Integer(index));
2401: if (markers == null) {
2402: markers = new java.util.ArrayList();
2403: this.foregroundRangeMarkers.put(new Integer(index), markers);
2404: }
2405: markers.add(marker);
2406: }
2407: else if (layer == Layer.BACKGROUND) {
2408: markers = (Collection) this.backgroundRangeMarkers.get(
2409: new Integer(index));
2410: if (markers == null) {
2411: markers = new java.util.ArrayList();
2412: this.backgroundRangeMarkers.put(new Integer(index), markers);
2413: }
2414: markers.add(marker);
2415: }
2416: marker.addChangeListener(this);
2417: if (notify) {
2418: fireChangeEvent();
2419: }
2420: }
2421:
2422:
2428: public void clearRangeMarkers(int index) {
2429: Integer key = new Integer(index);
2430: if (this.backgroundRangeMarkers != null) {
2431: Collection markers
2432: = (Collection) this.backgroundRangeMarkers.get(key);
2433: if (markers != null) {
2434: Iterator iterator = markers.iterator();
2435: while (iterator.hasNext()) {
2436: Marker m = (Marker) iterator.next();
2437: m.removeChangeListener(this);
2438: }
2439: markers.clear();
2440: }
2441: }
2442: if (this.foregroundRangeMarkers != null) {
2443: Collection markers
2444: = (Collection) this.foregroundRangeMarkers.get(key);
2445: if (markers != null) {
2446: Iterator iterator = markers.iterator();
2447: while (iterator.hasNext()) {
2448: Marker m = (Marker) iterator.next();
2449: m.removeChangeListener(this);
2450: }
2451: markers.clear();
2452: }
2453: }
2454: fireChangeEvent();
2455: }
2456:
2457:
2468: public boolean removeRangeMarker(Marker marker) {
2469: return removeRangeMarker(marker, Layer.FOREGROUND);
2470: }
2471:
2472:
2484: public boolean removeRangeMarker(Marker marker, Layer layer) {
2485: return removeRangeMarker(0, marker, layer);
2486: }
2487:
2488:
2501: public boolean removeRangeMarker(int index, Marker marker, Layer layer) {
2502: return removeRangeMarker(index, marker, layer, true);
2503: }
2504:
2505:
2519: public boolean removeRangeMarker(int index, Marker marker, Layer layer,
2520: boolean notify) {
2521: if (marker == null) {
2522: throw new IllegalArgumentException("Null 'marker' argument.");
2523: }
2524: ArrayList markers;
2525: if (layer == Layer.FOREGROUND) {
2526: markers = (ArrayList) this.foregroundRangeMarkers.get(
2527: new Integer(index));
2528: }
2529: else {
2530: markers = (ArrayList) this.backgroundRangeMarkers.get(
2531: new Integer(index));
2532: }
2533: if (markers == null) {
2534: return false;
2535: }
2536: boolean removed = markers.remove(marker);
2537: if (removed && notify) {
2538: fireChangeEvent();
2539: }
2540: return removed;
2541: }
2542:
2543:
2552: public void addAnnotation(XYAnnotation annotation) {
2553: addAnnotation(annotation, true);
2554: }
2555:
2556:
2565: public void addAnnotation(XYAnnotation annotation, boolean notify) {
2566: if (annotation == null) {
2567: throw new IllegalArgumentException("Null 'annotation' argument.");
2568: }
2569: this.annotations.add(annotation);
2570: if (notify) {
2571: fireChangeEvent();
2572: }
2573: }
2574:
2575:
2586: public boolean removeAnnotation(XYAnnotation annotation) {
2587: return removeAnnotation(annotation, true);
2588: }
2589:
2590:
2601: public boolean removeAnnotation(XYAnnotation annotation, boolean notify) {
2602: if (annotation == null) {
2603: throw new IllegalArgumentException("Null 'annotation' argument.");
2604: }
2605: boolean removed = this.annotations.remove(annotation);
2606: if (removed && notify) {
2607: fireChangeEvent();
2608: }
2609: return removed;
2610: }
2611:
2612:
2621: public List getAnnotations() {
2622: return new ArrayList(this.annotations);
2623: }
2624:
2625:
2631: public void clearAnnotations() {
2632: this.annotations.clear();
2633: fireChangeEvent();
2634: }
2635:
2636:
2644: protected AxisSpace calculateAxisSpace(Graphics2D g2,
2645: Rectangle2D plotArea) {
2646: AxisSpace space = new AxisSpace();
2647: space = calculateRangeAxisSpace(g2, plotArea, space);
2648: Rectangle2D revPlotArea = space.shrink(plotArea, null);
2649: space = calculateDomainAxisSpace(g2, revPlotArea, space);
2650: return space;
2651: }
2652:
2653:
2662: protected AxisSpace calculateDomainAxisSpace(Graphics2D g2,
2663: Rectangle2D plotArea,
2664: AxisSpace space) {
2665:
2666: if (space == null) {
2667: space = new AxisSpace();
2668: }
2669:
2670:
2671: if (this.fixedDomainAxisSpace != null) {
2672: if (this.orientation == PlotOrientation.HORIZONTAL) {
2673: space.ensureAtLeast(this.fixedDomainAxisSpace.getLeft(),
2674: RectangleEdge.LEFT);
2675: space.ensureAtLeast(this.fixedDomainAxisSpace.getRight(),
2676: RectangleEdge.RIGHT);
2677: }
2678: else if (this.orientation == PlotOrientation.VERTICAL) {
2679: space.ensureAtLeast(this.fixedDomainAxisSpace.getTop(),
2680: RectangleEdge.TOP);
2681: space.ensureAtLeast(this.fixedDomainAxisSpace.getBottom(),
2682: RectangleEdge.BOTTOM);
2683: }
2684: }
2685: else {
2686:
2687: for (int i = 0; i < this.domainAxes.size(); i++) {
2688: Axis axis = (Axis) this.domainAxes.get(i);
2689: if (axis != null) {
2690: RectangleEdge edge = getDomainAxisEdge(i);
2691: space = axis.reserveSpace(g2, this, plotArea, edge, space);
2692: }
2693: }
2694: }
2695:
2696: return space;
2697:
2698: }
2699:
2700:
2709: protected AxisSpace calculateRangeAxisSpace(Graphics2D g2,
2710: Rectangle2D plotArea,
2711: AxisSpace space) {
2712:
2713: if (space == null) {
2714: space = new AxisSpace();
2715: }
2716:
2717:
2718: if (this.fixedRangeAxisSpace != null) {
2719: if (this.orientation == PlotOrientation.HORIZONTAL) {
2720: space.ensureAtLeast(this.fixedRangeAxisSpace.getTop(),
2721: RectangleEdge.TOP);
2722: space.ensureAtLeast(this.fixedRangeAxisSpace.getBottom(),
2723: RectangleEdge.BOTTOM);
2724: }
2725: else if (this.orientation == PlotOrientation.VERTICAL) {
2726: space.ensureAtLeast(this.fixedRangeAxisSpace.getLeft(),
2727: RectangleEdge.LEFT);
2728: space.ensureAtLeast(this.fixedRangeAxisSpace.getRight(),
2729: RectangleEdge.RIGHT);
2730: }
2731: }
2732: else {
2733:
2734: for (int i = 0; i < this.rangeAxes.size(); i++) {
2735: Axis axis = (Axis) this.rangeAxes.get(i);
2736: if (axis != null) {
2737: RectangleEdge edge = getRangeAxisEdge(i);
2738: space = axis.reserveSpace(g2, this, plotArea, edge, space);
2739: }
2740: }
2741: }
2742: return space;
2743:
2744: }
2745:
2746:
2758: public void draw(Graphics2D g2,
2759: Rectangle2D area,
2760: Point2D anchor,
2761: PlotState parentState,
2762: PlotRenderingInfo info) {
2763:
2764:
2765: boolean b1 = (area.getWidth() <= MINIMUM_WIDTH_TO_DRAW);
2766: boolean b2 = (area.getHeight() <= MINIMUM_HEIGHT_TO_DRAW);
2767: if (b1 || b2) {
2768: return;
2769: }
2770:
2771:
2772: if (info != null) {
2773: info.setPlotArea(area);
2774: }
2775:
2776:
2777: RectangleInsets insets = getInsets();
2778: insets.trim(area);
2779:
2780: AxisSpace space = calculateAxisSpace(g2, area);
2781: Rectangle2D dataArea = space.shrink(area, null);
2782: this.axisOffset.trim(dataArea);
2783:
2784: if (info != null) {
2785: info.setDataArea(dataArea);
2786: }
2787:
2788:
2789: drawBackground(g2, dataArea);
2790: Map axisStateMap = drawAxes(g2, area, dataArea, info);
2791:
2792: PlotOrientation orient = getOrientation();
2793:
2794:
2795:
2796: if (anchor != null && !dataArea.contains(anchor)) {
2797: anchor = null;
2798: }
2799: CrosshairState crosshairState = new CrosshairState();
2800: crosshairState.setCrosshairDistance(Double.POSITIVE_INFINITY);
2801: crosshairState.setAnchor(anchor);
2802:
2803: crosshairState.setAnchorX(Double.NaN);
2804: crosshairState.setAnchorY(Double.NaN);
2805: if (anchor != null) {
2806: ValueAxis domainAxis = getDomainAxis();
2807: if (domainAxis != null) {
2808: double x;
2809: if (orient == PlotOrientation.VERTICAL) {
2810: x = domainAxis.java2DToValue(anchor.getX(), dataArea,
2811: getDomainAxisEdge());
2812: }
2813: else {
2814: x = domainAxis.java2DToValue(anchor.getY(), dataArea,
2815: getDomainAxisEdge());
2816: }
2817: crosshairState.setAnchorX(x);
2818: }
2819: ValueAxis rangeAxis = getRangeAxis();
2820: if (rangeAxis != null) {
2821: double y;
2822: if (orient == PlotOrientation.VERTICAL) {
2823: y = rangeAxis.java2DToValue(anchor.getY(), dataArea,
2824: getRangeAxisEdge());
2825: }
2826: else {
2827: y = rangeAxis.java2DToValue(anchor.getX(), dataArea,
2828: getRangeAxisEdge());
2829: }
2830: crosshairState.setAnchorY(y);
2831: }
2832: }
2833: crosshairState.setCrosshairX(getDomainCrosshairValue());
2834: crosshairState.setCrosshairY(getRangeCrosshairValue());
2835: Shape originalClip = g2.getClip();
2836: Composite originalComposite = g2.getComposite();
2837:
2838: g2.clip(dataArea);
2839: g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER,
2840: getForegroundAlpha()));
2841:
2842: AxisState domainAxisState = (AxisState) axisStateMap.get(
2843: getDomainAxis());
2844: if (domainAxisState == null) {
2845: if (parentState != null) {
2846: domainAxisState = (AxisState) parentState.getSharedAxisStates()
2847: .get(getDomainAxis());
2848: }
2849: }
2850:
2851: AxisState rangeAxisState = (AxisState) axisStateMap.get(getRangeAxis());
2852: if (rangeAxisState == null) {
2853: if (parentState != null) {
2854: rangeAxisState = (AxisState) parentState.getSharedAxisStates()
2855: .get(getRangeAxis());
2856: }
2857: }
2858: if (domainAxisState != null) {
2859: drawDomainTickBands(g2, dataArea, domainAxisState.getTicks());
2860: }
2861: if (rangeAxisState != null) {
2862: drawRangeTickBands(g2, dataArea, rangeAxisState.getTicks());
2863: }
2864: if (domainAxisState != null) {
2865: drawDomainGridlines(g2, dataArea, domainAxisState.getTicks());
2866: drawZeroDomainBaseline(g2, dataArea);
2867: }
2868: if (rangeAxisState != null) {
2869: drawRangeGridlines(g2, dataArea, rangeAxisState.getTicks());
2870: drawZeroRangeBaseline(g2, dataArea);
2871: }
2872:
2873:
2874: for (int i = 0; i < this.renderers.size(); i++) {
2875: drawDomainMarkers(g2, dataArea, i, Layer.BACKGROUND);
2876: }
2877: for (int i = 0; i < this.renderers.size(); i++) {
2878: drawRangeMarkers(g2, dataArea, i, Layer.BACKGROUND);
2879: }
2880:
2881:
2882: boolean foundData = false;
2883: DatasetRenderingOrder order = getDatasetRenderingOrder();
2884: if (order == DatasetRenderingOrder.FORWARD) {
2885:
2886:
2887: int rendererCount = this.renderers.size();
2888: for (int i = 0; i < rendererCount; i++) {
2889: XYItemRenderer r = getRenderer(i);
2890: if (r != null) {
2891: ValueAxis domainAxis = getDomainAxisForDataset(i);
2892: ValueAxis rangeAxis = getRangeAxisForDataset(i);
2893: r.drawAnnotations(g2, dataArea, domainAxis, rangeAxis,
2894: Layer.BACKGROUND, info);
2895: }
2896: }
2897:
2898:
2899: for (int i = 0; i < getDatasetCount(); i++) {
2900: foundData = render(g2, dataArea, i, info, crosshairState)
2901: || foundData;
2902: }
2903:
2904:
2905: for (int i = 0; i < rendererCount; i++) {
2906: XYItemRenderer r = getRenderer(i);
2907: if (r != null) {
2908: ValueAxis domainAxis = getDomainAxisForDataset(i);
2909: ValueAxis rangeAxis = getRangeAxisForDataset(i);
2910: r.drawAnnotations(g2, dataArea, domainAxis, rangeAxis,
2911: Layer.FOREGROUND, info);
2912: }
2913: }
2914:
2915: }
2916: else if (order == DatasetRenderingOrder.REVERSE) {
2917:
2918:
2919: int rendererCount = this.renderers.size();
2920: for (int i = rendererCount - 1; i >= 0; i--) {
2921: XYItemRenderer r = getRenderer(i);
2922: if (i >= getDatasetCount()) {
2923: continue;
2924: }
2925: if (r != null) {
2926: ValueAxis domainAxis = getDomainAxisForDataset(i);
2927: ValueAxis rangeAxis = getRangeAxisForDataset(i);
2928: r.drawAnnotations(g2, dataArea, domainAxis, rangeAxis,
2929: Layer.BACKGROUND, info);
2930: }
2931: }
2932:
2933: for (int i = getDatasetCount() - 1; i >= 0; i--) {
2934: foundData = render(g2, dataArea, i, info, crosshairState)
2935: || foundData;
2936: }
2937:
2938:
2939: for (int i = rendererCount - 1; i >= 0; i--) {
2940: XYItemRenderer r = getRenderer(i);
2941: if (i >= getDatasetCount()) {
2942: continue;
2943: }
2944: if (r != null) {
2945: ValueAxis domainAxis = getDomainAxisForDataset(i);
2946: ValueAxis rangeAxis = getRangeAxisForDataset(i);
2947: r.drawAnnotations(g2, dataArea, domainAxis, rangeAxis,
2948: Layer.FOREGROUND, info);
2949: }
2950: }
2951:
2952: }
2953:
2954:
2955: int xAxisIndex = crosshairState.getDomainAxisIndex();
2956: ValueAxis xAxis = getDomainAxis(xAxisIndex);
2957: RectangleEdge xAxisEdge = getDomainAxisEdge(xAxisIndex);
2958: if (!this.domainCrosshairLockedOnData && anchor != null) {
2959: double xx;
2960: if (orient == PlotOrientation.VERTICAL) {
2961: xx = xAxis.java2DToValue(anchor.getX(), dataArea, xAxisEdge);
2962: }
2963: else {
2964: xx = xAxis.java2DToValue(anchor.getY(), dataArea, xAxisEdge);
2965: }
2966: crosshairState.setCrosshairX(xx);
2967: }
2968: setDomainCrosshairValue(crosshairState.getCrosshairX(), false);
2969: if (isDomainCrosshairVisible()) {
2970: double x = getDomainCrosshairValue();
2971: Paint paint = getDomainCrosshairPaint();
2972: Stroke stroke = getDomainCrosshairStroke();
2973: drawDomainCrosshair(g2, dataArea, orient, x, xAxis, stroke, paint);
2974: }
2975:
2976:
2977: int yAxisIndex = crosshairState.getRangeAxisIndex();
2978: ValueAxis yAxis = getRangeAxis(yAxisIndex);
2979: RectangleEdge yAxisEdge = getRangeAxisEdge(yAxisIndex);
2980: if (!this.rangeCrosshairLockedOnData && anchor != null) {
2981: double yy;
2982: if (orient == PlotOrientation.VERTICAL) {
2983: yy = yAxis.java2DToValue(anchor.getY(), dataArea, yAxisEdge);
2984: } else {
2985: yy = yAxis.java2DToValue(anchor.getX(), dataArea, yAxisEdge);
2986: }
2987: crosshairState.setCrosshairY(yy);
2988: }
2989: setRangeCrosshairValue(crosshairState.getCrosshairY(), false);
2990: if (isRangeCrosshairVisible()) {
2991: double y = getRangeCrosshairValue();
2992: Paint paint = getRangeCrosshairPaint();
2993: Stroke stroke = getRangeCrosshairStroke();
2994: drawRangeCrosshair(g2, dataArea, orient, y, yAxis, stroke, paint);
2995: }
2996:
2997: if (!foundData) {
2998: drawNoDataMessage(g2, dataArea);
2999: }
3000:
3001: for (int i = 0; i < this.renderers.size(); i++) {
3002: drawDomainMarkers(g2, dataArea, i, Layer.FOREGROUND);
3003: }
3004: for (int i = 0; i < this.renderers.size(); i++) {
3005: drawRangeMarkers(g2, dataArea, i, Layer.FOREGROUND);
3006: }
3007:
3008: drawAnnotations(g2, dataArea, info);
3009: g2.setClip(originalClip);
3010: g2.setComposite(originalComposite);
3011:
3012: drawOutline(g2, dataArea);
3013:
3014: }
3015:
3016:
3022: public void drawBackground(Graphics2D g2, Rectangle2D area) {
3023: fillBackground(g2, area, this.orientation);
3024: drawQuadrants(g2, area);
3025: drawBackgroundImage(g2, area);
3026: }
3027:
3028:
3037: protected void drawQuadrants(Graphics2D g2, Rectangle2D area) {
3038:
3039:
3040:
3041: boolean somethingToDraw = false;
3042:
3043: ValueAxis xAxis = getDomainAxis();
3044: double x = xAxis.getRange().constrain(this.quadrantOrigin.getX());
3045: double xx = xAxis.valueToJava2D(x, area, getDomainAxisEdge());
3046:
3047: ValueAxis yAxis = getRangeAxis();
3048: double y = yAxis.getRange().constrain(this.quadrantOrigin.getY());
3049: double yy = yAxis.valueToJava2D(y, area, getRangeAxisEdge());
3050:
3051: double xmin = xAxis.getLowerBound();
3052: double xxmin = xAxis.valueToJava2D(xmin, area, getDomainAxisEdge());
3053:
3054: double xmax = xAxis.getUpperBound();
3055: double xxmax = xAxis.valueToJava2D(xmax, area, getDomainAxisEdge());
3056:
3057: double ymin = yAxis.getLowerBound();
3058: double yymin = yAxis.valueToJava2D(ymin, area, getRangeAxisEdge());
3059:
3060: double ymax = yAxis.getUpperBound();
3061: double yymax = yAxis.valueToJava2D(ymax, area, getRangeAxisEdge());
3062:
3063: Rectangle2D[] r = new Rectangle2D[] {null, null, null, null};
3064: if (this.quadrantPaint[0] != null) {
3065: if (x > xmin && y < ymax) {
3066: if (this.orientation == PlotOrientation.HORIZONTAL) {
3067: r[0] = new Rectangle2D.Double(Math.min(yymax, yy),
3068: Math.min(xxmin, xx), Math.abs(yy - yymax),
3069: Math.abs(xx - xxmin)
3070: );
3071: }
3072: else {
3073: r[0] = new Rectangle2D.Double(Math.min(xxmin, xx),
3074: Math.min(yymax, yy), Math.abs(xx - xxmin),
3075: Math.abs(yy - yymax));
3076: }
3077: somethingToDraw = true;
3078: }
3079: }
3080: if (this.quadrantPaint[1] != null) {
3081: if (x < xmax && y < ymax) {
3082: if (this.orientation == PlotOrientation.HORIZONTAL) {
3083: r[1] = new Rectangle2D.Double(Math.min(yymax, yy),
3084: Math.min(xxmax, xx), Math.abs(yy - yymax),
3085: Math.abs(xx - xxmax));
3086: }
3087: else {
3088: r[1] = new Rectangle2D.Double(Math.min(xx, xxmax),
3089: Math.min(yymax, yy), Math.abs(xx - xxmax),
3090: Math.abs(yy - yymax));
3091: }
3092: somethingToDraw = true;
3093: }
3094: }
3095: if (this.quadrantPaint[2] != null) {
3096: if (x > xmin && y > ymin) {
3097: if (this.orientation == PlotOrientation.HORIZONTAL) {
3098: r[2] = new Rectangle2D.Double(Math.min(yymin, yy),
3099: Math.min(xxmin, xx), Math.abs(yy - yymin),
3100: Math.abs(xx - xxmin));
3101: }
3102: else {
3103: r[2] = new Rectangle2D.Double(Math.min(xxmin, xx),
3104: Math.min(yymin, yy), Math.abs(xx - xxmin),
3105: Math.abs(yy - yymin));
3106: }
3107: somethingToDraw = true;
3108: }
3109: }
3110: if (this.quadrantPaint[3] != null) {
3111: if (x < xmax && y > ymin) {
3112: if (this.orientation == PlotOrientation.HORIZONTAL) {
3113: r[3] = new Rectangle2D.Double(Math.min(yymin, yy),
3114: Math.min(xxmax, xx), Math.abs(yy - yymin),
3115: Math.abs(xx - xxmax));
3116: }
3117: else {
3118: r[3] = new Rectangle2D.Double(Math.min(xx, xxmax),
3119: Math.min(yymin, yy), Math.abs(xx - xxmax),
3120: Math.abs(yy - yymin));
3121: }
3122: somethingToDraw = true;
3123: }
3124: }
3125: if (somethingToDraw) {
3126: Composite originalComposite = g2.getComposite();
3127: g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER,
3128: getBackgroundAlpha()));
3129: for (int i = 0; i < 4; i++) {
3130: if (this.quadrantPaint[i] != null && r[i] != null) {
3131: g2.setPaint(this.quadrantPaint[i]);
3132: g2.fill(r[i]);
3133: }
3134: }
3135: g2.setComposite(originalComposite);
3136: }
3137: }
3138:
3139:
3148: public void drawDomainTickBands(Graphics2D g2, Rectangle2D dataArea,
3149: List ticks) {
3150: Paint bandPaint = getDomainTickBandPaint();
3151: if (bandPaint != null) {
3152: boolean fillBand = false;
3153: ValueAxis xAxis = getDomainAxis();
3154: double previous = xAxis.getLowerBound();
3155: Iterator iterator = ticks.iterator();
3156: while (iterator.hasNext()) {
3157: ValueTick tick = (ValueTick) iterator.next();
3158: double current = tick.getValue();
3159: if (fillBand) {
3160: getRenderer().fillDomainGridBand(g2, this, xAxis, dataArea,
3161: previous, current);
3162: }
3163: previous = current;
3164: fillBand = !fillBand;
3165: }
3166: double end = xAxis.getUpperBound();
3167: if (fillBand) {
3168: getRenderer().fillDomainGridBand(g2, this, xAxis, dataArea,
3169: previous, end);
3170: }
3171: }
3172: }
3173:
3174:
3183: public void drawRangeTickBands(Graphics2D g2, Rectangle2D dataArea,
3184: List ticks) {
3185: Paint bandPaint = getRangeTickBandPaint();
3186: if (bandPaint != null) {
3187: boolean fillBand = false;
3188: ValueAxis axis = getRangeAxis();
3189: double previous = axis.getLowerBound();
3190: Iterator iterator = ticks.iterator();
3191: while (iterator.hasNext()) {
3192: ValueTick tick = (ValueTick) iterator.next();
3193: double current = tick.getValue();
3194: if (fillBand) {
3195: getRenderer().fillRangeGridBand(g2, this, axis, dataArea,
3196: previous, current);
3197: }
3198: previous = current;
3199: fillBand = !fillBand;
3200: }
3201: double end = axis.getUpperBound();
3202: if (fillBand) {
3203: getRenderer().fillRangeGridBand(g2, this, axis, dataArea,
3204: previous, end);
3205: }
3206: }
3207: }
3208:
3209:
3220: protected Map drawAxes(Graphics2D g2,
3221: Rectangle2D plotArea,
3222: Rectangle2D dataArea,
3223: PlotRenderingInfo plotState) {
3224:
3225: AxisCollection axisCollection = new AxisCollection();
3226:
3227:
3228: for (int index = 0; index < this.domainAxes.size(); index++) {
3229: ValueAxis axis = (ValueAxis) this.domainAxes.get(index);
3230: if (axis != null) {
3231: axisCollection.add(axis, getDomainAxisEdge(index));
3232: }
3233: }
3234:
3235:
3236: for (int index = 0; index < this.rangeAxes.size(); index++) {
3237: ValueAxis yAxis = (ValueAxis) this.rangeAxes.get(index);
3238: if (yAxis != null) {
3239: axisCollection.add(yAxis, getRangeAxisEdge(index));
3240: }
3241: }
3242:
3243: Map axisStateMap = new HashMap();
3244:
3245:
3246: double cursor = dataArea.getMinY() - this.axisOffset.calculateTopOutset(
3247: dataArea.getHeight());
3248: Iterator iterator = axisCollection.getAxesAtTop().iterator();
3249: while (iterator.hasNext()) {
3250: ValueAxis axis = (ValueAxis) iterator.next();
3251: AxisState info = axis.draw(g2, cursor, plotArea, dataArea,
3252: RectangleEdge.TOP, plotState);
3253: cursor = info.getCursor();
3254: axisStateMap.put(axis, info);
3255: }
3256:
3257:
3258: cursor = dataArea.getMaxY()
3259: + this.axisOffset.calculateBottomOutset(dataArea.getHeight());
3260: iterator = axisCollection.getAxesAtBottom().iterator();
3261: while (iterator.hasNext()) {
3262: ValueAxis axis = (ValueAxis) iterator.next();
3263: AxisState info = axis.draw(g2, cursor, plotArea, dataArea,
3264: RectangleEdge.BOTTOM, plotState);
3265: cursor = info.getCursor();
3266: axisStateMap.put(axis, info);
3267: }
3268:
3269:
3270: cursor = dataArea.getMinX()
3271: - this.axisOffset.calculateLeftOutset(dataArea.getWidth());
3272: iterator = axisCollection.getAxesAtLeft().iterator();
3273: while (iterator.hasNext()) {
3274: ValueAxis axis = (ValueAxis) iterator.next();
3275: AxisState info = axis.draw(g2, cursor, plotArea, dataArea,
3276: RectangleEdge.LEFT, plotState);
3277: cursor = info.getCursor();
3278: axisStateMap.put(axis, info);
3279: }
3280:
3281:
3282: cursor = dataArea.getMaxX()
3283: + this.axisOffset.calculateRightOutset(dataArea.getWidth());
3284: iterator = axisCollection.getAxesAtRight().iterator();
3285: while (iterator.hasNext()) {
3286: ValueAxis axis = (ValueAxis) iterator.next();
3287: AxisState info = axis.draw(g2, cursor, plotArea, dataArea,
3288: RectangleEdge.RIGHT, plotState);
3289: cursor = info.getCursor();
3290: axisStateMap.put(axis, info);
3291: }
3292:
3293: return axisStateMap;
3294: }
3295:
3296:
3312: public boolean render(Graphics2D g2, Rectangle2D dataArea, int index,
3313: PlotRenderingInfo info, CrosshairState crosshairState) {
3314:
3315: boolean foundData = false;
3316: XYDataset dataset = getDataset(index);
3317: if (!DatasetUtilities.isEmptyOrNull(dataset)) {
3318: foundData = true;
3319: ValueAxis xAxis = getDomainAxisForDataset(index);
3320: ValueAxis yAxis = getRangeAxisForDataset(index);
3321: XYItemRenderer renderer = getRenderer(index);
3322: if (renderer == null) {
3323: renderer = getRenderer();
3324: if (renderer == null) {
3325: return foundData;
3326: }
3327: }
3328:
3329: XYItemRendererState state = renderer.initialise(g2, dataArea, this,
3330: dataset, info);
3331: int passCount = renderer.getPassCount();
3332:
3333: SeriesRenderingOrder seriesOrder = getSeriesRenderingOrder();
3334: if (seriesOrder == SeriesRenderingOrder.REVERSE) {
3335:
3336: for (int pass = 0; pass < passCount; pass++) {
3337: int seriesCount = dataset.getSeriesCount();
3338: for (int series = seriesCount - 1; series >= 0; series--) {
3339: int firstItem = 0;
3340: int lastItem = dataset.getItemCount(series) - 1;
3341: if (lastItem == -1) {
3342: continue;
3343: }
3344: if (state.getProcessVisibleItemsOnly()) {
3345: int[] itemBounds = RendererUtilities.findLiveItems(
3346: dataset, series, xAxis.getLowerBound(),
3347: xAxis.getUpperBound());
3348: firstItem = itemBounds[0];
3349: lastItem = itemBounds[1];
3350: }
3351: for (int item = firstItem; item <= lastItem; item++) {
3352: renderer.drawItem(g2, state, dataArea, info,
3353: this, xAxis, yAxis, dataset, series, item,
3354: crosshairState, pass);
3355: }
3356: }
3357: }
3358: }
3359: else {
3360:
3361: for (int pass = 0; pass < passCount; pass++) {
3362: int seriesCount = dataset.getSeriesCount();
3363: for (int series = 0; series < seriesCount; series++) {
3364: int firstItem = 0;
3365: int lastItem = dataset.getItemCount(series) - 1;
3366: if (state.getProcessVisibleItemsOnly()) {
3367: int[] itemBounds = RendererUtilities.findLiveItems(
3368: dataset, series, xAxis.getLowerBound(),
3369: xAxis.getUpperBound());
3370: firstItem = itemBounds[0];
3371: lastItem = itemBounds[1];
3372: }
3373: for (int item = firstItem; item <= lastItem; item++) {
3374: renderer.drawItem(g2, state, dataArea, info,
3375: this, xAxis, yAxis, dataset, series, item,
3376: crosshairState, pass);
3377: }
3378: }
3379: }
3380: }
3381: }
3382: return foundData;
3383: }
3384:
3385:
3392: public ValueAxis getDomainAxisForDataset(int index) {
3393:
3394: if (index < 0 || index >= getDatasetCount()) {
3395: throw new IllegalArgumentException("Index " + index
3396: + " out of bounds.");
3397: }
3398:
3399: ValueAxis valueAxis = null;
3400: Integer axisIndex = (Integer) this.datasetToDomainAxisMap.get(
3401: new Integer(index));
3402: if (axisIndex != null) {
3403: valueAxis = getDomainAxis(axisIndex.intValue());
3404: }
3405: else {
3406: valueAxis = getDomainAxis(0);
3407: }
3408: return valueAxis;
3409:
3410: }
3411:
3412:
3419: public ValueAxis getRangeAxisForDataset(int index) {
3420:
3421: if (index < 0 || index >= getDatasetCount()) {
3422: throw new IllegalArgumentException("Index " + index
3423: + " out of bounds.");
3424: }
3425:
3426: ValueAxis valueAxis = null;
3427: Integer axisIndex
3428: = (Integer) this.datasetToRangeAxisMap.get(new Integer(index));
3429: if (axisIndex != null) {
3430: valueAxis = getRangeAxis(axisIndex.intValue());
3431: }
3432: else {
3433: valueAxis = getRangeAxis(0);
3434: }
3435: return valueAxis;
3436:
3437: }
3438:
3439:
3448: protected void drawDomainGridlines(Graphics2D g2, Rectangle2D dataArea,
3449: List ticks) {
3450:
3451:
3452: if (getRenderer() == null) {
3453: return;
3454: }
3455:
3456:
3457: if (isDomainGridlinesVisible()) {
3458: Stroke gridStroke = getDomainGridlineStroke();
3459: Paint gridPaint = getDomainGridlinePaint();
3460: if ((gridStroke != null) && (gridPaint != null)) {
3461: Iterator iterator = ticks.iterator();
3462: while (iterator.hasNext()) {
3463: ValueTick tick = (ValueTick) iterator.next();
3464: getRenderer().drawDomainGridLine(g2, this, getDomainAxis(),
3465: dataArea, tick.getValue());
3466: }
3467: }
3468: }
3469: }
3470:
3471:
3481: protected void drawRangeGridlines(Graphics2D g2, Rectangle2D area,
3482: List ticks) {
3483:
3484:
3485: if (getRenderer() == null) {
3486: return;
3487: }
3488:
3489:
3490: if (isRangeGridlinesVisible()) {
3491: Stroke gridStroke = getRangeGridlineStroke();
3492: Paint gridPaint = getRangeGridlinePaint();
3493: ValueAxis axis = getRangeAxis();
3494: if (axis != null) {
3495: Iterator iterator = ticks.iterator();
3496: while (iterator.hasNext()) {
3497: ValueTick tick = (ValueTick) iterator.next();
3498: if (tick.getValue() != 0.0
3499: || !isRangeZeroBaselineVisible()) {
3500: getRenderer().drawRangeLine(g2, this, getRangeAxis(),
3501: area, tick.getValue(), gridPaint, gridStroke);
3502: }
3503: }
3504: }
3505: }
3506: }
3507:
3508:
3518: protected void drawZeroDomainBaseline(Graphics2D g2, Rectangle2D area) {
3519: if (isDomainZeroBaselineVisible()) {
3520: XYItemRenderer r = getRenderer();
3521:
3522:
3523:
3524: if (r instanceof AbstractXYItemRenderer) {
3525: AbstractXYItemRenderer renderer = (AbstractXYItemRenderer) r;
3526: renderer.drawDomainLine(g2, this, getDomainAxis(), area, 0.0,
3527: this.domainZeroBaselinePaint,
3528: this.domainZeroBaselineStroke);
3529: }
3530: }
3531: }
3532:
3533:
3541: protected void drawZeroRangeBaseline(Graphics2D g2, Rectangle2D area) {
3542: if (isRangeZeroBaselineVisible()) {
3543: getRenderer().drawRangeLine(g2, this, getRangeAxis(), area, 0.0,
3544: this.rangeZeroBaselinePaint, this.rangeZeroBaselineStroke);
3545: }
3546: }
3547:
3548:
3555: public void drawAnnotations(Graphics2D g2,
3556: Rectangle2D dataArea,
3557: PlotRenderingInfo info) {
3558:
3559: Iterator iterator = this.annotations.iterator();
3560: while (iterator.hasNext()) {
3561: XYAnnotation annotation = (XYAnnotation) iterator.next();
3562: ValueAxis xAxis = getDomainAxis();
3563: ValueAxis yAxis = getRangeAxis();
3564: annotation.draw(g2, this, dataArea, xAxis, yAxis, 0, info);
3565: }
3566:
3567: }
3568:
3569:
3578: protected void drawDomainMarkers(Graphics2D g2, Rectangle2D dataArea,
3579: int index, Layer layer) {
3580:
3581: XYItemRenderer r = getRenderer(index);
3582: if (r == null) {
3583: return;
3584: }
3585:
3586:
3587: if (index >= getDatasetCount()) {
3588: return;
3589: }
3590: Collection markers = getDomainMarkers(index, layer);
3591: ValueAxis axis = getDomainAxisForDataset(index);
3592: if (markers != null && axis != null) {
3593: Iterator iterator = markers.iterator();
3594: while (iterator.hasNext()) {
3595: Marker marker = (Marker) iterator.next();
3596: r.drawDomainMarker(g2, this, axis, marker, dataArea);
3597: }
3598: }
3599:
3600: }
3601:
3602:
3611: protected void drawRangeMarkers(Graphics2D g2, Rectangle2D dataArea,
3612: int index, Layer layer) {
3613:
3614: XYItemRenderer r = getRenderer(index);
3615: if (r == null) {
3616: return;
3617: }
3618:
3619:
3620: if (index >= getDatasetCount()) {
3621: return;
3622: }
3623: Collection markers = getRangeMarkers(index, layer);
3624: ValueAxis axis = getRangeAxisForDataset(index);
3625: if (markers != null && axis != null) {
3626: Iterator iterator = markers.iterator();
3627: while (iterator.hasNext()) {
3628: Marker marker = (Marker) iterator.next();
3629: r.drawRangeMarker(g2, this, axis, marker, dataArea);
3630: }
3631: }
3632: }
3633:
3634:
3643: public Collection getDomainMarkers(Layer layer) {
3644: return getDomainMarkers(0, layer);
3645: }
3646:
3647:
3656: public Collection getRangeMarkers(Layer layer) {
3657: return getRangeMarkers(0, layer);
3658: }
3659:
3660:
3671: public Collection getDomainMarkers(int index, Layer layer) {
3672: Collection result = null;
3673: Integer key = new Integer(index);
3674: if (layer == Layer.FOREGROUND) {
3675: result = (Collection) this.foregroundDomainMarkers.get(key);
3676: }
3677: else if (layer == Layer.BACKGROUND) {
3678: result = (Collection) this.backgroundDomainMarkers.get(key);
3679: }
3680: if (result != null) {
3681: result = Collections.unmodifiableCollection(result);
3682: }
3683: return result;
3684: }
3685:
3686:
3697: public Collection getRangeMarkers(int index, Layer layer) {
3698: Collection result = null;
3699: Integer key = new Integer(index);
3700: if (layer == Layer.FOREGROUND) {
3701: result = (Collection) this.foregroundRangeMarkers.get(key);
3702: }
3703: else if (layer == Layer.BACKGROUND) {
3704: result = (Collection) this.backgroundRangeMarkers.get(key);
3705: }
3706: if (result != null) {
3707: result = Collections.unmodifiableCollection(result);
3708: }
3709: return result;
3710: }
3711:
3712:
3722: protected void drawHorizontalLine(Graphics2D g2, Rectangle2D dataArea,
3723: double value, Stroke stroke,
3724: Paint paint) {
3725:
3726: ValueAxis axis = getRangeAxis();
3727: if (getOrientation() == PlotOrientation.HORIZONTAL) {
3728: axis = getDomainAxis();
3729: }
3730: if (axis.getRange().contains(value)) {
3731: double yy = axis.valueToJava2D(value, dataArea, RectangleEdge.LEFT);
3732: Line2D line = new Line2D.Double(dataArea.getMinX(), yy,
3733: dataArea.getMaxX(), yy);
3734: g2.setStroke(stroke);
3735: g2.setPaint(paint);
3736: g2.draw(line);
3737: }
3738:
3739: }
3740:
3741:
3754: protected void drawDomainCrosshair(Graphics2D g2, Rectangle2D dataArea,
3755: PlotOrientation orientation, double value, ValueAxis axis,
3756: Stroke stroke, Paint paint) {
3757:
3758: if (axis.getRange().contains(value)) {
3759: Line2D line = null;
3760: if (orientation == PlotOrientation.VERTICAL) {
3761: double xx = axis.valueToJava2D(value, dataArea,
3762: RectangleEdge.BOTTOM);
3763: line = new Line2D.Double(xx, dataArea.getMinY(), xx,
3764: dataArea.getMaxY());
3765: }
3766: else {
3767: double yy = axis.valueToJava2D(value, dataArea,
3768: RectangleEdge.LEFT);
3769: line = new Line2D.Double(dataArea.getMinX(), yy,
3770: dataArea.getMaxX(), yy);
3771: }
3772: g2.setStroke(stroke);
3773: g2.setPaint(paint);
3774: g2.draw(line);
3775: }
3776:
3777: }
3778:
3779:
3788: protected void drawVerticalLine(Graphics2D g2, Rectangle2D dataArea,
3789: double value, Stroke stroke, Paint paint) {
3790:
3791: ValueAxis axis = getDomainAxis();
3792: if (getOrientation() == PlotOrientation.HORIZONTAL) {
3793: axis = getRangeAxis();
3794: }
3795: if (axis.getRange().contains(value)) {
3796: double xx = axis.valueToJava2D(value, dataArea,
3797: RectangleEdge.BOTTOM);
3798: Line2D line = new Line2D.Double(xx, dataArea.getMinY(), xx,
3799: dataArea.getMaxY());
3800: g2.setStroke(stroke);
3801: g2.setPaint(paint);
3802: g2.draw(line);
3803: }
3804:
3805: }
3806:
3807:
3820: protected void drawRangeCrosshair(Graphics2D g2, Rectangle2D dataArea,
3821: PlotOrientation orientation, double value, ValueAxis axis,
3822: Stroke stroke, Paint paint) {
3823:
3824: if (axis.getRange().contains(value)) {
3825: Line2D line = null;
3826: if (orientation == PlotOrientation.HORIZONTAL) {
3827: double xx = axis.valueToJava2D(value, dataArea,
3828: RectangleEdge.BOTTOM);
3829: line = new Line2D.Double(xx, dataArea.getMinY(), xx,
3830: dataArea.getMaxY());
3831: }
3832: else {
3833: double yy = axis.valueToJava2D(value, dataArea,
3834: RectangleEdge.LEFT);
3835: line = new Line2D.Double(dataArea.getMinX(), yy,
3836: dataArea.getMaxX(), yy);
3837: }
3838: g2.setStroke(stroke);
3839: g2.setPaint(paint);
3840: g2.draw(line);
3841: }
3842:
3843: }
3844:
3845:
3852: public void handleClick(int x, int y, PlotRenderingInfo info) {
3853:
3854: Rectangle2D dataArea = info.getDataArea();
3855: if (dataArea.contains(x, y)) {
3856:
3857: ValueAxis xaxis = getDomainAxis();
3858: if (xaxis != null) {
3859: double hvalue = xaxis.java2DToValue(x, info.getDataArea(),
3860: getDomainAxisEdge());
3861: setDomainCrosshairValue(hvalue);
3862: }
3863:
3864:
3865: ValueAxis yaxis = getRangeAxis();
3866: if (yaxis != null) {
3867: double vvalue = yaxis.java2DToValue(y, info.getDataArea(),
3868: getRangeAxisEdge());
3869: setRangeCrosshairValue(vvalue);
3870: }
3871: }
3872: }
3873:
3874:
3882: private List getDatasetsMappedToDomainAxis(Integer axisIndex) {
3883: if (axisIndex == null) {
3884: throw new IllegalArgumentException("Null 'axisIndex' argument.");
3885: }
3886: List result = new ArrayList();
3887: for (int i = 0; i < this.datasets.size(); i++) {
3888: Integer mappedAxis = (Integer) this.datasetToDomainAxisMap.get(
3889: new Integer(i));
3890: if (mappedAxis == null) {
3891: if (axisIndex.equals(ZERO)) {
3892: result.add(this.datasets.get(i));
3893: }
3894: }
3895: else {
3896: if (mappedAxis.equals(axisIndex)) {
3897: result.add(this.datasets.get(i));
3898: }
3899: }
3900: }
3901: return result;
3902: }
3903:
3904:
3912: private List getDatasetsMappedToRangeAxis(Integer axisIndex) {
3913: if (axisIndex == null) {
3914: throw new IllegalArgumentException("Null 'axisIndex' argument.");
3915: }
3916: List result = new ArrayList();
3917: for (int i = 0; i < this.datasets.size(); i++) {
3918: Integer mappedAxis = (Integer) this.datasetToRangeAxisMap.get(
3919: new Integer(i));
3920: if (mappedAxis == null) {
3921: if (axisIndex.equals(ZERO)) {
3922: result.add(this.datasets.get(i));
3923: }
3924: }
3925: else {
3926: if (mappedAxis.equals(axisIndex)) {
3927: result.add(this.datasets.get(i));
3928: }
3929: }
3930: }
3931: return result;
3932: }
3933:
3934:
3943: public int getDomainAxisIndex(ValueAxis axis) {
3944: int result = this.domainAxes.indexOf(axis);
3945: if (result < 0) {
3946:
3947: Plot parent = getParent();
3948: if (parent instanceof XYPlot) {
3949: XYPlot p = (XYPlot) parent;
3950: result = p.getDomainAxisIndex(axis);
3951: }
3952: }
3953: return result;
3954: }
3955:
3956:
3965: public int getRangeAxisIndex(ValueAxis axis) {
3966: int result = this.rangeAxes.indexOf(axis);
3967: if (result < 0) {
3968:
3969: Plot parent = getParent();
3970: if (parent instanceof XYPlot) {
3971: XYPlot p = (XYPlot) parent;
3972: result = p.getRangeAxisIndex(axis);
3973: }
3974: }
3975: return result;
3976: }
3977:
3978:
3985: public Range getDataRange(ValueAxis axis) {
3986:
3987: Range result = null;
3988: List mappedDatasets = new ArrayList();
3989: boolean isDomainAxis = true;
3990:
3991:
3992: int domainIndex = getDomainAxisIndex(axis);
3993: if (domainIndex >= 0) {
3994: isDomainAxis = true;
3995: mappedDatasets.addAll(getDatasetsMappedToDomainAxis(
3996: new Integer(domainIndex)));
3997: }
3998:
3999:
4000: int rangeIndex = getRangeAxisIndex(axis);
4001: if (rangeIndex >= 0) {
4002: isDomainAxis = false;
4003: mappedDatasets.addAll(getDatasetsMappedToRangeAxis(
4004: new Integer(rangeIndex)));
4005: }
4006:
4007:
4008:
4009: Iterator iterator = mappedDatasets.iterator();
4010: while (iterator.hasNext()) {
4011: XYDataset d = (XYDataset) iterator.next();
4012: if (d != null) {
4013: XYItemRenderer r = getRendererForDataset(d);
4014: if (isDomainAxis) {
4015: if (r != null) {
4016: result = Range.combine(result, r.findDomainBounds(d));
4017: }
4018: else {
4019: result = Range.combine(result,
4020: DatasetUtilities.findDomainBounds(d));
4021: }
4022: }
4023: else {
4024: if (r != null) {
4025: result = Range.combine(result, r.findRangeBounds(d));
4026: }
4027: else {
4028: result = Range.combine(result,
4029: DatasetUtilities.findRangeBounds(d));
4030: }
4031: }
4032: }
4033: }
4034: return result;
4035:
4036: }
4037:
4038:
4045: public void datasetChanged(DatasetChangeEvent event) {
4046: configureDomainAxes();
4047: configureRangeAxes();
4048: if (getParent() != null) {
4049: getParent().datasetChanged(event);
4050: }
4051: else {
4052: PlotChangeEvent e = new PlotChangeEvent(this);
4053: e.setType(ChartChangeEventType.DATASET_UPDATED);
4054: notifyListeners(e);
4055: }
4056: }
4057:
4058:
4063: public void rendererChanged(RendererChangeEvent event) {
4064: fireChangeEvent();
4065: }
4066:
4067:
4074: public boolean isDomainCrosshairVisible() {
4075: return this.domainCrosshairVisible;
4076: }
4077:
4078:
4087: public void setDomainCrosshairVisible(boolean flag) {
4088: if (this.domainCrosshairVisible != flag) {
4089: this.domainCrosshairVisible = flag;
4090: fireChangeEvent();
4091: }
4092: }
4093:
4094:
4102: public boolean isDomainCrosshairLockedOnData() {
4103: return this.domainCrosshairLockedOnData;
4104: }
4105:
4106:
4115: public void setDomainCrosshairLockedOnData(boolean flag) {
4116: if (this.domainCrosshairLockedOnData != flag) {
4117: this.domainCrosshairLockedOnData = flag;
4118: fireChangeEvent();
4119: }
4120: }
4121:
4122:
4129: public double getDomainCrosshairValue() {
4130: return this.domainCrosshairValue;
4131: }
4132:
4133:
4141: public void setDomainCrosshairValue(double value) {
4142: setDomainCrosshairValue(value, true);
4143: }
4144:
4145:
4155: public void setDomainCrosshairValue(double value, boolean notify) {
4156: this.domainCrosshairValue = value;
4157: if (isDomainCrosshairVisible() && notify) {
4158: fireChangeEvent();
4159: }
4160: }
4161:
4162:
4171: public Stroke getDomainCrosshairStroke() {
4172: return this.domainCrosshairStroke;
4173: }
4174:
4175:
4184: public void setDomainCrosshairStroke(Stroke stroke) {
4185: if (stroke == null) {
4186: throw new IllegalArgumentException("Null 'stroke' argument.");
4187: }
4188: this.domainCrosshairStroke = stroke;
4189: fireChangeEvent();
4190: }
4191:
4192:
4201: public Paint getDomainCrosshairPaint() {
4202: return this.domainCrosshairPaint;
4203: }
4204:
4205:
4213: public void setDomainCrosshairPaint(Paint paint) {
4214: if (paint == null) {
4215: throw new IllegalArgumentException("Null 'paint' argument.");
4216: }
4217: this.domainCrosshairPaint = paint;
4218: fireChangeEvent();
4219: }
4220:
4221:
4229: public boolean isRangeCrosshairVisible() {
4230: return this.rangeCrosshairVisible;
4231: }
4232:
4233:
4242: public void setRangeCrosshairVisible(boolean flag) {
4243: if (this.rangeCrosshairVisible != flag) {
4244: this.rangeCrosshairVisible = flag;
4245: fireChangeEvent();
4246: }
4247: }
4248:
4249:
4257: public boolean isRangeCrosshairLockedOnData() {
4258: return this.rangeCrosshairLockedOnData;
4259: }
4260:
4261:
4270: public void setRangeCrosshairLockedOnData(boolean flag) {
4271: if (this.rangeCrosshairLockedOnData != flag) {
4272: this.rangeCrosshairLockedOnData = flag;
4273: fireChangeEvent();
4274: }
4275: }
4276:
4277:
4284: public double getRangeCrosshairValue() {
4285: return this.rangeCrosshairValue;
4286: }
4287:
4288:
4298: public void setRangeCrosshairValue(double value) {
4299: setRangeCrosshairValue(value, true);
4300: }
4301:
4302:
4312: public void setRangeCrosshairValue(double value, boolean notify) {
4313: this.rangeCrosshairValue = value;
4314: if (isRangeCrosshairVisible() && notify) {
4315: fireChangeEvent();
4316: }
4317: }
4318:
4319:
4328: public Stroke getRangeCrosshairStroke() {
4329: return this.rangeCrosshairStroke;
4330: }
4331:
4332:
4341: public void setRangeCrosshairStroke(Stroke stroke) {
4342: if (stroke == null) {
4343: throw new IllegalArgumentException("Null 'stroke' argument.");
4344: }
4345: this.rangeCrosshairStroke = stroke;
4346: fireChangeEvent();
4347: }
4348:
4349:
4358: public Paint getRangeCrosshairPaint() {
4359: return this.rangeCrosshairPaint;
4360: }
4361:
4362:
4370: public void setRangeCrosshairPaint(Paint paint) {
4371: if (paint == null) {
4372: throw new IllegalArgumentException("Null 'paint' argument.");
4373: }
4374: this.rangeCrosshairPaint = paint;
4375: fireChangeEvent();
4376: }
4377:
4378:
4385: public AxisSpace getFixedDomainAxisSpace() {
4386: return this.fixedDomainAxisSpace;
4387: }
4388:
4389:
4397: public void setFixedDomainAxisSpace(AxisSpace space) {
4398: setFixedDomainAxisSpace(space, true);
4399: }
4400:
4401:
4412: public void setFixedDomainAxisSpace(AxisSpace space, boolean notify) {
4413: this.fixedDomainAxisSpace = space;
4414: if (notify) {
4415: fireChangeEvent();
4416: }
4417: }
4418:
4419:
4426: public AxisSpace getFixedRangeAxisSpace() {
4427: return this.fixedRangeAxisSpace;
4428: }
4429:
4430:
4438: public void setFixedRangeAxisSpace(AxisSpace space) {
4439: setFixedRangeAxisSpace(space, true);
4440: }
4441:
4442:
4453: public void setFixedRangeAxisSpace(AxisSpace space, boolean notify) {
4454: this.fixedRangeAxisSpace = space;
4455: if (notify) {
4456: fireChangeEvent();
4457: }
4458: }
4459:
4460:
4469: public void zoomDomainAxes(double factor, PlotRenderingInfo info,
4470: Point2D source) {
4471:
4472: zoomDomainAxes(factor, info, source, false);
4473: }
4474:
4475:
4487: public void zoomDomainAxes(double factor, PlotRenderingInfo info,
4488: Point2D source, boolean useAnchor) {
4489:
4490:
4491: for (int i = 0; i < this.domainAxes.size(); i++) {
4492: ValueAxis domainAxis = (ValueAxis) this.domainAxes.get(i);
4493: if (domainAxis != null) {
4494: if (useAnchor) {
4495:
4496:
4497: double sourceX = source.getX();
4498: if (this.orientation == PlotOrientation.HORIZONTAL) {
4499: sourceX = source.getY();
4500: }
4501: double anchorX = domainAxis.java2DToValue(sourceX,
4502: info.getDataArea(), getDomainAxisEdge());
4503: domainAxis.resizeRange(factor, anchorX);
4504: }
4505: else {
4506: domainAxis.resizeRange(factor);
4507: }
4508: }
4509: }
4510: }
4511:
4512:
4526: public void zoomDomainAxes(double lowerPercent, double upperPercent,
4527: PlotRenderingInfo info, Point2D source) {
4528: for (int i = 0; i < this.domainAxes.size(); i++) {
4529: ValueAxis domainAxis = (ValueAxis) this.domainAxes.get(i);
4530: if (domainAxis != null) {
4531: domainAxis.zoomRange(lowerPercent, upperPercent);
4532: }
4533: }
4534: }
4535:
4536:
4545: public void zoomRangeAxes(double factor, PlotRenderingInfo info,
4546: Point2D source) {
4547:
4548: zoomRangeAxes(factor, info, source, false);
4549: }
4550:
4551:
4564: public void zoomRangeAxes(double factor, PlotRenderingInfo info,
4565: Point2D source, boolean useAnchor) {
4566:
4567:
4568: for (int i = 0; i < this.rangeAxes.size(); i++) {
4569: ValueAxis rangeAxis = (ValueAxis) this.rangeAxes.get(i);
4570: if (rangeAxis != null) {
4571: if (useAnchor) {
4572:
4573:
4574: double sourceY = source.getY();
4575: if (this.orientation == PlotOrientation.HORIZONTAL) {
4576: sourceY = source.getX();
4577: }
4578: double anchorY = rangeAxis.java2DToValue(sourceY,
4579: info.getDataArea(), getRangeAxisEdge());
4580: rangeAxis.resizeRange(factor, anchorY);
4581: }
4582: else {
4583: rangeAxis.resizeRange(factor);
4584: }
4585: }
4586: }
4587: }
4588:
4589:
4599: public void zoomRangeAxes(double lowerPercent, double upperPercent,
4600: PlotRenderingInfo info, Point2D source) {
4601: for (int i = 0; i < this.rangeAxes.size(); i++) {
4602: ValueAxis rangeAxis = (ValueAxis) this.rangeAxes.get(i);
4603: if (rangeAxis != null) {
4604: rangeAxis.zoomRange(lowerPercent, upperPercent);
4605: }
4606: }
4607: }
4608:
4609:
4617: public boolean isDomainZoomable() {
4618: return true;
4619: }
4620:
4621:
4629: public boolean isRangeZoomable() {
4630: return true;
4631: }
4632:
4633:
4639: public int getSeriesCount() {
4640: int result = 0;
4641: XYDataset dataset = getDataset();
4642: if (dataset != null) {
4643: result = dataset.getSeriesCount();
4644: }
4645: return result;
4646: }
4647:
4648:
4655: public LegendItemCollection getFixedLegendItems() {
4656: return this.fixedLegendItems;
4657: }
4658:
4659:
4668: public void setFixedLegendItems(LegendItemCollection items) {
4669: this.fixedLegendItems = items;
4670: fireChangeEvent();
4671: }
4672:
4673:
4680: public LegendItemCollection getLegendItems() {
4681: if (this.fixedLegendItems != null) {
4682: return this.fixedLegendItems;
4683: }
4684: LegendItemCollection result = new LegendItemCollection();
4685: int count = this.datasets.size();
4686: for (int datasetIndex = 0; datasetIndex < count; datasetIndex++) {
4687: XYDataset dataset = getDataset(datasetIndex);
4688: if (dataset != null) {
4689: XYItemRenderer renderer = getRenderer(datasetIndex);
4690: if (renderer == null) {
4691: renderer = getRenderer(0);
4692: }
4693: if (renderer != null) {
4694: int seriesCount = dataset.getSeriesCount();
4695: for (int i = 0; i < seriesCount; i++) {
4696: if (renderer.isSeriesVisible(i)
4697: && renderer.isSeriesVisibleInLegend(i)) {
4698: LegendItem item = renderer.getLegendItem(
4699: datasetIndex, i);
4700: if (item != null) {
4701: result.add(item);
4702: }
4703: }
4704: }
4705: }
4706: }
4707: }
4708: return result;
4709: }
4710:
4711:
4718: public boolean equals(Object obj) {
4719:
4720: if (obj == this) {
4721: return true;
4722: }
4723: if (!(obj instanceof XYPlot)) {
4724: return false;
4725: }
4726:
4727: XYPlot that = (XYPlot) obj;
4728: if (this.weight != that.weight) {
4729: return false;
4730: }
4731: if (this.orientation != that.orientation) {
4732: return false;
4733: }
4734: if (!this.domainAxes.equals(that.domainAxes)) {
4735: return false;
4736: }
4737: if (!this.domainAxisLocations.equals(that.domainAxisLocations)) {
4738: return false;
4739: }
4740: if (this.rangeCrosshairLockedOnData
4741: != that.rangeCrosshairLockedOnData) {
4742: return false;
4743: }
4744: if (this.domainGridlinesVisible != that.domainGridlinesVisible) {
4745: return false;
4746: }
4747: if (this.rangeGridlinesVisible != that.rangeGridlinesVisible) {
4748: return false;
4749: }
4750: if (this.domainZeroBaselineVisible != that.domainZeroBaselineVisible) {
4751: return false;
4752: }
4753: if (this.rangeZeroBaselineVisible != that.rangeZeroBaselineVisible) {
4754: return false;
4755: }
4756: if (this.domainCrosshairVisible != that.domainCrosshairVisible) {
4757: return false;
4758: }
4759: if (this.domainCrosshairValue != that.domainCrosshairValue) {
4760: return false;
4761: }
4762: if (this.domainCrosshairLockedOnData
4763: != that.domainCrosshairLockedOnData) {
4764: return false;
4765: }
4766: if (this.rangeCrosshairVisible != that.rangeCrosshairVisible) {
4767: return false;
4768: }
4769: if (this.rangeCrosshairValue != that.rangeCrosshairValue) {
4770: return false;
4771: }
4772: if (!ObjectUtilities.equal(this.axisOffset, that.axisOffset)) {
4773: return false;
4774: }
4775: if (!ObjectUtilities.equal(this.renderers, that.renderers)) {
4776: return false;
4777: }
4778: if (!ObjectUtilities.equal(this.rangeAxes, that.rangeAxes)) {
4779: return false;
4780: }
4781: if (!this.rangeAxisLocations.equals(that.rangeAxisLocations)) {
4782: return false;
4783: }
4784: if (!ObjectUtilities.equal(this.datasetToDomainAxisMap,
4785: that.datasetToDomainAxisMap)) {
4786: return false;
4787: }
4788: if (!ObjectUtilities.equal(this.datasetToRangeAxisMap,
4789: that.datasetToRangeAxisMap)) {
4790: return false;
4791: }
4792: if (!ObjectUtilities.equal(this.domainGridlineStroke,
4793: that.domainGridlineStroke)) {
4794: return false;
4795: }
4796: if (!PaintUtilities.equal(this.domainGridlinePaint,
4797: that.domainGridlinePaint)) {
4798: return false;
4799: }
4800: if (!ObjectUtilities.equal(this.rangeGridlineStroke,
4801: that.rangeGridlineStroke)) {
4802: return false;
4803: }
4804: if (!PaintUtilities.equal(this.rangeGridlinePaint,
4805: that.rangeGridlinePaint)) {
4806: return false;
4807: }
4808: if (!PaintUtilities.equal(this.domainZeroBaselinePaint,
4809: that.domainZeroBaselinePaint)) {
4810: return false;
4811: }
4812: if (!ObjectUtilities.equal(this.domainZeroBaselineStroke,
4813: that.domainZeroBaselineStroke)) {
4814: return false;
4815: }
4816: if (!PaintUtilities.equal(this.rangeZeroBaselinePaint,
4817: that.rangeZeroBaselinePaint)) {
4818: return false;
4819: }
4820: if (!ObjectUtilities.equal(this.rangeZeroBaselineStroke,
4821: that.rangeZeroBaselineStroke)) {
4822: return false;
4823: }
4824: if (!ObjectUtilities.equal(this.domainCrosshairStroke,
4825: that.domainCrosshairStroke)) {
4826: return false;
4827: }
4828: if (!PaintUtilities.equal(this.domainCrosshairPaint,
4829: that.domainCrosshairPaint)) {
4830: return false;
4831: }
4832: if (!ObjectUtilities.equal(this.rangeCrosshairStroke,
4833: that.rangeCrosshairStroke)) {
4834: return false;
4835: }
4836: if (!PaintUtilities.equal(this.rangeCrosshairPaint,
4837: that.rangeCrosshairPaint)) {
4838: return false;
4839: }
4840: if (!ObjectUtilities.equal(this.foregroundDomainMarkers,
4841: that.foregroundDomainMarkers)) {
4842: return false;
4843: }
4844: if (!ObjectUtilities.equal(this.backgroundDomainMarkers,
4845: that.backgroundDomainMarkers)) {
4846: return false;
4847: }
4848: if (!ObjectUtilities.equal(this.foregroundRangeMarkers,
4849: that.foregroundRangeMarkers)) {
4850: return false;
4851: }
4852: if (!ObjectUtilities.equal(this.backgroundRangeMarkers,
4853: that.backgroundRangeMarkers)) {
4854: return false;
4855: }
4856: if (!ObjectUtilities.equal(this.foregroundDomainMarkers,
4857: that.foregroundDomainMarkers)) {
4858: return false;
4859: }
4860: if (!ObjectUtilities.equal(this.backgroundDomainMarkers,
4861: that.backgroundDomainMarkers)) {
4862: return false;
4863: }
4864: if (!ObjectUtilities.equal(this.foregroundRangeMarkers,
4865: that.foregroundRangeMarkers)) {
4866: return false;
4867: }
4868: if (!ObjectUtilities.equal(this.backgroundRangeMarkers,
4869: that.backgroundRangeMarkers)) {
4870: return false;
4871: }
4872: if (!ObjectUtilities.equal(this.annotations, that.annotations)) {
4873: return false;
4874: }
4875: if (!PaintUtilities.equal(this.domainTickBandPaint,
4876: that.domainTickBandPaint)) {
4877: return false;
4878: }
4879: if (!PaintUtilities.equal(this.rangeTickBandPaint,
4880: that.rangeTickBandPaint)) {
4881: return false;
4882: }
4883: if (!this.quadrantOrigin.equals(that.quadrantOrigin)) {
4884: return false;
4885: }
4886: for (int i = 0; i < 4; i++) {
4887: if (!PaintUtilities.equal(this.quadrantPaint[i],
4888: that.quadrantPaint[i])) {
4889: return false;
4890: }
4891: }
4892: return super.equals(obj);
4893: }
4894:
4895:
4903: public Object clone() throws CloneNotSupportedException {
4904:
4905: XYPlot clone = (XYPlot) super.clone();
4906: clone.domainAxes = (ObjectList) ObjectUtilities.clone(this.domainAxes);
4907: for (int i = 0; i < this.domainAxes.size(); i++) {
4908: ValueAxis axis = (ValueAxis) this.domainAxes.get(i);
4909: if (axis != null) {
4910: ValueAxis clonedAxis = (ValueAxis) axis.clone();
4911: clone.domainAxes.set(i, clonedAxis);
4912: clonedAxis.setPlot(clone);
4913: clonedAxis.addChangeListener(clone);
4914: }
4915: }
4916: clone.domainAxisLocations = (ObjectList)
4917: this.domainAxisLocations.clone();
4918:
4919: clone.rangeAxes = (ObjectList) ObjectUtilities.clone(this.rangeAxes);
4920: for (int i = 0; i < this.rangeAxes.size(); i++) {
4921: ValueAxis axis = (ValueAxis) this.rangeAxes.get(i);
4922: if (axis != null) {
4923: ValueAxis clonedAxis = (ValueAxis) axis.clone();
4924: clone.rangeAxes.set(i, clonedAxis);
4925: clonedAxis.setPlot(clone);
4926: clonedAxis.addChangeListener(clone);
4927: }
4928: }
4929: clone.rangeAxisLocations = (ObjectList) ObjectUtilities.clone(
4930: this.rangeAxisLocations);
4931:
4932:
4933: clone.datasets = (ObjectList) ObjectUtilities.clone(this.datasets);
4934: for (int i = 0; i < clone.datasets.size(); ++i) {
4935: XYDataset d = getDataset(i);
4936: if (d != null) {
4937: d.addChangeListener(clone);
4938: }
4939: }
4940:
4941: clone.datasetToDomainAxisMap = new TreeMap();
4942: clone.datasetToDomainAxisMap.putAll(this.datasetToDomainAxisMap);
4943: clone.datasetToRangeAxisMap = new TreeMap();
4944: clone.datasetToRangeAxisMap.putAll(this.datasetToRangeAxisMap);
4945:
4946: clone.renderers = (ObjectList) ObjectUtilities.clone(this.renderers);
4947: for (int i = 0; i < this.renderers.size(); i++) {
4948: XYItemRenderer renderer2 = (XYItemRenderer) this.renderers.get(i);
4949: if (renderer2 instanceof PublicCloneable) {
4950: PublicCloneable pc = (PublicCloneable) renderer2;
4951: clone.renderers.set(i, pc.clone());
4952: }
4953: }
4954: clone.foregroundDomainMarkers = (Map) ObjectUtilities.clone(
4955: this.foregroundDomainMarkers);
4956: clone.backgroundDomainMarkers = (Map) ObjectUtilities.clone(
4957: this.backgroundDomainMarkers);
4958: clone.foregroundRangeMarkers = (Map) ObjectUtilities.clone(
4959: this.foregroundRangeMarkers);
4960: clone.backgroundRangeMarkers = (Map) ObjectUtilities.clone(
4961: this.backgroundRangeMarkers);
4962: clone.annotations = (List) ObjectUtilities.deepClone(this.annotations);
4963: if (this.fixedDomainAxisSpace != null) {
4964: clone.fixedDomainAxisSpace = (AxisSpace) ObjectUtilities.clone(
4965: this.fixedDomainAxisSpace);
4966: }
4967: if (this.fixedRangeAxisSpace != null) {
4968: clone.fixedRangeAxisSpace = (AxisSpace) ObjectUtilities.clone(
4969: this.fixedRangeAxisSpace);
4970: }
4971:
4972: clone.quadrantOrigin = (Point2D) ObjectUtilities.clone(
4973: this.quadrantOrigin);
4974: clone.quadrantPaint = (Paint[]) this.quadrantPaint.clone();
4975: return clone;
4976:
4977: }
4978:
4979:
4986: private void writeObject(ObjectOutputStream stream) throws IOException {
4987: stream.defaultWriteObject();
4988: SerialUtilities.writeStroke(this.domainGridlineStroke, stream);
4989: SerialUtilities.writePaint(this.domainGridlinePaint, stream);
4990: SerialUtilities.writeStroke(this.rangeGridlineStroke, stream);
4991: SerialUtilities.writePaint(this.rangeGridlinePaint, stream);
4992: SerialUtilities.writeStroke(this.rangeZeroBaselineStroke, stream);
4993: SerialUtilities.writePaint(this.rangeZeroBaselinePaint, stream);
4994: SerialUtilities.writeStroke(this.domainCrosshairStroke, stream);
4995: SerialUtilities.writePaint(this.domainCrosshairPaint, stream);
4996: SerialUtilities.writeStroke(this.rangeCrosshairStroke, stream);
4997: SerialUtilities.writePaint(this.rangeCrosshairPaint, stream);
4998: SerialUtilities.writePaint(this.domainTickBandPaint, stream);
4999: SerialUtilities.writePaint(this.rangeTickBandPaint, stream);
5000: SerialUtilities.writePoint2D(this.quadrantOrigin, stream);
5001: for (int i = 0; i < 4; i++) {
5002: SerialUtilities.writePaint(this.quadrantPaint[i], stream);
5003: }
5004: SerialUtilities.writeStroke(this.domainZeroBaselineStroke, stream);
5005: SerialUtilities.writePaint(this.domainZeroBaselinePaint, stream);
5006: }
5007:
5008:
5016: private void readObject(ObjectInputStream stream)
5017: throws IOException, ClassNotFoundException {
5018:
5019: stream.defaultReadObject();
5020: this.domainGridlineStroke = SerialUtilities.readStroke(stream);
5021: this.domainGridlinePaint = SerialUtilities.readPaint(stream);
5022: this.rangeGridlineStroke = SerialUtilities.readStroke(stream);
5023: this.rangeGridlinePaint = SerialUtilities.readPaint(stream);
5024: this.rangeZeroBaselineStroke = SerialUtilities.readStroke(stream);
5025: this.rangeZeroBaselinePaint = SerialUtilities.readPaint(stream);
5026: this.domainCrosshairStroke = SerialUtilities.readStroke(stream);
5027: this.domainCrosshairPaint = SerialUtilities.readPaint(stream);
5028: this.rangeCrosshairStroke = SerialUtilities.readStroke(stream);
5029: this.rangeCrosshairPaint = SerialUtilities.readPaint(stream);
5030: this.domainTickBandPaint = SerialUtilities.readPaint(stream);
5031: this.rangeTickBandPaint = SerialUtilities.readPaint(stream);
5032: this.quadrantOrigin = SerialUtilities.readPoint2D(stream);
5033: this.quadrantPaint = new Paint[4];
5034: for (int i = 0; i < 4; i++) {
5035: this.quadrantPaint[i] = SerialUtilities.readPaint(stream);
5036: }
5037:
5038: this.domainZeroBaselineStroke = SerialUtilities.readStroke(stream);
5039: this.domainZeroBaselinePaint = SerialUtilities.readPaint(stream);
5040:
5041:
5042:
5043: int domainAxisCount = this.domainAxes.size();
5044: for (int i = 0; i < domainAxisCount; i++) {
5045: Axis axis = (Axis) this.domainAxes.get(i);
5046: if (axis != null) {
5047: axis.setPlot(this);
5048: axis.addChangeListener(this);
5049: }
5050: }
5051: int rangeAxisCount = this.rangeAxes.size();
5052: for (int i = 0; i < rangeAxisCount; i++) {
5053: Axis axis = (Axis) this.rangeAxes.get(i);
5054: if (axis != null) {
5055: axis.setPlot(this);
5056: axis.addChangeListener(this);
5057: }
5058: }
5059: int datasetCount = this.datasets.size();
5060: for (int i = 0; i < datasetCount; i++) {
5061: Dataset dataset = (Dataset) this.datasets.get(i);
5062: if (dataset != null) {
5063: dataset.addChangeListener(this);
5064: }
5065: }
5066: int rendererCount = this.renderers.size();
5067: for (int i = 0; i < rendererCount; i++) {
5068: XYItemRenderer renderer = (XYItemRenderer) this.renderers.get(i);
5069: if (renderer != null) {
5070: renderer.addChangeListener(this);
5071: }
5072: }
5073:
5074: }
5075:
5076: }