1:
96:
97: package ;
98:
99: import ;
100: import ;
101: import ;
102: import ;
103: import ;
104: import ;
105: import ;
106: import ;
107: import ;
108: import ;
109: import ;
110: import ;
111:
112: import ;
113: import ;
114: import ;
115: import ;
116: import ;
117: import ;
118: import ;
119: import ;
120: import ;
121: import ;
122: import ;
123: import ;
124: import ;
125: import ;
126: import ;
127: import ;
128: import ;
129: import ;
130: import ;
131: import ;
132: import ;
133: import ;
134: import ;
135: import ;
136: import ;
137: import ;
138: import ;
139: import ;
140: import ;
141: import ;
142: import ;
143: import ;
144: import ;
145:
146:
152: public abstract class AbstractCategoryItemRenderer extends AbstractRenderer
153: implements CategoryItemRenderer, Cloneable, PublicCloneable, Serializable {
154:
155:
156: private static final long serialVersionUID = 1247553218442497391L;
157:
158:
159: private CategoryPlot plot;
160:
161:
162: private CategoryItemLabelGenerator itemLabelGenerator;
163:
164:
165: private ObjectList itemLabelGeneratorList;
166:
167:
168: private CategoryItemLabelGenerator baseItemLabelGenerator;
169:
170:
171: private CategoryToolTipGenerator toolTipGenerator;
172:
173:
174: private ObjectList toolTipGeneratorList;
175:
176:
177: private CategoryToolTipGenerator baseToolTipGenerator;
178:
179:
180: private CategoryURLGenerator itemURLGenerator;
181:
182:
183: private ObjectList itemURLGeneratorList;
184:
185:
186: private CategoryURLGenerator baseItemURLGenerator;
187:
188:
189: private CategorySeriesLabelGenerator legendItemLabelGenerator;
190:
191:
192: private CategorySeriesLabelGenerator legendItemToolTipGenerator;
193:
194:
195: private CategorySeriesLabelGenerator legendItemURLGenerator;
196:
197:
198: private transient int rowCount;
199:
200:
201: private transient int columnCount;
202:
203:
210: protected AbstractCategoryItemRenderer() {
211: this.itemLabelGenerator = null;
212: this.itemLabelGeneratorList = new ObjectList();
213: this.toolTipGenerator = null;
214: this.toolTipGeneratorList = new ObjectList();
215: this.itemURLGenerator = null;
216: this.itemURLGeneratorList = new ObjectList();
217: this.legendItemLabelGenerator
218: = new StandardCategorySeriesLabelGenerator();
219: }
220:
221:
228: public int getPassCount() {
229: return 1;
230: }
231:
232:
241: public CategoryPlot getPlot() {
242: return this.plot;
243: }
244:
245:
254: public void setPlot(CategoryPlot plot) {
255: if (plot == null) {
256: throw new IllegalArgumentException("Null 'plot' argument.");
257: }
258: this.plot = plot;
259: }
260:
261:
262:
263:
274: public CategoryItemLabelGenerator getItemLabelGenerator(int row,
275: int column) {
276: return getSeriesItemLabelGenerator(row);
277: }
278:
279:
288: public CategoryItemLabelGenerator getSeriesItemLabelGenerator(int series) {
289:
290:
291: if (this.itemLabelGenerator != null) {
292: return this.itemLabelGenerator;
293: }
294:
295:
296: CategoryItemLabelGenerator generator = (CategoryItemLabelGenerator)
297: this.itemLabelGeneratorList.get(series);
298: if (generator == null) {
299: generator = this.baseItemLabelGenerator;
300: }
301: return generator;
302:
303: }
304:
305:
306:
307:
313: public void setItemLabelGenerator(CategoryItemLabelGenerator generator) {
314: this.itemLabelGenerator = generator;
315: notifyListeners(new RendererChangeEvent(this));
316: }
317:
318:
327: public void setSeriesItemLabelGenerator(int series,
328: CategoryItemLabelGenerator generator) {
329: this.itemLabelGeneratorList.set(series, generator);
330: notifyListeners(new RendererChangeEvent(this));
331: }
332:
333:
340: public CategoryItemLabelGenerator getBaseItemLabelGenerator() {
341: return this.baseItemLabelGenerator;
342: }
343:
344:
352: public void setBaseItemLabelGenerator(CategoryItemLabelGenerator generator)
353: {
354: this.baseItemLabelGenerator = generator;
355: notifyListeners(new RendererChangeEvent(this));
356: }
357:
358:
359:
360:
372: public CategoryToolTipGenerator getToolTipGenerator(int row, int column) {
373:
374: CategoryToolTipGenerator result = null;
375: if (this.toolTipGenerator != null) {
376: result = this.toolTipGenerator;
377: }
378: else {
379: result = getSeriesToolTipGenerator(row);
380: if (result == null) {
381: result = this.baseToolTipGenerator;
382: }
383: }
384: return result;
385: }
386:
387:
395: public CategoryToolTipGenerator getToolTipGenerator() {
396: return this.toolTipGenerator;
397: }
398:
399:
408: public void setToolTipGenerator(CategoryToolTipGenerator generator) {
409: this.toolTipGenerator = generator;
410: notifyListeners(new RendererChangeEvent(this));
411: }
412:
413:
423: public CategoryToolTipGenerator getSeriesToolTipGenerator(int series) {
424: return (CategoryToolTipGenerator) this.toolTipGeneratorList.get(series);
425: }
426:
427:
437: public void setSeriesToolTipGenerator(int series,
438: CategoryToolTipGenerator generator) {
439: this.toolTipGeneratorList.set(series, generator);
440: notifyListeners(new RendererChangeEvent(this));
441: }
442:
443:
450: public CategoryToolTipGenerator getBaseToolTipGenerator() {
451: return this.baseToolTipGenerator;
452: }
453:
454:
462: public void setBaseToolTipGenerator(CategoryToolTipGenerator generator) {
463: this.baseToolTipGenerator = generator;
464: notifyListeners(new RendererChangeEvent(this));
465: }
466:
467:
468:
469:
479: public CategoryURLGenerator getItemURLGenerator(int row, int column) {
480: return getSeriesItemURLGenerator(row);
481: }
482:
483:
492: public CategoryURLGenerator getSeriesItemURLGenerator(int series) {
493:
494:
495: if (this.itemURLGenerator != null) {
496: return this.itemURLGenerator;
497: }
498:
499:
500: CategoryURLGenerator generator
501: = (CategoryURLGenerator) this.itemURLGeneratorList.get(series);
502: if (generator == null) {
503: generator = this.baseItemURLGenerator;
504: }
505: return generator;
506:
507: }
508:
509:
510:
511:
516: public void setItemURLGenerator(CategoryURLGenerator generator) {
517: this.itemURLGenerator = generator;
518:
519: }
520:
521:
529: public void setSeriesItemURLGenerator(int series,
530: CategoryURLGenerator generator) {
531: this.itemURLGeneratorList.set(series, generator);
532:
533: }
534:
535:
542: public CategoryURLGenerator getBaseItemURLGenerator() {
543: return this.baseItemURLGenerator;
544: }
545:
546:
553: public void setBaseItemURLGenerator(CategoryURLGenerator generator) {
554: this.baseItemURLGenerator = generator;
555:
556: }
557:
558:
564: public int getRowCount() {
565: return this.rowCount;
566: }
567:
568:
574: public int getColumnCount() {
575: return this.columnCount;
576: }
577:
578:
590: protected CategoryItemRendererState createState(PlotRenderingInfo info) {
591: return new CategoryItemRendererState(info);
592: }
593:
594:
609: public CategoryItemRendererState initialise(Graphics2D g2,
610: Rectangle2D dataArea,
611: CategoryPlot plot,
612: int rendererIndex,
613: PlotRenderingInfo info) {
614:
615: setPlot(plot);
616: CategoryDataset data = plot.getDataset(rendererIndex);
617: if (data != null) {
618: this.rowCount = data.getRowCount();
619: this.columnCount = data.getColumnCount();
620: }
621: else {
622: this.rowCount = 0;
623: this.columnCount = 0;
624: }
625: return createState(info);
626:
627: }
628:
629:
638: public Range findRangeBounds(CategoryDataset dataset) {
639: return DatasetUtilities.findRangeBounds(dataset);
640: }
641:
642:
651: public void drawBackground(Graphics2D g2,
652: CategoryPlot plot,
653: Rectangle2D dataArea) {
654:
655: plot.drawBackground(g2, dataArea);
656:
657: }
658:
659:
668: public void drawOutline(Graphics2D g2,
669: CategoryPlot plot,
670: Rectangle2D dataArea) {
671:
672: plot.drawOutline(g2, dataArea);
673:
674: }
675:
676:
692: public void drawDomainGridline(Graphics2D g2,
693: CategoryPlot plot,
694: Rectangle2D dataArea,
695: double value) {
696:
697: Line2D line = null;
698: PlotOrientation orientation = plot.getOrientation();
699:
700: if (orientation == PlotOrientation.HORIZONTAL) {
701: line = new Line2D.Double(dataArea.getMinX(), value,
702: dataArea.getMaxX(), value);
703: }
704: else if (orientation == PlotOrientation.VERTICAL) {
705: line = new Line2D.Double(value, dataArea.getMinY(), value,
706: dataArea.getMaxY());
707: }
708:
709: Paint paint = plot.getDomainGridlinePaint();
710: if (paint == null) {
711: paint = CategoryPlot.DEFAULT_GRIDLINE_PAINT;
712: }
713: g2.setPaint(paint);
714:
715: Stroke stroke = plot.getDomainGridlineStroke();
716: if (stroke == null) {
717: stroke = CategoryPlot.DEFAULT_GRIDLINE_STROKE;
718: }
719: g2.setStroke(stroke);
720:
721: g2.draw(line);
722:
723: }
724:
725:
738: public void drawRangeGridline(Graphics2D g2,
739: CategoryPlot plot,
740: ValueAxis axis,
741: Rectangle2D dataArea,
742: double value) {
743:
744: Range range = axis.getRange();
745: if (!range.contains(value)) {
746: return;
747: }
748:
749: PlotOrientation orientation = plot.getOrientation();
750: double v = axis.valueToJava2D(value, dataArea, plot.getRangeAxisEdge());
751: Line2D line = null;
752: if (orientation == PlotOrientation.HORIZONTAL) {
753: line = new Line2D.Double(v, dataArea.getMinY(), v,
754: dataArea.getMaxY());
755: }
756: else if (orientation == PlotOrientation.VERTICAL) {
757: line = new Line2D.Double(dataArea.getMinX(), v,
758: dataArea.getMaxX(), v);
759: }
760:
761: Paint paint = plot.getRangeGridlinePaint();
762: if (paint == null) {
763: paint = CategoryPlot.DEFAULT_GRIDLINE_PAINT;
764: }
765: g2.setPaint(paint);
766:
767: Stroke stroke = plot.getRangeGridlineStroke();
768: if (stroke == null) {
769: stroke = CategoryPlot.DEFAULT_GRIDLINE_STROKE;
770: }
771: g2.setStroke(stroke);
772:
773: g2.draw(line);
774:
775: }
776:
777:
789: public void drawDomainMarker(Graphics2D g2,
790: CategoryPlot plot,
791: CategoryAxis axis,
792: CategoryMarker marker,
793: Rectangle2D dataArea) {
794:
795: Comparable category = marker.getKey();
796: CategoryDataset dataset = plot.getDataset(plot.getIndexOf(this));
797: int columnIndex = dataset.getColumnIndex(category);
798: if (columnIndex < 0) {
799: return;
800: }
801:
802: final Composite savedComposite = g2.getComposite();
803: g2.setComposite(AlphaComposite.getInstance(
804: AlphaComposite.SRC_OVER, marker.getAlpha()));
805:
806: PlotOrientation orientation = plot.getOrientation();
807: Rectangle2D bounds = null;
808: if (marker.getDrawAsLine()) {
809: double v = axis.getCategoryMiddle(columnIndex,
810: dataset.getColumnCount(), dataArea,
811: plot.getDomainAxisEdge());
812: Line2D line = null;
813: if (orientation == PlotOrientation.HORIZONTAL) {
814: line = new Line2D.Double(dataArea.getMinX(), v,
815: dataArea.getMaxX(), v);
816: }
817: else if (orientation == PlotOrientation.VERTICAL) {
818: line = new Line2D.Double(v, dataArea.getMinY(), v,
819: dataArea.getMaxY());
820: }
821: g2.setPaint(marker.getPaint());
822: g2.setStroke(marker.getStroke());
823: g2.draw(line);
824: bounds = line.getBounds2D();
825: }
826: else {
827: double v0 = axis.getCategoryStart(columnIndex,
828: dataset.getColumnCount(), dataArea,
829: plot.getDomainAxisEdge());
830: double v1 = axis.getCategoryEnd(columnIndex,
831: dataset.getColumnCount(), dataArea,
832: plot.getDomainAxisEdge());
833: Rectangle2D area = null;
834: if (orientation == PlotOrientation.HORIZONTAL) {
835: area = new Rectangle2D.Double(dataArea.getMinX(), v0,
836: dataArea.getWidth(), (v1 - v0));
837: }
838: else if (orientation == PlotOrientation.VERTICAL) {
839: area = new Rectangle2D.Double(v0, dataArea.getMinY(),
840: (v1 - v0), dataArea.getHeight());
841: }
842: g2.setPaint(marker.getPaint());
843: g2.fill(area);
844: bounds = area;
845: }
846:
847: String label = marker.getLabel();
848: RectangleAnchor anchor = marker.getLabelAnchor();
849: if (label != null) {
850: Font labelFont = marker.getLabelFont();
851: g2.setFont(labelFont);
852: g2.setPaint(marker.getLabelPaint());
853: Point2D coordinates = calculateDomainMarkerTextAnchorPoint(
854: g2, orientation, dataArea, bounds, marker.getLabelOffset(),
855: marker.getLabelOffsetType(), anchor);
856: TextUtilities.drawAlignedString(label, g2,
857: (float) coordinates.getX(), (float) coordinates.getY(),
858: marker.getLabelTextAnchor());
859: }
860: g2.setComposite(savedComposite);
861: }
862:
863:
875: public void drawRangeMarker(Graphics2D g2,
876: CategoryPlot plot,
877: ValueAxis axis,
878: Marker marker,
879: Rectangle2D dataArea) {
880:
881: if (marker instanceof ValueMarker) {
882: ValueMarker vm = (ValueMarker) marker;
883: double value = vm.getValue();
884: Range range = axis.getRange();
885:
886: if (!range.contains(value)) {
887: return;
888: }
889:
890: final Composite savedComposite = g2.getComposite();
891: g2.setComposite(AlphaComposite.getInstance(
892: AlphaComposite.SRC_OVER, marker.getAlpha()));
893:
894: PlotOrientation orientation = plot.getOrientation();
895: double v = axis.valueToJava2D(value, dataArea,
896: plot.getRangeAxisEdge());
897: Line2D line = null;
898: if (orientation == PlotOrientation.HORIZONTAL) {
899: line = new Line2D.Double(v, dataArea.getMinY(), v,
900: dataArea.getMaxY());
901: }
902: else if (orientation == PlotOrientation.VERTICAL) {
903: line = new Line2D.Double(dataArea.getMinX(), v,
904: dataArea.getMaxX(), v);
905: }
906:
907: g2.setPaint(marker.getPaint());
908: g2.setStroke(marker.getStroke());
909: g2.draw(line);
910:
911: String label = marker.getLabel();
912: RectangleAnchor anchor = marker.getLabelAnchor();
913: if (label != null) {
914: Font labelFont = marker.getLabelFont();
915: g2.setFont(labelFont);
916: g2.setPaint(marker.getLabelPaint());
917: Point2D coordinates = calculateRangeMarkerTextAnchorPoint(
918: g2, orientation, dataArea, line.getBounds2D(),
919: marker.getLabelOffset(), LengthAdjustmentType.EXPAND,
920: anchor);
921: TextUtilities.drawAlignedString(label, g2,
922: (float) coordinates.getX(), (float) coordinates.getY(),
923: marker.getLabelTextAnchor());
924: }
925: g2.setComposite(savedComposite);
926: }
927: else if (marker instanceof IntervalMarker) {
928: IntervalMarker im = (IntervalMarker) marker;
929: double start = im.getStartValue();
930: double end = im.getEndValue();
931: Range range = axis.getRange();
932: if (!(range.intersects(start, end))) {
933: return;
934: }
935:
936: final Composite savedComposite = g2.getComposite();
937: g2.setComposite(AlphaComposite.getInstance(
938: AlphaComposite.SRC_OVER, marker.getAlpha()));
939:
940: double start2d = axis.valueToJava2D(start, dataArea,
941: plot.getRangeAxisEdge());
942: double end2d = axis.valueToJava2D(end, dataArea,
943: plot.getRangeAxisEdge());
944: double low = Math.min(start2d, end2d);
945: double high = Math.max(start2d, end2d);
946:
947: PlotOrientation orientation = plot.getOrientation();
948: Rectangle2D rect = null;
949: if (orientation == PlotOrientation.HORIZONTAL) {
950:
951: low = Math.max(low, dataArea.getMinX());
952: high = Math.min(high, dataArea.getMaxX());
953: rect = new Rectangle2D.Double(low,
954: dataArea.getMinY(), high - low,
955: dataArea.getHeight());
956: }
957: else if (orientation == PlotOrientation.VERTICAL) {
958:
959: low = Math.max(low, dataArea.getMinY());
960: high = Math.min(high, dataArea.getMaxY());
961: rect = new Rectangle2D.Double(dataArea.getMinX(),
962: low, dataArea.getWidth(),
963: high - low);
964: }
965: Paint p = marker.getPaint();
966: if (p instanceof GradientPaint) {
967: GradientPaint gp = (GradientPaint) p;
968: GradientPaintTransformer t = im.getGradientPaintTransformer();
969: if (t != null) {
970: gp = t.transform(gp, rect);
971: }
972: g2.setPaint(gp);
973: }
974: else {
975: g2.setPaint(p);
976: }
977: g2.fill(rect);
978:
979:
980: if (im.getOutlinePaint() != null && im.getOutlineStroke() != null) {
981: if (orientation == PlotOrientation.VERTICAL) {
982: Line2D line = new Line2D.Double();
983: double x0 = dataArea.getMinX();
984: double x1 = dataArea.getMaxX();
985: g2.setPaint(im.getOutlinePaint());
986: g2.setStroke(im.getOutlineStroke());
987: if (range.contains(start)) {
988: line.setLine(x0, start2d, x1, start2d);
989: g2.draw(line);
990: }
991: if (range.contains(end)) {
992: line.setLine(x0, end2d, x1, end2d);
993: g2.draw(line);
994: }
995: }
996: else {
997: Line2D line = new Line2D.Double();
998: double y0 = dataArea.getMinY();
999: double y1 = dataArea.getMaxY();
1000: g2.setPaint(im.getOutlinePaint());
1001: g2.setStroke(im.getOutlineStroke());
1002: if (range.contains(start)) {
1003: line.setLine(start2d, y0, start2d, y1);
1004: g2.draw(line);
1005: }
1006: if (range.contains(end)) {
1007: line.setLine(end2d, y0, end2d, y1);
1008: g2.draw(line);
1009: }
1010: }
1011: }
1012:
1013: String label = marker.getLabel();
1014: RectangleAnchor anchor = marker.getLabelAnchor();
1015: if (label != null) {
1016: Font labelFont = marker.getLabelFont();
1017: g2.setFont(labelFont);
1018: g2.setPaint(marker.getLabelPaint());
1019: Point2D coordinates = calculateRangeMarkerTextAnchorPoint(
1020: g2, orientation, dataArea, rect,
1021: marker.getLabelOffset(), marker.getLabelOffsetType(),
1022: anchor);
1023: TextUtilities.drawAlignedString(label, g2,
1024: (float) coordinates.getX(), (float) coordinates.getY(),
1025: marker.getLabelTextAnchor());
1026: }
1027: g2.setComposite(savedComposite);
1028: }
1029: }
1030:
1031:
1045: protected Point2D calculateDomainMarkerTextAnchorPoint(Graphics2D g2,
1046: PlotOrientation orientation,
1047: Rectangle2D dataArea,
1048: Rectangle2D markerArea,
1049: RectangleInsets markerOffset,
1050: LengthAdjustmentType labelOffsetType,
1051: RectangleAnchor anchor) {
1052:
1053: Rectangle2D anchorRect = null;
1054: if (orientation == PlotOrientation.HORIZONTAL) {
1055: anchorRect = markerOffset.createAdjustedRectangle(markerArea,
1056: LengthAdjustmentType.CONTRACT, labelOffsetType);
1057: }
1058: else if (orientation == PlotOrientation.VERTICAL) {
1059: anchorRect = markerOffset.createAdjustedRectangle(markerArea,
1060: labelOffsetType, LengthAdjustmentType.CONTRACT);
1061: }
1062: return RectangleAnchor.coordinates(anchorRect, anchor);
1063:
1064: }
1065:
1066:
1079: protected Point2D calculateRangeMarkerTextAnchorPoint(Graphics2D g2,
1080: PlotOrientation orientation,
1081: Rectangle2D dataArea,
1082: Rectangle2D markerArea,
1083: RectangleInsets markerOffset,
1084: LengthAdjustmentType labelOffsetType,
1085: RectangleAnchor anchor) {
1086:
1087: Rectangle2D anchorRect = null;
1088: if (orientation == PlotOrientation.HORIZONTAL) {
1089: anchorRect = markerOffset.createAdjustedRectangle(markerArea,
1090: labelOffsetType, LengthAdjustmentType.CONTRACT);
1091: }
1092: else if (orientation == PlotOrientation.VERTICAL) {
1093: anchorRect = markerOffset.createAdjustedRectangle(markerArea,
1094: LengthAdjustmentType.CONTRACT, labelOffsetType);
1095: }
1096: return RectangleAnchor.coordinates(anchorRect, anchor);
1097:
1098: }
1099:
1100:
1110: public LegendItem getLegendItem(int datasetIndex, int series) {
1111:
1112: CategoryPlot p = getPlot();
1113: if (p == null) {
1114: return null;
1115: }
1116:
1117:
1118: if (!isSeriesVisible(series) || !isSeriesVisibleInLegend(series)) {
1119: return null;
1120: }
1121:
1122: CategoryDataset dataset;
1123: dataset = p.getDataset(datasetIndex);
1124: String label = this.legendItemLabelGenerator.generateLabel(dataset,
1125: series);
1126: String description = label;
1127: String toolTipText = null;
1128: if (this.legendItemToolTipGenerator != null) {
1129: toolTipText = this.legendItemToolTipGenerator.generateLabel(
1130: dataset, series);
1131: }
1132: String urlText = null;
1133: if (this.legendItemURLGenerator != null) {
1134: urlText = this.legendItemURLGenerator.generateLabel(dataset,
1135: series);
1136: }
1137: Shape shape = getSeriesShape(series);
1138: Paint paint = getSeriesPaint(series);
1139: Paint outlinePaint = getSeriesOutlinePaint(series);
1140: Stroke outlineStroke = getSeriesOutlineStroke(series);
1141:
1142: LegendItem item = new LegendItem(label, description, toolTipText,
1143: urlText, shape, paint, outlineStroke, outlinePaint);
1144: item.setSeriesIndex(series);
1145: item.setDatasetIndex(datasetIndex);
1146: return item;
1147: }
1148:
1149:
1156: public boolean equals(Object obj) {
1157:
1158: if (obj == this) {
1159: return true;
1160: }
1161: if (!(obj instanceof AbstractCategoryItemRenderer)) {
1162: return false;
1163: }
1164: AbstractCategoryItemRenderer that = (AbstractCategoryItemRenderer) obj;
1165:
1166: if (!ObjectUtilities.equal(this.itemLabelGenerator,
1167: that.itemLabelGenerator)) {
1168: return false;
1169: }
1170: if (!ObjectUtilities.equal(this.itemLabelGeneratorList,
1171: that.itemLabelGeneratorList)) {
1172: return false;
1173: }
1174: if (!ObjectUtilities.equal(this.baseItemLabelGenerator,
1175: that.baseItemLabelGenerator)) {
1176: return false;
1177: }
1178: if (!ObjectUtilities.equal(this.toolTipGenerator,
1179: that.toolTipGenerator)) {
1180: return false;
1181: }
1182: if (!ObjectUtilities.equal(this.toolTipGeneratorList,
1183: that.toolTipGeneratorList)) {
1184: return false;
1185: }
1186: if (!ObjectUtilities.equal(this.baseToolTipGenerator,
1187: that.baseToolTipGenerator)) {
1188: return false;
1189: }
1190: if (!ObjectUtilities.equal(this.itemURLGenerator,
1191: that.itemURLGenerator)) {
1192: return false;
1193: }
1194: if (!ObjectUtilities.equal(this.itemURLGeneratorList,
1195: that.itemURLGeneratorList)) {
1196: return false;
1197: }
1198: if (!ObjectUtilities.equal(this.baseItemURLGenerator,
1199: that.baseItemURLGenerator)) {
1200: return false;
1201: }
1202: if (!ObjectUtilities.equal(this.legendItemLabelGenerator,
1203: that.legendItemLabelGenerator)) {
1204: return false;
1205: }
1206: if (!ObjectUtilities.equal(this.legendItemToolTipGenerator,
1207: that.legendItemToolTipGenerator)) {
1208: return false;
1209: }
1210: if (!ObjectUtilities.equal(this.legendItemURLGenerator,
1211: that.legendItemURLGenerator)) {
1212: return false;
1213: }
1214: return super.equals(obj);
1215: }
1216:
1217:
1222: public int hashCode() {
1223: int result = super.hashCode();
1224: return result;
1225: }
1226:
1227:
1232: public DrawingSupplier getDrawingSupplier() {
1233: DrawingSupplier result = null;
1234: CategoryPlot cp = getPlot();
1235: if (cp != null) {
1236: result = cp.getDrawingSupplier();
1237: }
1238: return result;
1239: }
1240:
1241:
1254: protected void drawItemLabel(Graphics2D g2,
1255: PlotOrientation orientation,
1256: CategoryDataset dataset,
1257: int row, int column,
1258: double x, double y,
1259: boolean negative) {
1260:
1261: CategoryItemLabelGenerator generator
1262: = getItemLabelGenerator(row, column);
1263: if (generator != null) {
1264: Font labelFont = getItemLabelFont(row, column);
1265: Paint paint = getItemLabelPaint(row, column);
1266: g2.setFont(labelFont);
1267: g2.setPaint(paint);
1268: String label = generator.generateLabel(dataset, row, column);
1269: ItemLabelPosition position = null;
1270: if (!negative) {
1271: position = getPositiveItemLabelPosition(row, column);
1272: }
1273: else {
1274: position = getNegativeItemLabelPosition(row, column);
1275: }
1276: Point2D anchorPoint = calculateLabelAnchorPoint(
1277: position.getItemLabelAnchor(), x, y, orientation);
1278: TextUtilities.drawRotatedString(label, g2,
1279: (float) anchorPoint.getX(), (float) anchorPoint.getY(),
1280: position.getTextAnchor(),
1281: position.getAngle(), position.getRotationAnchor());
1282: }
1283:
1284: }
1285:
1286:
1296: public Object clone() throws CloneNotSupportedException {
1297:
1298: AbstractCategoryItemRenderer clone
1299: = (AbstractCategoryItemRenderer) super.clone();
1300:
1301: if (this.itemLabelGenerator != null) {
1302: if (this.itemLabelGenerator instanceof PublicCloneable) {
1303: PublicCloneable pc = (PublicCloneable) this.itemLabelGenerator;
1304: clone.itemLabelGenerator
1305: = (CategoryItemLabelGenerator) pc.clone();
1306: }
1307: else {
1308: throw new CloneNotSupportedException(
1309: "ItemLabelGenerator not cloneable.");
1310: }
1311: }
1312:
1313: if (this.itemLabelGeneratorList != null) {
1314: clone.itemLabelGeneratorList
1315: = (ObjectList) this.itemLabelGeneratorList.clone();
1316: }
1317:
1318: if (this.baseItemLabelGenerator != null) {
1319: if (this.baseItemLabelGenerator instanceof PublicCloneable) {
1320: PublicCloneable pc
1321: = (PublicCloneable) this.baseItemLabelGenerator;
1322: clone.baseItemLabelGenerator
1323: = (CategoryItemLabelGenerator) pc.clone();
1324: }
1325: else {
1326: throw new CloneNotSupportedException(
1327: "ItemLabelGenerator not cloneable.");
1328: }
1329: }
1330:
1331: if (this.toolTipGenerator != null) {
1332: if (this.toolTipGenerator instanceof PublicCloneable) {
1333: PublicCloneable pc = (PublicCloneable) this.toolTipGenerator;
1334: clone.toolTipGenerator = (CategoryToolTipGenerator) pc.clone();
1335: }
1336: else {
1337: throw new CloneNotSupportedException(
1338: "Tool tip generator not cloneable.");
1339: }
1340: }
1341:
1342: if (this.toolTipGeneratorList != null) {
1343: clone.toolTipGeneratorList
1344: = (ObjectList) this.toolTipGeneratorList.clone();
1345: }
1346:
1347: if (this.baseToolTipGenerator != null) {
1348: if (this.baseToolTipGenerator instanceof PublicCloneable) {
1349: PublicCloneable pc
1350: = (PublicCloneable) this.baseToolTipGenerator;
1351: clone.baseToolTipGenerator
1352: = (CategoryToolTipGenerator) pc.clone();
1353: }
1354: else {
1355: throw new CloneNotSupportedException(
1356: "Base tool tip generator not cloneable.");
1357: }
1358: }
1359:
1360: if (this.itemURLGenerator != null) {
1361: if (this.itemURLGenerator instanceof PublicCloneable) {
1362: PublicCloneable pc = (PublicCloneable) this.itemURLGenerator;
1363: clone.itemURLGenerator = (CategoryURLGenerator) pc.clone();
1364: }
1365: else {
1366: throw new CloneNotSupportedException(
1367: "Item URL generator not cloneable.");
1368: }
1369: }
1370:
1371: if (this.itemURLGeneratorList != null) {
1372: clone.itemURLGeneratorList
1373: = (ObjectList) this.itemURLGeneratorList.clone();
1374: }
1375:
1376: if (this.baseItemURLGenerator != null) {
1377: if (this.baseItemURLGenerator instanceof PublicCloneable) {
1378: PublicCloneable pc
1379: = (PublicCloneable) this.baseItemURLGenerator;
1380: clone.baseItemURLGenerator = (CategoryURLGenerator) pc.clone();
1381: }
1382: else {
1383: throw new CloneNotSupportedException(
1384: "Base item URL generator not cloneable.");
1385: }
1386: }
1387:
1388: if (this.legendItemLabelGenerator instanceof PublicCloneable) {
1389: clone.legendItemLabelGenerator = (CategorySeriesLabelGenerator)
1390: ObjectUtilities.clone(this.legendItemLabelGenerator);
1391: }
1392: if (this.legendItemToolTipGenerator instanceof PublicCloneable) {
1393: clone.legendItemToolTipGenerator = (CategorySeriesLabelGenerator)
1394: ObjectUtilities.clone(this.legendItemToolTipGenerator);
1395: }
1396: if (this.legendItemURLGenerator instanceof PublicCloneable) {
1397: clone.legendItemURLGenerator = (CategorySeriesLabelGenerator)
1398: ObjectUtilities.clone(this.legendItemURLGenerator);
1399: }
1400: return clone;
1401: }
1402:
1403:
1411: protected CategoryAxis getDomainAxis(CategoryPlot plot, int index) {
1412: CategoryAxis result = plot.getDomainAxis(index);
1413: if (result == null) {
1414: result = plot.getDomainAxis();
1415: }
1416: return result;
1417: }
1418:
1419:
1427: protected ValueAxis getRangeAxis(CategoryPlot plot, int index) {
1428: ValueAxis result = plot.getRangeAxis(index);
1429: if (result == null) {
1430: result = plot.getRangeAxis();
1431: }
1432: return result;
1433: }
1434:
1435:
1443: public LegendItemCollection getLegendItems() {
1444: if (this.plot == null) {
1445: return new LegendItemCollection();
1446: }
1447: LegendItemCollection result = new LegendItemCollection();
1448: int index = this.plot.getIndexOf(this);
1449: CategoryDataset dataset = this.plot.getDataset(index);
1450: if (dataset != null) {
1451: int seriesCount = dataset.getRowCount();
1452: for (int i = 0; i < seriesCount; i++) {
1453: if (isSeriesVisibleInLegend(i)) {
1454: LegendItem item = getLegendItem(index, i);
1455: if (item != null) {
1456: result.add(item);
1457: }
1458: }
1459: }
1460:
1461: }
1462: return result;
1463: }
1464:
1465:
1472: public CategorySeriesLabelGenerator getLegendItemLabelGenerator() {
1473: return this.legendItemLabelGenerator;
1474: }
1475:
1476:
1484: public void setLegendItemLabelGenerator(
1485: CategorySeriesLabelGenerator generator) {
1486: if (generator == null) {
1487: throw new IllegalArgumentException("Null 'generator' argument.");
1488: }
1489: this.legendItemLabelGenerator = generator;
1490: notifyListeners(new RendererChangeEvent(this));
1491: }
1492:
1493:
1500: public CategorySeriesLabelGenerator getLegendItemToolTipGenerator() {
1501: return this.legendItemToolTipGenerator;
1502: }
1503:
1504:
1512: public void setLegendItemToolTipGenerator(
1513: CategorySeriesLabelGenerator generator) {
1514: this.legendItemToolTipGenerator = generator;
1515: notifyListeners(new RendererChangeEvent(this));
1516: }
1517:
1518:
1525: public CategorySeriesLabelGenerator getLegendItemURLGenerator() {
1526: return this.legendItemURLGenerator;
1527: }
1528:
1529:
1537: public void setLegendItemURLGenerator(
1538: CategorySeriesLabelGenerator generator) {
1539: this.legendItemURLGenerator = generator;
1540: notifyListeners(new RendererChangeEvent(this));
1541: }
1542:
1543:
1552: protected void addItemEntity(EntityCollection entities,
1553: CategoryDataset dataset, int row, int column,
1554: Shape hotspot) {
1555:
1556: String tip = null;
1557: CategoryToolTipGenerator tipster = getToolTipGenerator(row, column);
1558: if (tipster != null) {
1559: tip = tipster.generateToolTip(dataset, row, column);
1560: }
1561: String url = null;
1562: CategoryURLGenerator urlster = getItemURLGenerator(row, column);
1563: if (urlster != null) {
1564: url = urlster.generateURL(dataset, row, column);
1565: }
1566: CategoryItemEntity entity = new CategoryItemEntity(hotspot, tip, url,
1567: dataset, row, dataset.getColumnKey(column), column);
1568: entities.add(entity);
1569:
1570: }
1571:
1572: }