##// END OF EJS Templates
Added removeSeries and removeAllSeries to QML API
Tero Ahola -
r1948:1def3447669a
parent child
Show More
@@ -1,678 +1,688
1 /****************************************************************************
1 /****************************************************************************
2 **
2 **
3 ** Copyright (C) 2012 Digia Plc
3 ** Copyright (C) 2012 Digia Plc
4 ** All rights reserved.
4 ** All rights reserved.
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 **
6 **
7 ** This file is part of the Qt Commercial Charts Add-on.
7 ** This file is part of the Qt Commercial Charts Add-on.
8 **
8 **
9 ** $QT_BEGIN_LICENSE$
9 ** $QT_BEGIN_LICENSE$
10 ** Licensees holding valid Qt Commercial licenses may use this file in
10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 ** accordance with the Qt Commercial License Agreement provided with the
11 ** accordance with the Qt Commercial License Agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia.
13 ** a written agreement between you and Digia.
14 **
14 **
15 ** If you have questions regarding the use of this file, please use
15 ** If you have questions regarding the use of this file, please use
16 ** contact form at http://qt.digia.com
16 ** contact form at http://qt.digia.com
17 ** $QT_END_LICENSE$
17 ** $QT_END_LICENSE$
18 **
18 **
19 ****************************************************************************/
19 ****************************************************************************/
20
20
21 #include "declarativechart.h"
21 #include "declarativechart.h"
22 #include <QPainter>
22 #include <QPainter>
23 #include <QDeclarativeEngine>
23 #include <QDeclarativeEngine>
24 #include "declarativelineseries.h"
24 #include "declarativelineseries.h"
25 #include "declarativeareaseries.h"
25 #include "declarativeareaseries.h"
26 #include "declarativebarseries.h"
26 #include "declarativebarseries.h"
27 #include "declarativepieseries.h"
27 #include "declarativepieseries.h"
28 #include "declarativesplineseries.h"
28 #include "declarativesplineseries.h"
29 #include "declarativescatterseries.h"
29 #include "declarativescatterseries.h"
30 #include "qbarcategoryaxis.h"
30 #include "qbarcategoryaxis.h"
31 #include "qvalueaxis.h"
31 #include "qvalueaxis.h"
32 #include "qcategoryaxis.h"
32 #include "qcategoryaxis.h"
33 #include "qabstractseries_p.h"
33 #include "qabstractseries_p.h"
34 #include "declarativemargins.h"
34 #include "declarativemargins.h"
35
35
36 #ifndef QT_ON_ARM
36 #ifndef QT_ON_ARM
37 #include "qdatetimeaxis.h"
37 #include "qdatetimeaxis.h"
38 #endif
38 #endif
39
39
40 QTCOMMERCIALCHART_BEGIN_NAMESPACE
40 QTCOMMERCIALCHART_BEGIN_NAMESPACE
41
41
42 /*!
42 /*!
43 \qmlclass ChartView DeclarativeChart
43 \qmlclass ChartView DeclarativeChart
44
44
45 ChartView element is the parent that is responsible for showing different chart series types.
45 ChartView element is the parent that is responsible for showing different chart series types.
46
46
47 The following QML shows how to create a simple chart with one pie series:
47 The following QML shows how to create a simple chart with one pie series:
48 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 1
48 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 1
49 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 2
49 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 2
50 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 3
50 \snippet ../examples/qmlpiechart/qml/qmlpiechart/main.qml 3
51
51
52 \beginfloatleft
52 \beginfloatleft
53 \image examples_qmlpiechart.png
53 \image examples_qmlpiechart.png
54 \endfloat
54 \endfloat
55 \clearfloat
55 \clearfloat
56 */
56 */
57
57
58 /*!
58 /*!
59 \qmlproperty Theme ChartView::theme
59 \qmlproperty Theme ChartView::theme
60 Theme defines the visual appearance of the chart, including for example colors, fonts, line
60 Theme defines the visual appearance of the chart, including for example colors, fonts, line
61 widths and chart background.
61 widths and chart background.
62 */
62 */
63
63
64 /*!
64 /*!
65 \qmlproperty Animation ChartView::animation
65 \qmlproperty Animation ChartView::animation
66 Animation configuration of the chart. One of ChartView.NoAnimation, ChartView.GridAxisAnimations,
66 Animation configuration of the chart. One of ChartView.NoAnimation, ChartView.GridAxisAnimations,
67 ChartView.SeriesAnimations or ChartView.AllAnimations.
67 ChartView.SeriesAnimations or ChartView.AllAnimations.
68 */
68 */
69
69
70 /*!
70 /*!
71 \qmlproperty Font ChartView::titleFont
71 \qmlproperty Font ChartView::titleFont
72 The title font of the chart
72 The title font of the chart
73
73
74 See the \l {Font} {QML Font Element} for detailed documentation.
74 See the \l {Font} {QML Font Element} for detailed documentation.
75 */
75 */
76
76
77 /*!
77 /*!
78 \qmlproperty string ChartView::title
78 \qmlproperty string ChartView::title
79 The title of the chart, shown on top of the chart.
79 The title of the chart, shown on top of the chart.
80 \sa ChartView::titleColor
80 \sa ChartView::titleColor
81 */
81 */
82
82
83 /*!
83 /*!
84 \qmlproperty string ChartView::titleColor
84 \qmlproperty string ChartView::titleColor
85 The color of the title text.
85 The color of the title text.
86 */
86 */
87
87
88 /*!
88 /*!
89 \qmlproperty Axis ChartView::axisX
89 \qmlproperty Axis ChartView::axisX
90 The x-axis of the chart.
90 The x-axis of the chart.
91 */
91 */
92
92
93 /*!
93 /*!
94 \qmlproperty Axis ChartView::axisY
94 \qmlproperty Axis ChartView::axisY
95 The default y-axis of the chart.
95 The default y-axis of the chart.
96 */
96 */
97
97
98 /*!
98 /*!
99 \qmlproperty Legend ChartView::legend
99 \qmlproperty Legend ChartView::legend
100 The legend of the chart. Legend lists all the series, pie slices and bar sets added on the chart.
100 The legend of the chart. Legend lists all the series, pie slices and bar sets added on the chart.
101 */
101 */
102
102
103 /*!
103 /*!
104 \qmlproperty int ChartView::count
104 \qmlproperty int ChartView::count
105 The count of series added to the chart.
105 The count of series added to the chart.
106 */
106 */
107
107
108 /*!
108 /*!
109 \qmlproperty color ChartView::backgroundColor
109 \qmlproperty color ChartView::backgroundColor
110 The color of the chart's background. By default background color is defined by chart theme.
110 The color of the chart's background. By default background color is defined by chart theme.
111 \sa ChartView::theme
111 \sa ChartView::theme
112 */
112 */
113
113
114 /*!
114 /*!
115 \qmlproperty bool ChartView::dropShadowEnabled
115 \qmlproperty bool ChartView::dropShadowEnabled
116 The chart's border drop shadow. Set to true to enable drop shadow.
116 The chart's border drop shadow. Set to true to enable drop shadow.
117 */
117 */
118
118
119 /*!
119 /*!
120 \qmlproperty real ChartView::topMargin
120 \qmlproperty real ChartView::topMargin
121 Deprecated. Use minimumMargins and plotArea instead.
121 Deprecated. Use minimumMargins and plotArea instead.
122 */
122 */
123
123
124 /*!
124 /*!
125 \qmlproperty real ChartView::bottomMargin
125 \qmlproperty real ChartView::bottomMargin
126 Deprecated. Use minimumMargins and plotArea instead.
126 Deprecated. Use minimumMargins and plotArea instead.
127 */
127 */
128
128
129 /*!
129 /*!
130 \qmlproperty real ChartView::leftMargin
130 \qmlproperty real ChartView::leftMargin
131 Deprecated. Use minimumMargins and plotArea instead.
131 Deprecated. Use minimumMargins and plotArea instead.
132 */
132 */
133
133
134 /*!
134 /*!
135 \qmlproperty real ChartView::rightMargin
135 \qmlproperty real ChartView::rightMargin
136 Deprecated. Use minimumMargins and plotArea instead.
136 Deprecated. Use minimumMargins and plotArea instead.
137 */
137 */
138
138
139 /*!
139 /*!
140 \qmlproperty Margins ChartView::minimumMargins
140 \qmlproperty Margins ChartView::minimumMargins
141 The minimum margins allowed between the outer bounds and the plotArea of the ChartView. Margins
141 The minimum margins allowed between the outer bounds and the plotArea of the ChartView. Margins
142 area of ChartView is used for drawing title, axes and legend. Please note that setting the
142 area of ChartView is used for drawing title, axes and legend. Please note that setting the
143 properties of minimumMargins may be bigger than the defined value, depending on other ChartView
143 properties of minimumMargins may be bigger than the defined value, depending on other ChartView
144 properties that affect it's layout. If you need to know the actual plotting area used at any
144 properties that affect it's layout. If you need to know the actual plotting area used at any
145 given time, you can check ChartView::plotArea instead.
145 given time, you can check ChartView::plotArea instead.
146 */
146 */
147
147
148 /*!
148 /*!
149 \qmlproperty rect ChartView::plotArea
149 \qmlproperty rect ChartView::plotArea
150 The area on the ChartView that is used for drawing series. This is the ChartView rect without the
150 The area on the ChartView that is used for drawing series. This is the ChartView rect without the
151 margins.
151 margins.
152 \sa ChartView::minimumMargins
152 \sa ChartView::minimumMargins
153 */
153 */
154
154
155 /*!
155 /*!
156 \qmlmethod AbstractSeries ChartView::series(int index)
156 \qmlmethod AbstractSeries ChartView::series(int index)
157 Returns the series with \a index on the chart. This allows you to loop through the series of a chart together with
157 Returns the series with \a index on the chart. This allows you to loop through the series of a chart together with
158 the count property of the chart.
158 the count property of the chart.
159 */
159 */
160
160
161 /*!
161 /*!
162 \qmlmethod AbstractSeries ChartView::series(string name)
162 \qmlmethod AbstractSeries ChartView::series(string name)
163 Returns the first series on the chart with \a name. If there is no series with that name, returns null.
163 Returns the first series on the chart with \a name. If there is no series with that name, returns null.
164 */
164 */
165
165
166 /*!
166 /*!
167 \qmlmethod AbstractSeries ChartView::createSeries(SeriesType type, string name)
167 \qmlmethod AbstractSeries ChartView::createSeries(SeriesType type, string name)
168 Creates a series object of \a type to the chart. For example:
168 Creates a series object of \a type to the chart. For example:
169 \code
169 \code
170 var scatter = chartView.createSeries(ChartView.SeriesTypeScatter, "scatter series");
170 var scatter = chartView.createSeries(ChartView.SeriesTypeScatter, "scatter series");
171 scatter.markerSize = 22;
171 scatter.markerSize = 22;
172 scatter.append(1.1, 2.0);
172 scatter.append(1.1, 2.0);
173 \endcode
173 \endcode
174 */
174 */
175
175
176 /*!
176 /*!
177 \qmlmethod ChartView::removeSeries(AbstractSeries series)
178 Removes the \a series from the chart. The series object is also destroyed.
179 */
180
181 /*!
182 \qmlmethod ChartView::removeAllSeries()
183 Removes all series from the chart. All the series objects are also destroyed.
184 */
185
186 /*!
177 \qmlmethod Axis ChartView::axisY(QAbstractSeries *series)
187 \qmlmethod Axis ChartView::axisY(QAbstractSeries *series)
178 The y-axis of the series. This is the same as the default y-axis of the chart as multiple y-axes are not yet supported.
188 The y-axis of the series. This is the same as the default y-axis of the chart as multiple y-axes are not yet supported.
179 */
189 */
180
190
181 /*!
191 /*!
182 \qmlmethod ChartView::zoomY(real factor)
192 \qmlmethod ChartView::zoomY(real factor)
183 Zooms in by \a factor on the center of the chart.
193 Zooms in by \a factor on the center of the chart.
184 */
194 */
185
195
186 /*!
196 /*!
187 \qmlmethod ChartView::scrollLeft(real pixels)
197 \qmlmethod ChartView::scrollLeft(real pixels)
188 Scrolls to left by \a pixels. This is a convenience function that suits for example for key navigation.
198 Scrolls to left by \a pixels. This is a convenience function that suits for example for key navigation.
189 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
199 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
190 */
200 */
191
201
192 /*!
202 /*!
193 \qmlmethod ChartView::scrollRight(real pixels)
203 \qmlmethod ChartView::scrollRight(real pixels)
194 Scrolls to right by \a pixels. This is a convenience function that suits for example for key navigation.
204 Scrolls to right by \a pixels. This is a convenience function that suits for example for key navigation.
195 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
205 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
196 */
206 */
197
207
198 /*!
208 /*!
199 \qmlmethod ChartView::scrollUp(real pixels)
209 \qmlmethod ChartView::scrollUp(real pixels)
200 Scrolls up by \a pixels. This is a convenience function that suits for example for key navigation.
210 Scrolls up by \a pixels. This is a convenience function that suits for example for key navigation.
201 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
211 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
202 */
212 */
203
213
204 /*!
214 /*!
205 \qmlmethod ChartView::scrollDown(real pixels)
215 \qmlmethod ChartView::scrollDown(real pixels)
206 Scrolls down by \a pixels. This is a convenience function that suits for example for key navigation.
216 Scrolls down by \a pixels. This is a convenience function that suits for example for key navigation.
207 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
217 \sa ValueAxis::min, ValueAxis::max, BarCategoryAxis::min, BarCategoryAxis::max
208 */
218 */
209
219
210 /*!
220 /*!
211 \qmlsignal ChartView::onPlotAreaChanged(rect plotArea)
221 \qmlsignal ChartView::onPlotAreaChanged(rect plotArea)
212 The plot area of the chart has changed. This may happen for example, if you modify minimumMargins
222 The plot area of the chart has changed. This may happen for example, if you modify minimumMargins
213 or if you resize the chart, or if you modify font size related properties of the legend or chart
223 or if you resize the chart, or if you modify font size related properties of the legend or chart
214 title.
224 title.
215 */
225 */
216
226
217 DeclarativeChart::DeclarativeChart(QDeclarativeItem *parent)
227 DeclarativeChart::DeclarativeChart(QDeclarativeItem *parent)
218 : QDeclarativeItem(parent),
228 : QDeclarativeItem(parent),
219 m_chart(new QChart(this))
229 m_chart(new QChart(this))
220 {
230 {
221 setFlag(QGraphicsItem::ItemHasNoContents, false);
231 setFlag(QGraphicsItem::ItemHasNoContents, false);
222 m_minMargins = new DeclarativeMargins(this);
232 m_minMargins = new DeclarativeMargins(this);
223 connect(m_minMargins, SIGNAL(topChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
233 connect(m_minMargins, SIGNAL(topChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
224 connect(m_minMargins, SIGNAL(bottomChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
234 connect(m_minMargins, SIGNAL(bottomChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
225 connect(m_minMargins, SIGNAL(leftChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
235 connect(m_minMargins, SIGNAL(leftChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
226 connect(m_minMargins, SIGNAL(rightChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
236 connect(m_minMargins, SIGNAL(rightChanged(int, int, int, int)), this, SLOT(changeMinimumMargins(int, int, int, int)));
227 }
237 }
228
238
229 void DeclarativeChart::changeMinimumMargins(int top, int bottom, int left, int right)
239 void DeclarativeChart::changeMinimumMargins(int top, int bottom, int left, int right)
230 {
240 {
231 m_chart->setMinimumMargins(QMargins(left, top, right, bottom));
241 m_chart->setMinimumMargins(QMargins(left, top, right, bottom));
232 emit minimumMarginsChanged();
242 emit minimumMarginsChanged();
233 emit plotAreaChanged(m_chart->plotArea());
243 emit plotAreaChanged(m_chart->plotArea());
234 }
244 }
235
245
236 DeclarativeChart::~DeclarativeChart()
246 DeclarativeChart::~DeclarativeChart()
237 {
247 {
238 delete m_chart;
248 delete m_chart;
239 }
249 }
240
250
241 void DeclarativeChart::childEvent(QChildEvent *event)
251 void DeclarativeChart::childEvent(QChildEvent *event)
242 {
252 {
243 if (event->type() == QEvent::ChildAdded) {
253 if (event->type() == QEvent::ChildAdded) {
244 if (qobject_cast<QAbstractSeries *>(event->child())) {
254 if (qobject_cast<QAbstractSeries *>(event->child())) {
245 m_chart->addSeries(qobject_cast<QAbstractSeries *>(event->child()));
255 m_chart->addSeries(qobject_cast<QAbstractSeries *>(event->child()));
246 }
256 }
247 }
257 }
248 }
258 }
249
259
250 void DeclarativeChart::componentComplete()
260 void DeclarativeChart::componentComplete()
251 {
261 {
252 foreach(QObject *child, children()) {
262 foreach(QObject *child, children()) {
253 if (qobject_cast<QAbstractSeries *>(child)) {
263 if (qobject_cast<QAbstractSeries *>(child)) {
254 // Add series to the chart
264 // Add series to the chart
255 QAbstractSeries *series = qobject_cast<QAbstractSeries *>(child);
265 QAbstractSeries *series = qobject_cast<QAbstractSeries *>(child);
256 m_chart->addSeries(series);
266 m_chart->addSeries(series);
257
267
258 // Set optional user defined axes for the series and connect axis related signals
268 // Set optional user defined axes for the series and connect axis related signals
259 if (qobject_cast<DeclarativeLineSeries *>(child)) {
269 if (qobject_cast<DeclarativeLineSeries *>(child)) {
260 DeclarativeLineSeries *s = qobject_cast<DeclarativeLineSeries *>(child);
270 DeclarativeLineSeries *s = qobject_cast<DeclarativeLineSeries *>(child);
261 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
271 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
262 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
272 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
263 setAxisX(s->axisX(), s);
273 setAxisX(s->axisX(), s);
264 setAxisY(s->axisY(), s);
274 setAxisY(s->axisY(), s);
265 } else if (qobject_cast<DeclarativeSplineSeries *>(child)) {
275 } else if (qobject_cast<DeclarativeSplineSeries *>(child)) {
266 DeclarativeSplineSeries *s = qobject_cast<DeclarativeSplineSeries *>(child);
276 DeclarativeSplineSeries *s = qobject_cast<DeclarativeSplineSeries *>(child);
267 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
277 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
268 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
278 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
269 setAxisX(s->axisX(), s);
279 setAxisX(s->axisX(), s);
270 setAxisY(s->axisY(), s);
280 setAxisY(s->axisY(), s);
271 } else if (qobject_cast<DeclarativeScatterSeries *>(child)) {
281 } else if (qobject_cast<DeclarativeScatterSeries *>(child)) {
272 DeclarativeScatterSeries *s = qobject_cast<DeclarativeScatterSeries *>(child);
282 DeclarativeScatterSeries *s = qobject_cast<DeclarativeScatterSeries *>(child);
273 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
283 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
274 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
284 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
275 setAxisX(s->axisX(), s);
285 setAxisX(s->axisX(), s);
276 setAxisY(s->axisY(), s);
286 setAxisY(s->axisY(), s);
277 } else if (qobject_cast<DeclarativeAreaSeries *>(child)) {
287 } else if (qobject_cast<DeclarativeAreaSeries *>(child)) {
278 DeclarativeAreaSeries *s = qobject_cast<DeclarativeAreaSeries *>(child);
288 DeclarativeAreaSeries *s = qobject_cast<DeclarativeAreaSeries *>(child);
279 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
289 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
280 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
290 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
281 setAxisX(s->axisX(), s);
291 setAxisX(s->axisX(), s);
282 setAxisY(s->axisY(), s);
292 setAxisY(s->axisY(), s);
283 } else if (qobject_cast<DeclarativeBarSeries *>(child)) {
293 } else if (qobject_cast<DeclarativeBarSeries *>(child)) {
284 DeclarativeBarSeries *s = qobject_cast<DeclarativeBarSeries *>(child);
294 DeclarativeBarSeries *s = qobject_cast<DeclarativeBarSeries *>(child);
285 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
295 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
286 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
296 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
287 setAxisX(s->axisX(), s);
297 setAxisX(s->axisX(), s);
288 setAxisY(s->axisY(), s);
298 setAxisY(s->axisY(), s);
289 } else if (qobject_cast<DeclarativeStackedBarSeries *>(child)) {
299 } else if (qobject_cast<DeclarativeStackedBarSeries *>(child)) {
290 DeclarativeStackedBarSeries *s = qobject_cast<DeclarativeStackedBarSeries *>(child);
300 DeclarativeStackedBarSeries *s = qobject_cast<DeclarativeStackedBarSeries *>(child);
291 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
301 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
292 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
302 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
293 setAxisX(s->axisX(), s);
303 setAxisX(s->axisX(), s);
294 setAxisY(s->axisY(), s);
304 setAxisY(s->axisY(), s);
295 } else if (qobject_cast<DeclarativePercentBarSeries *>(child)) {
305 } else if (qobject_cast<DeclarativePercentBarSeries *>(child)) {
296 DeclarativePercentBarSeries *s = qobject_cast<DeclarativePercentBarSeries *>(child);
306 DeclarativePercentBarSeries *s = qobject_cast<DeclarativePercentBarSeries *>(child);
297 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
307 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
298 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
308 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
299 setAxisX(s->axisX(), s);
309 setAxisX(s->axisX(), s);
300 setAxisY(s->axisY(), s);
310 setAxisY(s->axisY(), s);
301 } else if (qobject_cast<DeclarativeHorizontalBarSeries *>(child)) {
311 } else if (qobject_cast<DeclarativeHorizontalBarSeries *>(child)) {
302 DeclarativeHorizontalBarSeries *s = qobject_cast<DeclarativeHorizontalBarSeries *>(child);
312 DeclarativeHorizontalBarSeries *s = qobject_cast<DeclarativeHorizontalBarSeries *>(child);
303 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
313 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
304 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
314 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
305 setAxisX(s->axisX(), s);
315 setAxisX(s->axisX(), s);
306 setAxisY(s->axisY(), s);
316 setAxisY(s->axisY(), s);
307 } else if (qobject_cast<DeclarativeHorizontalStackedBarSeries *>(child)) {
317 } else if (qobject_cast<DeclarativeHorizontalStackedBarSeries *>(child)) {
308 DeclarativeHorizontalStackedBarSeries *s = qobject_cast<DeclarativeHorizontalStackedBarSeries *>(child);
318 DeclarativeHorizontalStackedBarSeries *s = qobject_cast<DeclarativeHorizontalStackedBarSeries *>(child);
309 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
319 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
310 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
320 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
311 setAxisX(s->axisX(), s);
321 setAxisX(s->axisX(), s);
312 setAxisY(s->axisY(), s);
322 setAxisY(s->axisY(), s);
313 } else if (qobject_cast<DeclarativeHorizontalPercentBarSeries *>(child)) {
323 } else if (qobject_cast<DeclarativeHorizontalPercentBarSeries *>(child)) {
314 DeclarativeHorizontalPercentBarSeries *s = qobject_cast<DeclarativeHorizontalPercentBarSeries *>(child);
324 DeclarativeHorizontalPercentBarSeries *s = qobject_cast<DeclarativeHorizontalPercentBarSeries *>(child);
315 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
325 connect(s, SIGNAL(axisXChanged(QAbstractAxis*)), this, SLOT(handleAxisXSet(QAbstractAxis*)));
316 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
326 connect(s, SIGNAL(axisYChanged(QAbstractAxis*)), this, SLOT(handleAxisYSet(QAbstractAxis*)));
317 setAxisX(s->axisX(), s);
327 setAxisX(s->axisX(), s);
318 setAxisY(s->axisY(), s);
328 setAxisY(s->axisY(), s);
319 }
329 }
320 }
330 }
321 }
331 }
322
332
323 // Create the missing axes for the series that cannot be painted without axes
333 // Create the missing axes for the series that cannot be painted without axes
324 foreach (QAbstractSeries *chartSeries, m_chart->series())
334 foreach (QAbstractSeries *chartSeries, m_chart->series())
325 createDefaultAxes(chartSeries);
335 createDefaultAxes(chartSeries);
326
336
327 QDeclarativeItem::componentComplete();
337 QDeclarativeItem::componentComplete();
328 }
338 }
329
339
330 void DeclarativeChart::handleAxisXSet(QAbstractAxis* axis)
340 void DeclarativeChart::handleAxisXSet(QAbstractAxis* axis)
331 {
341 {
332 // qDebug() << "DeclarativeChart::handleAxisXSet" << sender() << axis;
342 // qDebug() << "DeclarativeChart::handleAxisXSet" << sender() << axis;
333 if (axis && qobject_cast<QAbstractSeries *>(sender()))
343 if (axis && qobject_cast<QAbstractSeries *>(sender()))
334 m_chart->setAxisX(axis, qobject_cast<QAbstractSeries *>(sender()));
344 m_chart->setAxisX(axis, qobject_cast<QAbstractSeries *>(sender()));
335 else
345 else
336 qWarning() << "Trying to set axisX to null.";
346 qWarning() << "Trying to set axisX to null.";
337 }
347 }
338
348
339 void DeclarativeChart::handleAxisYSet(QAbstractAxis* axis)
349 void DeclarativeChart::handleAxisYSet(QAbstractAxis* axis)
340 {
350 {
341 // qDebug() << "DeclarativeChart::handleAxisYSet" << sender() << axis;
351 // qDebug() << "DeclarativeChart::handleAxisYSet" << sender() << axis;
342 if (axis && qobject_cast<QAbstractSeries *>(sender()))
352 if (axis && qobject_cast<QAbstractSeries *>(sender()))
343 m_chart->setAxisY(axis, qobject_cast<QAbstractSeries *>(sender()));
353 m_chart->setAxisY(axis, qobject_cast<QAbstractSeries *>(sender()));
344 else
354 else
345 qWarning() << "Trying to set axisY to null.";
355 qWarning() << "Trying to set axisY to null.";
346 }
356 }
347
357
348 void DeclarativeChart::geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry)
358 void DeclarativeChart::geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry)
349 {
359 {
350 // qDebug() << "DeclarativeChart::geometryChanged" << newGeometry.width() << newGeometry.height();
360 // qDebug() << "DeclarativeChart::geometryChanged" << newGeometry.width() << newGeometry.height();
351 if (newGeometry.isValid()) {
361 if (newGeometry.isValid()) {
352 if (newGeometry.width() > 0 && newGeometry.height() > 0) {
362 if (newGeometry.width() > 0 && newGeometry.height() > 0) {
353 m_chart->resize(newGeometry.width(), newGeometry.height());
363 m_chart->resize(newGeometry.width(), newGeometry.height());
354 }
364 }
355 }
365 }
356 QDeclarativeItem::geometryChanged(newGeometry, oldGeometry);
366 QDeclarativeItem::geometryChanged(newGeometry, oldGeometry);
357
367
358 // It would be better to trigger the plotAreaChanged signal from QChart::plotAreaChanged or
368 // It would be better to trigger the plotAreaChanged signal from QChart::plotAreaChanged or
359 // similar. Since that kind of a signal is not clearly needed in the C++ API the work-around is
369 // similar. Since that kind of a signal is not clearly needed in the C++ API the work-around is
360 // to implement it here for the QML API purposes.
370 // to implement it here for the QML API purposes.
361 emit plotAreaChanged(m_chart->plotArea());
371 emit plotAreaChanged(m_chart->plotArea());
362 }
372 }
363
373
364 void DeclarativeChart::setTheme(DeclarativeChart::Theme theme)
374 void DeclarativeChart::setTheme(DeclarativeChart::Theme theme)
365 {
375 {
366 QChart::ChartTheme chartTheme = (QChart::ChartTheme) theme;
376 QChart::ChartTheme chartTheme = (QChart::ChartTheme) theme;
367 if (chartTheme != m_chart->theme())
377 if (chartTheme != m_chart->theme())
368 m_chart->setTheme(chartTheme);
378 m_chart->setTheme(chartTheme);
369 }
379 }
370
380
371 DeclarativeChart::Theme DeclarativeChart::theme()
381 DeclarativeChart::Theme DeclarativeChart::theme()
372 {
382 {
373 return (DeclarativeChart::Theme) m_chart->theme();
383 return (DeclarativeChart::Theme) m_chart->theme();
374 }
384 }
375
385
376 void DeclarativeChart::setAnimationOptions(DeclarativeChart::Animation animations)
386 void DeclarativeChart::setAnimationOptions(DeclarativeChart::Animation animations)
377 {
387 {
378 QChart::AnimationOption animationOptions = (QChart::AnimationOption) animations;
388 QChart::AnimationOption animationOptions = (QChart::AnimationOption) animations;
379 if (animationOptions != m_chart->animationOptions())
389 if (animationOptions != m_chart->animationOptions())
380 m_chart->setAnimationOptions(animationOptions);
390 m_chart->setAnimationOptions(animationOptions);
381 }
391 }
382
392
383 DeclarativeChart::Animation DeclarativeChart::animationOptions()
393 DeclarativeChart::Animation DeclarativeChart::animationOptions()
384 {
394 {
385 if (m_chart->animationOptions().testFlag(QChart::AllAnimations))
395 if (m_chart->animationOptions().testFlag(QChart::AllAnimations))
386 return DeclarativeChart::AllAnimations;
396 return DeclarativeChart::AllAnimations;
387 else if (m_chart->animationOptions().testFlag(QChart::GridAxisAnimations))
397 else if (m_chart->animationOptions().testFlag(QChart::GridAxisAnimations))
388 return DeclarativeChart::GridAxisAnimations;
398 return DeclarativeChart::GridAxisAnimations;
389 else if (m_chart->animationOptions().testFlag(QChart::SeriesAnimations))
399 else if (m_chart->animationOptions().testFlag(QChart::SeriesAnimations))
390 return DeclarativeChart::SeriesAnimations;
400 return DeclarativeChart::SeriesAnimations;
391 else
401 else
392 return DeclarativeChart::NoAnimation;
402 return DeclarativeChart::NoAnimation;
393 }
403 }
394
404
395 void DeclarativeChart::setTitle(QString title)
405 void DeclarativeChart::setTitle(QString title)
396 {
406 {
397 if (title != m_chart->title())
407 if (title != m_chart->title())
398 m_chart->setTitle(title);
408 m_chart->setTitle(title);
399 }
409 }
400 QString DeclarativeChart::title()
410 QString DeclarativeChart::title()
401 {
411 {
402 return m_chart->title();
412 return m_chart->title();
403 }
413 }
404
414
405 QAbstractAxis *DeclarativeChart::axisX(QAbstractSeries *series)
415 QAbstractAxis *DeclarativeChart::axisX(QAbstractSeries *series)
406 {
416 {
407 return m_chart->axisX(series);
417 return m_chart->axisX(series);
408 }
418 }
409
419
410 QAbstractAxis *DeclarativeChart::axisY(QAbstractSeries *series)
420 QAbstractAxis *DeclarativeChart::axisY(QAbstractSeries *series)
411 {
421 {
412 return m_chart->axisY(series);
422 return m_chart->axisY(series);
413 }
423 }
414
424
415 QLegend *DeclarativeChart::legend()
425 QLegend *DeclarativeChart::legend()
416 {
426 {
417 return m_chart->legend();
427 return m_chart->legend();
418 }
428 }
419
429
420 void DeclarativeChart::setTitleColor(QColor color)
430 void DeclarativeChart::setTitleColor(QColor color)
421 {
431 {
422 QBrush b = m_chart->titleBrush();
432 QBrush b = m_chart->titleBrush();
423 if (color != b.color()) {
433 if (color != b.color()) {
424 b.setColor(color);
434 b.setColor(color);
425 m_chart->setTitleBrush(b);
435 m_chart->setTitleBrush(b);
426 emit titleColorChanged(color);
436 emit titleColorChanged(color);
427 }
437 }
428 }
438 }
429
439
430 QFont DeclarativeChart::titleFont() const
440 QFont DeclarativeChart::titleFont() const
431 {
441 {
432 return m_chart->titleFont();
442 return m_chart->titleFont();
433 }
443 }
434
444
435 void DeclarativeChart::setTitleFont(const QFont& font)
445 void DeclarativeChart::setTitleFont(const QFont& font)
436 {
446 {
437 m_chart->setTitleFont(font);
447 m_chart->setTitleFont(font);
438 }
448 }
439
449
440 QColor DeclarativeChart::titleColor()
450 QColor DeclarativeChart::titleColor()
441 {
451 {
442 return m_chart->titleBrush().color();
452 return m_chart->titleBrush().color();
443 }
453 }
444
454
445 void DeclarativeChart::setBackgroundColor(QColor color)
455 void DeclarativeChart::setBackgroundColor(QColor color)
446 {
456 {
447 QBrush b = m_chart->backgroundBrush();
457 QBrush b = m_chart->backgroundBrush();
448 if (b.style() != Qt::SolidPattern || color != b.color()) {
458 if (b.style() != Qt::SolidPattern || color != b.color()) {
449 b.setStyle(Qt::SolidPattern);
459 b.setStyle(Qt::SolidPattern);
450 b.setColor(color);
460 b.setColor(color);
451 m_chart->setBackgroundBrush(b);
461 m_chart->setBackgroundBrush(b);
452 emit backgroundColorChanged();
462 emit backgroundColorChanged();
453 }
463 }
454 }
464 }
455
465
456 QColor DeclarativeChart::backgroundColor()
466 QColor DeclarativeChart::backgroundColor()
457 {
467 {
458 return m_chart->backgroundBrush().color();
468 return m_chart->backgroundBrush().color();
459 }
469 }
460
470
461 int DeclarativeChart::count()
471 int DeclarativeChart::count()
462 {
472 {
463 return m_chart->series().count();
473 return m_chart->series().count();
464 }
474 }
465
475
466 void DeclarativeChart::setDropShadowEnabled(bool enabled)
476 void DeclarativeChart::setDropShadowEnabled(bool enabled)
467 {
477 {
468 if (enabled != m_chart->isDropShadowEnabled()) {
478 if (enabled != m_chart->isDropShadowEnabled()) {
469 m_chart->setDropShadowEnabled(enabled);
479 m_chart->setDropShadowEnabled(enabled);
470 dropShadowEnabledChanged(enabled);
480 dropShadowEnabledChanged(enabled);
471 }
481 }
472 }
482 }
473
483
474 bool DeclarativeChart::dropShadowEnabled()
484 bool DeclarativeChart::dropShadowEnabled()
475 {
485 {
476 return m_chart->isDropShadowEnabled();
486 return m_chart->isDropShadowEnabled();
477 }
487 }
478
488
479 qreal DeclarativeChart::topMargin()
489 qreal DeclarativeChart::topMargin()
480 {
490 {
481 qWarning() << "ChartView.topMargin is deprecated. Use minimumMargins and plotArea instead.";
491 qWarning() << "ChartView.topMargin is deprecated. Use minimumMargins and plotArea instead.";
482 return m_chart->plotArea().top();
492 return m_chart->plotArea().top();
483 }
493 }
484
494
485 qreal DeclarativeChart::bottomMargin()
495 qreal DeclarativeChart::bottomMargin()
486 {
496 {
487 qWarning() << "ChartView.bottomMargin is deprecated. Use minimumMargins and plotArea instead.";
497 qWarning() << "ChartView.bottomMargin is deprecated. Use minimumMargins and plotArea instead.";
488 return m_chart->plotArea().bottom();
498 return m_chart->plotArea().bottom();
489 }
499 }
490
500
491 qreal DeclarativeChart::leftMargin()
501 qreal DeclarativeChart::leftMargin()
492 {
502 {
493 qWarning() << "ChartView.leftMargin is deprecated. Use minimumMargins and plotArea instead.";
503 qWarning() << "ChartView.leftMargin is deprecated. Use minimumMargins and plotArea instead.";
494 return m_chart->plotArea().left();
504 return m_chart->plotArea().left();
495 }
505 }
496
506
497 qreal DeclarativeChart::rightMargin()
507 qreal DeclarativeChart::rightMargin()
498 {
508 {
499 qWarning() << "ChartView.rightMargin is deprecated. Use minimumMargins and plotArea instead.";
509 qWarning() << "ChartView.rightMargin is deprecated. Use minimumMargins and plotArea instead.";
500 return m_chart->plotArea().right();
510 return m_chart->plotArea().right();
501 }
511 }
502
512
503 void DeclarativeChart::zoom(qreal factor)
513 void DeclarativeChart::zoom(qreal factor)
504 {
514 {
505 m_chart->zoom(factor);
515 m_chart->zoom(factor);
506 }
516 }
507
517
508 void DeclarativeChart::scrollLeft(qreal pixels)
518 void DeclarativeChart::scrollLeft(qreal pixels)
509 {
519 {
510 m_chart->scroll(pixels, 0);
520 m_chart->scroll(pixels, 0);
511 }
521 }
512
522
513 void DeclarativeChart::scrollRight(qreal pixels)
523 void DeclarativeChart::scrollRight(qreal pixels)
514 {
524 {
515 m_chart->scroll(-pixels, 0);
525 m_chart->scroll(-pixels, 0);
516 }
526 }
517
527
518 void DeclarativeChart::scrollUp(qreal pixels)
528 void DeclarativeChart::scrollUp(qreal pixels)
519 {
529 {
520 m_chart->scroll(0, pixels);
530 m_chart->scroll(0, pixels);
521 }
531 }
522
532
523 void DeclarativeChart::scrollDown(qreal pixels)
533 void DeclarativeChart::scrollDown(qreal pixels)
524 {
534 {
525 m_chart->scroll(0, -pixels);
535 m_chart->scroll(0, -pixels);
526 }
536 }
527
537
528 QAbstractSeries *DeclarativeChart::series(int index)
538 QAbstractSeries *DeclarativeChart::series(int index)
529 {
539 {
530 if (index < m_chart->series().count()) {
540 if (index < m_chart->series().count()) {
531 return m_chart->series().at(index);
541 return m_chart->series().at(index);
532 }
542 }
533 return 0;
543 return 0;
534 }
544 }
535
545
536 QAbstractSeries *DeclarativeChart::series(QString seriesName)
546 QAbstractSeries *DeclarativeChart::series(QString seriesName)
537 {
547 {
538 foreach(QAbstractSeries *series, m_chart->series()) {
548 foreach(QAbstractSeries *series, m_chart->series()) {
539 if (series->name() == seriesName)
549 if (series->name() == seriesName)
540 return series;
550 return series;
541 }
551 }
542 return 0;
552 return 0;
543 }
553 }
544
554
545 QAbstractSeries *DeclarativeChart::createSeries(DeclarativeChart::SeriesType type, QString name)
555 QAbstractSeries *DeclarativeChart::createSeries(DeclarativeChart::SeriesType type, QString name)
546 {
556 {
547 QAbstractSeries *series = 0;
557 QAbstractSeries *series = 0;
548
558
549 switch (type) {
559 switch (type) {
550 case DeclarativeChart::SeriesTypeLine:
560 case DeclarativeChart::SeriesTypeLine:
551 series = new DeclarativeLineSeries();
561 series = new DeclarativeLineSeries();
552 break;
562 break;
553 case DeclarativeChart::SeriesTypeArea:
563 case DeclarativeChart::SeriesTypeArea:
554 series = new DeclarativeAreaSeries();
564 series = new DeclarativeAreaSeries();
555 break;
565 break;
556 case DeclarativeChart::SeriesTypeStackedBar:
566 case DeclarativeChart::SeriesTypeStackedBar:
557 series = new DeclarativeStackedBarSeries();
567 series = new DeclarativeStackedBarSeries();
558 break;
568 break;
559 case DeclarativeChart::SeriesTypePercentBar:
569 case DeclarativeChart::SeriesTypePercentBar:
560 series = new DeclarativePercentBarSeries();
570 series = new DeclarativePercentBarSeries();
561 break;
571 break;
562 case DeclarativeChart::SeriesTypeBar:
572 case DeclarativeChart::SeriesTypeBar:
563 series = new DeclarativeBarSeries();
573 series = new DeclarativeBarSeries();
564 break;
574 break;
565 case DeclarativeChart::SeriesTypeHorizontalBar:
575 case DeclarativeChart::SeriesTypeHorizontalBar:
566 series = new DeclarativeHorizontalBarSeries();
576 series = new DeclarativeHorizontalBarSeries();
567 break;
577 break;
568 case DeclarativeChart::SeriesTypeHorizontalPercentBar:
578 case DeclarativeChart::SeriesTypeHorizontalPercentBar:
569 series = new DeclarativeHorizontalPercentBarSeries();
579 series = new DeclarativeHorizontalPercentBarSeries();
570 break;
580 break;
571 case DeclarativeChart::SeriesTypeHorizontalStackedBar:
581 case DeclarativeChart::SeriesTypeHorizontalStackedBar:
572 series = new DeclarativeHorizontalStackedBarSeries();
582 series = new DeclarativeHorizontalStackedBarSeries();
573 break;
583 break;
574 case DeclarativeChart::SeriesTypePie:
584 case DeclarativeChart::SeriesTypePie:
575 series = new DeclarativePieSeries();
585 series = new DeclarativePieSeries();
576 break;
586 break;
577 case DeclarativeChart::SeriesTypeScatter:
587 case DeclarativeChart::SeriesTypeScatter:
578 series = new DeclarativeScatterSeries();
588 series = new DeclarativeScatterSeries();
579 break;
589 break;
580 case DeclarativeChart::SeriesTypeSpline:
590 case DeclarativeChart::SeriesTypeSpline:
581 series = new DeclarativeSplineSeries();
591 series = new DeclarativeSplineSeries();
582 break;
592 break;
583 default:
593 default:
584 qWarning() << "Illegal series type";
594 qWarning() << "Illegal series type";
585 }
595 }
586
596
587 if (series) {
597 if (series) {
588 series->setName(name);
598 series->setName(name);
589 m_chart->addSeries(series);
599 m_chart->addSeries(series);
590 createDefaultAxes(series);
600 createDefaultAxes(series);
591 }
601 }
592
602
593 return series;
603 return series;
594 }
604 }
595
605
596 void DeclarativeChart::setAxisX(QAbstractAxis *axis, QAbstractSeries *series)
606 void DeclarativeChart::setAxisX(QAbstractAxis *axis, QAbstractSeries *series)
597 {
607 {
598 if (axis)
608 if (axis)
599 m_chart->setAxisX(axis, series);
609 m_chart->setAxisX(axis, series);
600 }
610 }
601
611
602 void DeclarativeChart::setAxisY(QAbstractAxis *axis, QAbstractSeries *series)
612 void DeclarativeChart::setAxisY(QAbstractAxis *axis, QAbstractSeries *series)
603 {
613 {
604 if (axis)
614 if (axis)
605 m_chart->setAxisY(axis, series);
615 m_chart->setAxisY(axis, series);
606 }
616 }
607
617
608 void DeclarativeChart::createDefaultAxes()
618 void DeclarativeChart::createDefaultAxes()
609 {
619 {
610 qWarning() << "ChartView.createDefaultAxes() is deprecated. Axes are created automatically.";
620 qWarning() << "ChartView.createDefaultAxes() is deprecated. Axes are created automatically.";
611 }
621 }
612
622
613 void DeclarativeChart::createDefaultAxes(QAbstractSeries* series)
623 void DeclarativeChart::createDefaultAxes(QAbstractSeries* series)
614 {
624 {
615 foreach (QAbstractSeries *s, m_chart->series()) {
625 foreach (QAbstractSeries *s, m_chart->series()) {
616 // If there is already an x axis of the correct type, re-use it
626 // If there is already an x axis of the correct type, re-use it
617 if (!m_chart->axisX(series) && s != series && m_chart->axisX(s)
627 if (!m_chart->axisX(series) && s != series && m_chart->axisX(s)
618 && m_chart->axisX(s)->type() == series->d_ptr->defaultAxisType(Qt::Horizontal))
628 && m_chart->axisX(s)->type() == series->d_ptr->defaultAxisType(Qt::Horizontal))
619 m_chart->setAxisX(m_chart->axisX(s), series);
629 m_chart->setAxisX(m_chart->axisX(s), series);
620
630
621 // If there is already a y axis of the correct type, re-use it
631 // If there is already a y axis of the correct type, re-use it
622 if (!m_chart->axisY(series) && s != series && m_chart->axisY(s)
632 if (!m_chart->axisY(series) && s != series && m_chart->axisY(s)
623 && m_chart->axisY(s)->type() == series->d_ptr->defaultAxisType(Qt::Vertical))
633 && m_chart->axisY(s)->type() == series->d_ptr->defaultAxisType(Qt::Vertical))
624 m_chart->setAxisY(m_chart->axisY(s), series);
634 m_chart->setAxisY(m_chart->axisY(s), series);
625 }
635 }
626
636
627 // If no x axis of correct type was found, create a new x axis based of default axis type
637 // If no x axis of correct type was found, create a new x axis based of default axis type
628 if (!m_chart->axisX(series)) {
638 if (!m_chart->axisX(series)) {
629 switch (series->d_ptr->defaultAxisType(Qt::Horizontal)) {
639 switch (series->d_ptr->defaultAxisType(Qt::Horizontal)) {
630 case QAbstractAxis::AxisTypeValue:
640 case QAbstractAxis::AxisTypeValue:
631 m_chart->setAxisX(new QValueAxis(this), series);
641 m_chart->setAxisX(new QValueAxis(this), series);
632 break;
642 break;
633 case QAbstractAxis::AxisTypeBarCategory:
643 case QAbstractAxis::AxisTypeBarCategory:
634 m_chart->setAxisX(new QBarCategoryAxis(this), series);
644 m_chart->setAxisX(new QBarCategoryAxis(this), series);
635 break;
645 break;
636 case QAbstractAxis::AxisTypeCategory:
646 case QAbstractAxis::AxisTypeCategory:
637 m_chart->setAxisX(new QCategoryAxis(this), series);
647 m_chart->setAxisX(new QCategoryAxis(this), series);
638 break;
648 break;
639 #ifndef QT_ON_ARM
649 #ifndef QT_ON_ARM
640 case QAbstractAxis::AxisTypeDateTime:
650 case QAbstractAxis::AxisTypeDateTime:
641 m_chart->setAxisX(new QDateTimeAxis(this), series);
651 m_chart->setAxisX(new QDateTimeAxis(this), series);
642 break;
652 break;
643 #endif
653 #endif
644 default:
654 default:
645 // Do nothing, assume AxisTypeNoAxis
655 // Do nothing, assume AxisTypeNoAxis
646 break;
656 break;
647 }
657 }
648 }
658 }
649
659
650 // If no y axis of correct type was found, create a new y axis based of default axis type
660 // If no y axis of correct type was found, create a new y axis based of default axis type
651 if (!m_chart->axisY(series)) {
661 if (!m_chart->axisY(series)) {
652 switch (series->d_ptr->defaultAxisType(Qt::Vertical)) {
662 switch (series->d_ptr->defaultAxisType(Qt::Vertical)) {
653 case QAbstractAxis::AxisTypeValue:
663 case QAbstractAxis::AxisTypeValue:
654 m_chart->setAxisY(new QValueAxis(this), series);
664 m_chart->setAxisY(new QValueAxis(this), series);
655 break;
665 break;
656 case QAbstractAxis::AxisTypeBarCategory:
666 case QAbstractAxis::AxisTypeBarCategory:
657 m_chart->setAxisY(new QBarCategoryAxis(this), series);
667 m_chart->setAxisY(new QBarCategoryAxis(this), series);
658 break;
668 break;
659 case QAbstractAxis::AxisTypeCategory:
669 case QAbstractAxis::AxisTypeCategory:
660 m_chart->setAxisY(new QCategoryAxis(this), series);
670 m_chart->setAxisY(new QCategoryAxis(this), series);
661 break;
671 break;
662 #ifndef QT_ON_ARM
672 #ifndef QT_ON_ARM
663 case QAbstractAxis::AxisTypeDateTime:
673 case QAbstractAxis::AxisTypeDateTime:
664 m_chart->setAxisY(new QDateTimeAxis(this), series);
674 m_chart->setAxisY(new QDateTimeAxis(this), series);
665 break;
675 break;
666 #endif
676 #endif
667 default:
677 default:
668 // Do nothing, assume AxisTypeNoAxis
678 // Do nothing, assume AxisTypeNoAxis
669 break;
679 break;
670 }
680 }
671 }
681 }
672
682
673 //qDebug() << "axis for series" << series << "x:" << m_chart->axisX(series) << "y:" << m_chart->axisY(series);
683 //qDebug() << "axis for series" << series << "x:" << m_chart->axisX(series) << "y:" << m_chart->axisY(series);
674 }
684 }
675
685
676 #include "moc_declarativechart.cpp"
686 #include "moc_declarativechart.cpp"
677
687
678 QTCOMMERCIALCHART_END_NAMESPACE
688 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,160 +1,161
1 /****************************************************************************
1 /****************************************************************************
2 **
2 **
3 ** Copyright (C) 2012 Digia Plc
3 ** Copyright (C) 2012 Digia Plc
4 ** All rights reserved.
4 ** All rights reserved.
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 **
6 **
7 ** This file is part of the Qt Commercial Charts Add-on.
7 ** This file is part of the Qt Commercial Charts Add-on.
8 **
8 **
9 ** $QT_BEGIN_LICENSE$
9 ** $QT_BEGIN_LICENSE$
10 ** Licensees holding valid Qt Commercial licenses may use this file in
10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 ** accordance with the Qt Commercial License Agreement provided with the
11 ** accordance with the Qt Commercial License Agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia.
13 ** a written agreement between you and Digia.
14 **
14 **
15 ** If you have questions regarding the use of this file, please use
15 ** If you have questions regarding the use of this file, please use
16 ** contact form at http://qt.digia.com
16 ** contact form at http://qt.digia.com
17 ** $QT_END_LICENSE$
17 ** $QT_END_LICENSE$
18 **
18 **
19 ****************************************************************************/
19 ****************************************************************************/
20
20
21 #ifndef DECLARATIVECHART_H
21 #ifndef DECLARATIVECHART_H
22 #define DECLARATIVECHART_H
22 #define DECLARATIVECHART_H
23
23
24 #include <QtCore/QtGlobal>
24 #include <QtCore/QtGlobal>
25 #include <QDeclarativeItem>
25 #include <QDeclarativeItem>
26 #include "qchart.h"
26 #include "qchart.h"
27
27
28 QTCOMMERCIALCHART_BEGIN_NAMESPACE
28 QTCOMMERCIALCHART_BEGIN_NAMESPACE
29
29
30 class DeclarativeMargins;
30 class DeclarativeMargins;
31
31
32 class DeclarativeChart : public QDeclarativeItem
32 class DeclarativeChart : public QDeclarativeItem
33 {
33 {
34 Q_OBJECT
34 Q_OBJECT
35 Q_PROPERTY(Theme theme READ theme WRITE setTheme)
35 Q_PROPERTY(Theme theme READ theme WRITE setTheme)
36 Q_PROPERTY(Animation animationOptions READ animationOptions WRITE setAnimationOptions)
36 Q_PROPERTY(Animation animationOptions READ animationOptions WRITE setAnimationOptions)
37 Q_PROPERTY(QString title READ title WRITE setTitle)
37 Q_PROPERTY(QString title READ title WRITE setTitle)
38 Q_PROPERTY(QFont titleFont READ titleFont WRITE setTitleFont)
38 Q_PROPERTY(QFont titleFont READ titleFont WRITE setTitleFont)
39 Q_PROPERTY(QColor titleColor READ titleColor WRITE setTitleColor NOTIFY titleColorChanged)
39 Q_PROPERTY(QColor titleColor READ titleColor WRITE setTitleColor NOTIFY titleColorChanged)
40 Q_PROPERTY(QLegend *legend READ legend)
40 Q_PROPERTY(QLegend *legend READ legend)
41 Q_PROPERTY(int count READ count)
41 Q_PROPERTY(int count READ count)
42 Q_PROPERTY(QColor backgroundColor READ backgroundColor WRITE setBackgroundColor NOTIFY backgroundColorChanged)
42 Q_PROPERTY(QColor backgroundColor READ backgroundColor WRITE setBackgroundColor NOTIFY backgroundColorChanged)
43 Q_PROPERTY(bool dropShadowEnabled READ dropShadowEnabled WRITE setDropShadowEnabled NOTIFY dropShadowEnabledChanged)
43 Q_PROPERTY(bool dropShadowEnabled READ dropShadowEnabled WRITE setDropShadowEnabled NOTIFY dropShadowEnabledChanged)
44 Q_PROPERTY(qreal topMargin READ topMargin)
44 Q_PROPERTY(qreal topMargin READ topMargin)
45 Q_PROPERTY(qreal bottomMargin READ bottomMargin)
45 Q_PROPERTY(qreal bottomMargin READ bottomMargin)
46 Q_PROPERTY(qreal leftMargin READ leftMargin)
46 Q_PROPERTY(qreal leftMargin READ leftMargin)
47 Q_PROPERTY(qreal rightMargin READ rightMargin)
47 Q_PROPERTY(qreal rightMargin READ rightMargin)
48 Q_PROPERTY(DeclarativeMargins *minimumMargins READ minimumMargins NOTIFY minimumMarginsChanged REVISION 1)
48 Q_PROPERTY(DeclarativeMargins *minimumMargins READ minimumMargins NOTIFY minimumMarginsChanged REVISION 1)
49 Q_PROPERTY(QRectF plotArea READ plotArea NOTIFY plotAreaChanged REVISION 1)
49 Q_PROPERTY(QRectF plotArea READ plotArea NOTIFY plotAreaChanged REVISION 1)
50 Q_ENUMS(Animation)
50 Q_ENUMS(Animation)
51 Q_ENUMS(Theme)
51 Q_ENUMS(Theme)
52 Q_ENUMS(SeriesType)
52 Q_ENUMS(SeriesType)
53
53
54 public:
54 public:
55 // duplicating enums from QChart to make the QML api namings 1-to-1 with the C++ api
55 // duplicating enums from QChart to make the QML api namings 1-to-1 with the C++ api
56 enum Theme {
56 enum Theme {
57 ChartThemeLight = 0,
57 ChartThemeLight = 0,
58 ChartThemeBlueCerulean,
58 ChartThemeBlueCerulean,
59 ChartThemeDark,
59 ChartThemeDark,
60 ChartThemeBrownSand,
60 ChartThemeBrownSand,
61 ChartThemeBlueNcs,
61 ChartThemeBlueNcs,
62 ChartThemeHighContrast,
62 ChartThemeHighContrast,
63 ChartThemeBlueIcy
63 ChartThemeBlueIcy
64 };
64 };
65
65
66 enum Animation {
66 enum Animation {
67 NoAnimation = 0x0,
67 NoAnimation = 0x0,
68 GridAxisAnimations = 0x1,
68 GridAxisAnimations = 0x1,
69 SeriesAnimations =0x2,
69 SeriesAnimations =0x2,
70 AllAnimations = 0x3
70 AllAnimations = 0x3
71 };
71 };
72
72
73 enum SeriesType {
73 enum SeriesType {
74 SeriesTypeLine,
74 SeriesTypeLine,
75 SeriesTypeArea,
75 SeriesTypeArea,
76 SeriesTypeBar,
76 SeriesTypeBar,
77 SeriesTypeStackedBar,
77 SeriesTypeStackedBar,
78 SeriesTypePercentBar,
78 SeriesTypePercentBar,
79 SeriesTypePie,
79 SeriesTypePie,
80 SeriesTypeScatter,
80 SeriesTypeScatter,
81 SeriesTypeSpline,
81 SeriesTypeSpline,
82 SeriesTypeHorizontalBar,
82 SeriesTypeHorizontalBar,
83 SeriesTypeHorizontalStackedBar,
83 SeriesTypeHorizontalStackedBar,
84 SeriesTypeHorizontalPercentBar
84 SeriesTypeHorizontalPercentBar
85 };
85 };
86
86
87 public:
87 public:
88 DeclarativeChart(QDeclarativeItem *parent = 0);
88 DeclarativeChart(QDeclarativeItem *parent = 0);
89 ~DeclarativeChart();
89 ~DeclarativeChart();
90
90
91 public: // From QDeclarativeItem/QGraphicsItem
91 public: // From QDeclarativeItem/QGraphicsItem
92 void childEvent(QChildEvent *event);
92 void childEvent(QChildEvent *event);
93 void componentComplete();
93 void componentComplete();
94 void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry);
94 void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry);
95
95
96 public:
96 public:
97 void setTheme(DeclarativeChart::Theme theme);
97 void setTheme(DeclarativeChart::Theme theme);
98 DeclarativeChart::Theme theme();
98 DeclarativeChart::Theme theme();
99 void setAnimationOptions(DeclarativeChart::Animation animations);
99 void setAnimationOptions(DeclarativeChart::Animation animations);
100 DeclarativeChart::Animation animationOptions();
100 DeclarativeChart::Animation animationOptions();
101 void setTitle(QString title);
101 void setTitle(QString title);
102 QString title();
102 QString title();
103 QLegend *legend();
103 QLegend *legend();
104 QFont titleFont() const;
104 QFont titleFont() const;
105 void setTitleFont(const QFont& font);
105 void setTitleFont(const QFont& font);
106 void setTitleColor(QColor color);
106 void setTitleColor(QColor color);
107 QColor titleColor();
107 QColor titleColor();
108 void setBackgroundColor(QColor color);
108 void setBackgroundColor(QColor color);
109 QColor backgroundColor();
109 QColor backgroundColor();
110 int count();
110 int count();
111 void setDropShadowEnabled(bool enabled);
111 void setDropShadowEnabled(bool enabled);
112 bool dropShadowEnabled();
112 bool dropShadowEnabled();
113 qreal topMargin();
113 qreal topMargin();
114 qreal bottomMargin();
114 qreal bottomMargin();
115 qreal leftMargin();
115 qreal leftMargin();
116 qreal rightMargin();
116 qreal rightMargin();
117 void createDefaultAxes(QAbstractSeries* series);
117 void createDefaultAxes(QAbstractSeries* series);
118 DeclarativeMargins *minimumMargins() { return m_minMargins; }
118 DeclarativeMargins *minimumMargins() { return m_minMargins; }
119 QRectF plotArea() { return m_chart->plotArea(); }
119 QRectF plotArea() { return m_chart->plotArea(); }
120
120
121 public:
121 public:
122 Q_INVOKABLE QAbstractSeries *series(int index);
122 Q_INVOKABLE QAbstractSeries *series(int index);
123 Q_INVOKABLE QAbstractSeries *series(QString seriesName);
123 Q_INVOKABLE QAbstractSeries *series(QString seriesName);
124 Q_INVOKABLE QAbstractSeries *createSeries(DeclarativeChart::SeriesType type, QString name = "");
124 Q_INVOKABLE QAbstractSeries *createSeries(DeclarativeChart::SeriesType type, QString name = "");
125 Q_INVOKABLE void removeSeries(QAbstractSeries *series) { m_chart->removeSeries(series); }
126 Q_INVOKABLE void removeAllSeries() { m_chart->removeAllSeries(); }
125 Q_INVOKABLE void setAxisX(QAbstractAxis *axis, QAbstractSeries *series = 0);
127 Q_INVOKABLE void setAxisX(QAbstractAxis *axis, QAbstractSeries *series = 0);
126 Q_INVOKABLE void setAxisY(QAbstractAxis *axis, QAbstractSeries *series = 0);
128 Q_INVOKABLE void setAxisY(QAbstractAxis *axis, QAbstractSeries *series = 0);
127 Q_INVOKABLE void createDefaultAxes();
129 Q_INVOKABLE void createDefaultAxes();
128 Q_INVOKABLE QAbstractAxis *axisX(QAbstractSeries *series = 0);
130 Q_INVOKABLE QAbstractAxis *axisX(QAbstractSeries *series = 0);
129 Q_INVOKABLE QAbstractAxis *axisY(QAbstractSeries *series = 0);
131 Q_INVOKABLE QAbstractAxis *axisY(QAbstractSeries *series = 0);
130
131 Q_INVOKABLE void zoom(qreal factor);
132 Q_INVOKABLE void zoom(qreal factor);
132 Q_INVOKABLE void scrollLeft(qreal pixels);
133 Q_INVOKABLE void scrollLeft(qreal pixels);
133 Q_INVOKABLE void scrollRight(qreal pixels);
134 Q_INVOKABLE void scrollRight(qreal pixels);
134 Q_INVOKABLE void scrollUp(qreal pixels);
135 Q_INVOKABLE void scrollUp(qreal pixels);
135 Q_INVOKABLE void scrollDown(qreal pixels);
136 Q_INVOKABLE void scrollDown(qreal pixels);
136
137
137 Q_SIGNALS:
138 Q_SIGNALS:
138 void axisLabelsChanged();
139 void axisLabelsChanged();
139 void titleColorChanged(QColor color);
140 void titleColorChanged(QColor color);
140 void backgroundColorChanged();
141 void backgroundColorChanged();
141 void dropShadowEnabledChanged(bool enabled);
142 void dropShadowEnabledChanged(bool enabled);
142 void minimumMarginsChanged();
143 void minimumMarginsChanged();
143 void plotAreaChanged(QRectF plotArea);
144 void plotAreaChanged(QRectF plotArea);
144
145
145 public Q_SLOTS:
146 public Q_SLOTS:
146 void changeMinimumMargins(int top, int bottom, int left, int right);
147 void changeMinimumMargins(int top, int bottom, int left, int right);
147 void handleAxisXSet(QAbstractAxis *axis);
148 void handleAxisXSet(QAbstractAxis *axis);
148 void handleAxisYSet(QAbstractAxis *axis);
149 void handleAxisYSet(QAbstractAxis *axis);
149
150
150 private:
151 private:
151 // Extending QChart with DeclarativeChart is not possible because QObject does not support
152 // Extending QChart with DeclarativeChart is not possible because QObject does not support
152 // multi inheritance, so we now have a QChart as a member instead
153 // multi inheritance, so we now have a QChart as a member instead
153 QChart *m_chart;
154 QChart *m_chart;
154 //QMargins m_chartMargins;
155 //QMargins m_chartMargins;
155 DeclarativeMargins *m_minMargins;
156 DeclarativeMargins *m_minMargins;
156 };
157 };
157
158
158 QTCOMMERCIALCHART_END_NAMESPACE
159 QTCOMMERCIALCHART_END_NAMESPACE
159
160
160 #endif // DECLARATIVECHART_H
161 #endif // DECLARATIVECHART_H
@@ -1,68 +1,68
1 /****************************************************************************
1 /****************************************************************************
2 **
2 **
3 ** Copyright (C) 2012 Digia Plc
3 ** Copyright (C) 2012 Digia Plc
4 ** All rights reserved.
4 ** All rights reserved.
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 **
6 **
7 ** This file is part of the Qt Commercial Charts Add-on.
7 ** This file is part of the Qt Commercial Charts Add-on.
8 **
8 **
9 ** $QT_BEGIN_LICENSE$
9 ** $QT_BEGIN_LICENSE$
10 ** Licensees holding valid Qt Commercial licenses may use this file in
10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 ** accordance with the Qt Commercial License Agreement provided with the
11 ** accordance with the Qt Commercial License Agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia.
13 ** a written agreement between you and Digia.
14 **
14 **
15 ** If you have questions regarding the use of this file, please use
15 ** If you have questions regarding the use of this file, please use
16 ** contact form at http://qt.digia.com
16 ** contact form at http://qt.digia.com
17 ** $QT_END_LICENSE$
17 ** $QT_END_LICENSE$
18 **
18 **
19 ****************************************************************************/
19 ****************************************************************************/
20
20
21 import QtQuick 1.0
21 import QtQuick 1.0
22 import QtCommercial.Chart 1.1
22 import QtCommercial.Chart 1.1
23
23
24 ChartView {
24 ChartView {
25 id: chartView
25 id: chartView
26 title: "creating dyn. new series"
26 title: "creating dyn. new series"
27 property int index: 0
27 property int index: 0
28
28
29 Timer {
29 Timer {
30 interval: 1000
30 interval: 1000
31 repeat: true
31 repeat: true
32 running: true
32 running: true
33 onTriggered: {
33 onTriggered: {
34 switch (index) {
34 switch (index) {
35 case 0:
35 case 0:
36 while (chartView.count) {
36 var count = chartView.count;
37 console.log("Destroying series. Count: " + chartView.count);
38 chartView.series(0).destroy();
39 }
40 var line = chartView.createSeries(ChartView.SeriesTypeLine, "line");
37 var line = chartView.createSeries(ChartView.SeriesTypeLine, "line");
41 line.append(0, 0);
38 line.append(0, 0);
42 line.append(1, 1);
39 line.append(1, 1);
43 line.append(2, 2);
40 line.append(2, 2);
44 line.append(3, 3);
41 line.append(3, 3);
45 line.append(4, 4);
42 line.append(4, 4);
46 break;
43 break;
47 case 1:
44 case 1:
48 chartView.axisX().min = 0;
45 chartView.axisX().min = 0;
49 chartView.axisX().max = 4.5;
46 chartView.axisX().max = 4.5;
50 chartView.axisY().min = 0;
47 chartView.axisY().min = 0;
51 chartView.axisY().max = 4.5;
48 chartView.axisY().max = 4.5;
52 break;
49 break;
53 default:
50 case 2:
54 var scatter = chartView.createSeries(ChartView.SeriesTypeScatter, "scatter");
51 var scatter = chartView.createSeries(ChartView.SeriesTypeScatter, "scatter");
55 scatter.append(0, 0);
52 scatter.append(0, 0);
56 scatter.append(0.5, 1);
53 scatter.append(0.5, 1);
57 scatter.append(1, 2);
54 scatter.append(1, 2);
58 scatter.append(1.5, 3);
55 scatter.append(1.5, 3);
59 scatter.append(2, 4);
56 scatter.append(2, 4);
60 scatter.append(1, 1);
57 scatter.append(1, 1);
61 scatter.append(2, 2);
58 scatter.append(2, 2);
62 scatter.append(3, 3);
59 scatter.append(3, 3);
63 scatter.append(4, 4);
60 scatter.append(4, 4);
61 break;
62 default:
63 chartView.removeAllSeries();
64 }
64 }
65 index = (index + 1) % 3;
65 index = (index + 1) % 4;
66 }
66 }
67 }
67 }
68 }
68 }
General Comments 0
You need to be logged in to leave comments. Login now