comparison gnv-artifacts/src/main/java/de/intevation/gnv/chart/AbstractXYLineChart.java @ 540:80630520e25a

merged gnv-artifacts/0.4
author Thomas Arendsen Hein <thomas@intevation.de>
date Fri, 28 Sep 2012 12:13:49 +0200
parents d41c155db337
children b98d1adee7a6
comparison
equal deleted inserted replaced
415:9f4a0b990d27 540:80630520e25a
1 package de.intevation.gnv.chart;
2
3 import java.awt.Color;
4 import java.awt.geom.Ellipse2D;
5 import java.text.NumberFormat;
6 import java.util.Collection;
7 import java.util.Iterator;
8 import java.util.Locale;
9 import java.util.Map;
10
11 import org.apache.log4j.Logger;
12
13 import org.jfree.chart.JFreeChart;
14 import org.jfree.chart.ChartFactory;
15 import org.jfree.chart.axis.Axis;
16 import org.jfree.chart.axis.NumberAxis;
17 import org.jfree.chart.axis.NumberTickUnit;
18 import org.jfree.chart.axis.AxisLocation;
19 import org.jfree.chart.plot.PlotOrientation;
20 import org.jfree.chart.plot.XYPlot;
21 import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
22 import org.jfree.chart.title.TextTitle;
23 import org.jfree.data.xy.XYDataset;
24 import org.jfree.data.Range;
25 import org.jfree.data.general.Series;
26
27 import de.intevation.gnv.geobackend.base.Result;
28 import de.intevation.gnv.state.describedata.KeyValueDescibeData;
29
30
31 /**
32 * @author Ingo Weinzierl <ingo.weinzierl@intevation.de>
33 */
34 public abstract class AbstractXYLineChart
35 extends AbstractChart
36 {
37 public static final double LOWER_MARGIN = 0.05D;
38 public static final double UPPER_MARGIN = 0.05D;
39
40 private static Logger log = Logger.getLogger(AbstractXYLineChart.class);
41
42 protected static Color[] COLOR = {
43 Color.black, Color.red, Color.green, Color.blue, Color.yellow,
44 Color.gray, Color.orange, Color.pink, Color.cyan
45 };
46
47 protected static int nextColor = 0;
48
49 protected PlotOrientation PLOT_ORIENTATION = PlotOrientation.VERTICAL;
50
51 /** Map to store datasets for each parameter */
52 protected Map datasets;
53
54 /** Map to store max ranges of each parameter (axis.setAutoRange(true)
55 * doesn't seem to work */
56 protected Map ranges;
57
58 protected abstract void initData();
59 protected abstract void addValue(Result row, Series series);
60 protected abstract void addSeries(Series series, String label, int idx);
61 protected abstract void localizeDomainAxis(Axis axis, Locale locale);
62 protected abstract String createSeriesName(
63 String breakPoint1,
64 String breakPoint2,
65 String breakPoint3
66 );
67
68
69 public JFreeChart generateChart() {
70 log.debug("generate XYLineChart");
71 nextColor = 0;
72
73 if (chart != null)
74 return chart;
75
76 initChart();
77
78 chart.addSubtitle(new TextTitle(labels.getSubtitle()));
79
80 theme.apply(chart);
81 initData();
82
83 adjustPlot((XYPlot)chart.getPlot());
84
85 return chart;
86 }
87
88
89 protected void initChart() {
90 chart = ChartFactory.createXYLineChart(
91 labels.getTitle(),
92 labels.getDomainAxisLabel(),
93 null,
94 null,
95 PLOT_ORIENTATION,
96 true,
97 false,
98 false
99 );
100 }
101
102
103 protected void prepareAxis(String seriesKey, int idx) {
104 log.debug("prepare axis of xychart");
105
106 XYPlot plot = chart.getXYPlot();
107 Axis xAxis = plot.getDomainAxis();
108 NumberAxis yAxis = new NumberAxis(seriesKey);
109
110 localizeDomainAxis(xAxis, locale);
111 localizeRangeAxis(yAxis, locale);
112
113 // litte workarround to adjust the max range of axes.
114 // NumberAxis.setAutoRange(true) doesn't seem to work properly.
115 Range yRange = (Range) ranges.get(seriesKey);
116 yAxis.setRange(Range.expand(yRange, LOWER_MARGIN, UPPER_MARGIN));
117 log.debug("Max Range of dataset is: " + yRange.toString());
118
119 if (seriesKey.contains("richtung")) {
120 yAxis.setTickUnit(new NumberTickUnit(30.0));
121 yAxis.setUpperBound(360.0);
122 yAxis.setLowerBound(0.0);
123 }
124 else {
125 yAxis.setFixedDimension(10.0);
126 yAxis.setAutoRangeIncludesZero(false);
127 }
128
129 plot.setRangeAxis(idx, yAxis);
130 yAxis.configure();
131
132 if (idx % 2 != 0)
133 plot.setRangeAxisLocation(idx, AxisLocation.BOTTOM_OR_RIGHT);
134 else
135 plot.setRangeAxisLocation(idx, AxisLocation.BOTTOM_OR_LEFT);
136
137 plot.mapDatasetToRangeAxis(idx, idx);
138 }
139
140
141 protected void adjustRenderer(
142 int idx,
143 int seriesCount,
144 boolean renderLines,
145 boolean renderShapes
146 ) {
147 log.debug("Adjust render of series");
148 XYLineAndShapeRenderer renderer = null;
149 XYPlot plot = chart.getXYPlot();
150
151 try {
152 renderer = (XYLineAndShapeRenderer)((XYLineAndShapeRenderer)
153 (plot.getRenderer())).clone();
154 }
155 catch (CloneNotSupportedException cnse) {
156 log.warn("Error while cloning renderer.", cnse);
157 renderer = new XYLineAndShapeRenderer(renderLines, renderShapes);
158 renderer.setBaseShape(new Ellipse2D.Double(-2,-2,4,4));
159 }
160
161 for (int i = 0; i < seriesCount; i++) {
162 renderer.setSeriesShape(i, renderer.getSeriesShape(0));
163 renderer.setSeriesPaint(i, COLOR[nextColor%COLOR.length]);
164 renderer.setSeriesShapesVisible(i, renderShapes);
165 renderer.setSeriesLinesVisible(i, renderLines);
166 nextColor++;
167 }
168 plot.setRenderer(idx, renderer);
169 }
170
171
172 protected void adjustPlot(XYPlot plot) {
173 if (plot.getRangeAxisCount() > 1)
174 plot.setRangeGridlinesVisible(false);
175 }
176
177
178 protected void localizeRangeAxis(Axis axis, Locale locale) {
179 if (locale == null)
180 return;
181
182 log.debug(
183 "Set language of axis [" + axis.getLabel() + "] " +
184 "to " + locale.toString()
185 );
186
187 NumberFormat format = NumberFormat.getInstance(locale);
188 ((NumberAxis) axis).setNumberFormatOverride(format);
189 }
190
191
192 public Range getMaxRangeOfDataset(XYDataset dataset) {
193 int seriesCount = dataset.getSeriesCount();
194 double upper = Double.NEGATIVE_INFINITY;
195 double lower = Double.POSITIVE_INFINITY;
196
197 for (int i = 0; i < seriesCount; i++) {
198 int itemCount = dataset.getItemCount(i);
199
200 for (int j = 0; j < itemCount; j++) {
201 Number num = dataset.getY(i, j);
202
203 if (num != null) {
204 double y = num.doubleValue();
205 lower = y < lower ? y : lower;
206 upper = y > upper ? y : upper;
207 }
208 }
209 }
210
211 return new Range(lower, upper);
212 }
213
214
215 public Range getMaxRangeOfDatasetWithMargin(
216 XYDataset dataset,
217 double percent
218 ) {
219 Range range = getMaxRangeOfDataset(dataset);
220 double length = range.getLength();
221 double upper = range.getUpperBound() + length /100 * percent;
222 double lower = range.getLowerBound() - length /100 * percent;
223
224 return new Range(lower, upper);
225 }
226
227
228 protected String findParameter(String label) {
229 Iterator iter = parameters.iterator();
230
231 while (iter.hasNext()) {
232 KeyValueDescibeData data = (KeyValueDescibeData) iter.next();
233 String key = data.getValue();
234
235 if (label.indexOf(key) > -1)
236 return key;
237 }
238
239 return label;
240 }
241
242
243 protected String findValueTitle(Collection values, String id) {
244 log.debug("find description of dataset");
245
246 if (values != null){
247 Iterator it = values.iterator();
248 while (it.hasNext()) {
249 KeyValueDescibeData data = (KeyValueDescibeData) it.next();
250
251 if (id.equals(data.getKey()))
252 return data.getValue();
253 }
254 }
255 return "";
256 }
257
258
259 protected void storeMaxRange(double value, String parameter) {
260 Range range = null;
261
262 range = ranges.containsKey(parameter)
263 ? (Range) ranges.get(parameter)
264 : new Range(value, value);
265
266 double lower = range.getLowerBound();
267 double upper = range.getUpperBound();
268
269 lower = value < lower ? value : lower;
270 upper = value > upper ? value : upper;
271
272 ranges.put(parameter, new Range(lower, upper));
273 }
274 }
275 // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf-8 :

http://dive4elements.wald.intevation.org