##// END OF EJS Templates
Added one more type of label placing on Pie chart
Marek Rosa -
r1712:0c76e21b1f34
parent child
Show More
@@ -1,347 +1,349
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 #include "mainwidget.h"
20 #include "mainwidget.h"
21 #include "customslice.h"
21 #include "customslice.h"
22 #include "pentool.h"
22 #include "pentool.h"
23 #include "brushtool.h"
23 #include "brushtool.h"
24 #include <QPushButton>
24 #include <QPushButton>
25 #include <QComboBox>
25 #include <QComboBox>
26 #include <QCheckBox>
26 #include <QCheckBox>
27 #include <QLineEdit>
27 #include <QLineEdit>
28 #include <QGroupBox>
28 #include <QGroupBox>
29 #include <QDoubleSpinBox>
29 #include <QDoubleSpinBox>
30 #include <QFormLayout>
30 #include <QFormLayout>
31 #include <QFontDialog>
31 #include <QFontDialog>
32 #include <QChartView>
32 #include <QChartView>
33 #include <QPieSeries>
33 #include <QPieSeries>
34
34
35 QTCOMMERCIALCHART_USE_NAMESPACE
35 QTCOMMERCIALCHART_USE_NAMESPACE
36
36
37 MainWidget::MainWidget(QWidget* parent)
37 MainWidget::MainWidget(QWidget* parent)
38 :QWidget(parent),
38 :QWidget(parent),
39 m_slice(0)
39 m_slice(0)
40 {
40 {
41 // create chart
41 // create chart
42 QChart *chart = new QChart;
42 QChart *chart = new QChart;
43 chart->setTitle("Piechart customization");
43 chart->setTitle("Piechart customization");
44 chart->setAnimationOptions(QChart::AllAnimations);
44 chart->setAnimationOptions(QChart::AllAnimations);
45
45
46 // create series
46 // create series
47 m_series = new QPieSeries();
47 m_series = new QPieSeries();
48 *m_series << new CustomSlice("Slice 1", 10.0);
48 *m_series << new CustomSlice("Slice 1", 10.0);
49 *m_series << new CustomSlice("Slice 2", 20.0);
49 *m_series << new CustomSlice("Slice 2", 20.0);
50 *m_series << new CustomSlice("Slice 3", 30.0);
50 *m_series << new CustomSlice("Slice 3", 30.0);
51 *m_series << new CustomSlice("Slice 4", 40.0);
51 *m_series << new CustomSlice("Slice 4", 40.0);
52 *m_series << new CustomSlice("Slice 5", 50.0);
52 *m_series << new CustomSlice("Slice 5", 50.0);
53 m_series->setLabelsVisible();
53 m_series->setLabelsVisible();
54 chart->addSeries(m_series);
54 chart->addSeries(m_series);
55
55
56 connect(m_series, SIGNAL(clicked(QPieSlice*)), this, SLOT(handleSliceClicked(QPieSlice*)));
56 connect(m_series, SIGNAL(clicked(QPieSlice*)), this, SLOT(handleSliceClicked(QPieSlice*)));
57
57
58 // chart settings
58 // chart settings
59 m_themeComboBox = new QComboBox();
59 m_themeComboBox = new QComboBox();
60 m_themeComboBox->addItem("Light", QChart::ChartThemeLight);
60 m_themeComboBox->addItem("Light", QChart::ChartThemeLight);
61 m_themeComboBox->addItem("BlueCerulean", QChart::ChartThemeBlueCerulean);
61 m_themeComboBox->addItem("BlueCerulean", QChart::ChartThemeBlueCerulean);
62 m_themeComboBox->addItem("Dark", QChart::ChartThemeDark);
62 m_themeComboBox->addItem("Dark", QChart::ChartThemeDark);
63 m_themeComboBox->addItem("BrownSand", QChart::ChartThemeBrownSand);
63 m_themeComboBox->addItem("BrownSand", QChart::ChartThemeBrownSand);
64 m_themeComboBox->addItem("BlueNcs", QChart::ChartThemeBlueNcs);
64 m_themeComboBox->addItem("BlueNcs", QChart::ChartThemeBlueNcs);
65 m_themeComboBox->addItem("High Contrast", QChart::ChartThemeHighContrast);
65 m_themeComboBox->addItem("High Contrast", QChart::ChartThemeHighContrast);
66 m_themeComboBox->addItem("Blue Icy", QChart::ChartThemeBlueIcy);
66 m_themeComboBox->addItem("Blue Icy", QChart::ChartThemeBlueIcy);
67
67
68 m_aaCheckBox = new QCheckBox();
68 m_aaCheckBox = new QCheckBox();
69 m_animationsCheckBox = new QCheckBox();
69 m_animationsCheckBox = new QCheckBox();
70 m_animationsCheckBox->setCheckState(Qt::Checked);
70 m_animationsCheckBox->setCheckState(Qt::Checked);
71
71
72 m_legendCheckBox = new QCheckBox();
72 m_legendCheckBox = new QCheckBox();
73
73
74 QFormLayout* chartSettingsLayout = new QFormLayout();
74 QFormLayout* chartSettingsLayout = new QFormLayout();
75 chartSettingsLayout->addRow("Theme", m_themeComboBox);
75 chartSettingsLayout->addRow("Theme", m_themeComboBox);
76 chartSettingsLayout->addRow("Antialiasing", m_aaCheckBox);
76 chartSettingsLayout->addRow("Antialiasing", m_aaCheckBox);
77 chartSettingsLayout->addRow("Animations", m_animationsCheckBox);
77 chartSettingsLayout->addRow("Animations", m_animationsCheckBox);
78 chartSettingsLayout->addRow("Legend", m_legendCheckBox);
78 chartSettingsLayout->addRow("Legend", m_legendCheckBox);
79 QGroupBox* chartSettings = new QGroupBox("Chart");
79 QGroupBox* chartSettings = new QGroupBox("Chart");
80 chartSettings->setLayout(chartSettingsLayout);
80 chartSettings->setLayout(chartSettingsLayout);
81
81
82 connect(m_themeComboBox, SIGNAL(currentIndexChanged(int)), this ,SLOT(updateChartSettings()));
82 connect(m_themeComboBox, SIGNAL(currentIndexChanged(int)), this ,SLOT(updateChartSettings()));
83 connect(m_aaCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
83 connect(m_aaCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
84 connect(m_animationsCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
84 connect(m_animationsCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
85 connect(m_legendCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
85 connect(m_legendCheckBox, SIGNAL(toggled(bool)), this ,SLOT(updateChartSettings()));
86
86
87 // series settings
87 // series settings
88 m_hPosition = new QDoubleSpinBox();
88 m_hPosition = new QDoubleSpinBox();
89 m_hPosition->setMinimum(0.0);
89 m_hPosition->setMinimum(0.0);
90 m_hPosition->setMaximum(1.0);
90 m_hPosition->setMaximum(1.0);
91 m_hPosition->setSingleStep(0.1);
91 m_hPosition->setSingleStep(0.1);
92 m_hPosition->setValue(m_series->horizontalPosition());
92 m_hPosition->setValue(m_series->horizontalPosition());
93
93
94 m_vPosition = new QDoubleSpinBox();
94 m_vPosition = new QDoubleSpinBox();
95 m_vPosition->setMinimum(0.0);
95 m_vPosition->setMinimum(0.0);
96 m_vPosition->setMaximum(1.0);
96 m_vPosition->setMaximum(1.0);
97 m_vPosition->setSingleStep(0.1);
97 m_vPosition->setSingleStep(0.1);
98 m_vPosition->setValue(m_series->verticalPosition());
98 m_vPosition->setValue(m_series->verticalPosition());
99
99
100 m_sizeFactor = new QDoubleSpinBox();
100 m_sizeFactor = new QDoubleSpinBox();
101 m_sizeFactor->setMinimum(0.0);
101 m_sizeFactor->setMinimum(0.0);
102 m_sizeFactor->setMaximum(1.0);
102 m_sizeFactor->setMaximum(1.0);
103 m_sizeFactor->setSingleStep(0.1);
103 m_sizeFactor->setSingleStep(0.1);
104 m_sizeFactor->setValue(m_series->pieSize());
104 m_sizeFactor->setValue(m_series->pieSize());
105
105
106 m_startAngle = new QDoubleSpinBox();
106 m_startAngle = new QDoubleSpinBox();
107 m_startAngle->setMinimum(-720);
107 m_startAngle->setMinimum(-720);
108 m_startAngle->setMaximum(720);
108 m_startAngle->setMaximum(720);
109 m_startAngle->setValue(m_series->pieStartAngle());
109 m_startAngle->setValue(m_series->pieStartAngle());
110 m_startAngle->setSingleStep(1);
110 m_startAngle->setSingleStep(1);
111
111
112 m_endAngle = new QDoubleSpinBox();
112 m_endAngle = new QDoubleSpinBox();
113 m_endAngle->setMinimum(-720);
113 m_endAngle->setMinimum(-720);
114 m_endAngle->setMaximum(720);
114 m_endAngle->setMaximum(720);
115 m_endAngle->setValue(m_series->pieEndAngle());
115 m_endAngle->setValue(m_series->pieEndAngle());
116 m_endAngle->setSingleStep(1);
116 m_endAngle->setSingleStep(1);
117
117
118 QPushButton *appendSlice = new QPushButton("Append slice");
118 QPushButton *appendSlice = new QPushButton("Append slice");
119 QPushButton *insertSlice = new QPushButton("Insert slice");
119 QPushButton *insertSlice = new QPushButton("Insert slice");
120 QPushButton *removeSlice = new QPushButton("Remove selected slice");
120 QPushButton *removeSlice = new QPushButton("Remove selected slice");
121
121
122 QFormLayout* seriesSettingsLayout = new QFormLayout();
122 QFormLayout* seriesSettingsLayout = new QFormLayout();
123 seriesSettingsLayout->addRow("Horizontal position", m_hPosition);
123 seriesSettingsLayout->addRow("Horizontal position", m_hPosition);
124 seriesSettingsLayout->addRow("Vertical position", m_vPosition);
124 seriesSettingsLayout->addRow("Vertical position", m_vPosition);
125 seriesSettingsLayout->addRow("Size factor", m_sizeFactor);
125 seriesSettingsLayout->addRow("Size factor", m_sizeFactor);
126 seriesSettingsLayout->addRow("Start angle", m_startAngle);
126 seriesSettingsLayout->addRow("Start angle", m_startAngle);
127 seriesSettingsLayout->addRow("End angle", m_endAngle);
127 seriesSettingsLayout->addRow("End angle", m_endAngle);
128 seriesSettingsLayout->addRow(appendSlice);
128 seriesSettingsLayout->addRow(appendSlice);
129 seriesSettingsLayout->addRow(insertSlice);
129 seriesSettingsLayout->addRow(insertSlice);
130 seriesSettingsLayout->addRow(removeSlice);
130 seriesSettingsLayout->addRow(removeSlice);
131 QGroupBox* seriesSettings = new QGroupBox("Series");
131 QGroupBox* seriesSettings = new QGroupBox("Series");
132 seriesSettings->setLayout(seriesSettingsLayout);
132 seriesSettings->setLayout(seriesSettingsLayout);
133
133
134 connect(m_vPosition, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
134 connect(m_vPosition, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
135 connect(m_hPosition, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
135 connect(m_hPosition, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
136 connect(m_sizeFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
136 connect(m_sizeFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
137 connect(m_startAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
137 connect(m_startAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
138 connect(m_endAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
138 connect(m_endAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
139 connect(appendSlice, SIGNAL(clicked()), this, SLOT(appendSlice()));
139 connect(appendSlice, SIGNAL(clicked()), this, SLOT(appendSlice()));
140 connect(insertSlice, SIGNAL(clicked()), this, SLOT(insertSlice()));
140 connect(insertSlice, SIGNAL(clicked()), this, SLOT(insertSlice()));
141 connect(removeSlice, SIGNAL(clicked()), this, SLOT(removeSlice()));
141 connect(removeSlice, SIGNAL(clicked()), this, SLOT(removeSlice()));
142
142
143 // slice settings
143 // slice settings
144 m_sliceName = new QLineEdit("<click a slice>");
144 m_sliceName = new QLineEdit("<click a slice>");
145 m_sliceName->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Maximum);
145 m_sliceName->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Maximum);
146 m_sliceValue = new QDoubleSpinBox();
146 m_sliceValue = new QDoubleSpinBox();
147 m_sliceValue->setMaximum(1000);
147 m_sliceValue->setMaximum(1000);
148 m_sliceLabelVisible = new QCheckBox();
148 m_sliceLabelVisible = new QCheckBox();
149 m_sliceLabelArmFactor = new QDoubleSpinBox();
149 m_sliceLabelArmFactor = new QDoubleSpinBox();
150 m_sliceLabelArmFactor->setSingleStep(0.01);
150 m_sliceLabelArmFactor->setSingleStep(0.01);
151 m_sliceExploded = new QCheckBox();
151 m_sliceExploded = new QCheckBox();
152 m_sliceExplodedFactor = new QDoubleSpinBox();
152 m_sliceExplodedFactor = new QDoubleSpinBox();
153 m_sliceExplodedFactor->setSingleStep(0.01);
153 m_sliceExplodedFactor->setSingleStep(0.01);
154 m_pen = new QPushButton();
154 m_pen = new QPushButton();
155 m_penTool = new PenTool("Slice pen", this);
155 m_penTool = new PenTool("Slice pen", this);
156 m_brush = new QPushButton();
156 m_brush = new QPushButton();
157 m_brushTool = new BrushTool("Slice brush", this);
157 m_brushTool = new BrushTool("Slice brush", this);
158 m_font = new QPushButton();
158 m_font = new QPushButton();
159 m_labelBrush = new QPushButton();
159 m_labelBrush = new QPushButton();
160 m_labelBrushTool = new BrushTool("Label brush", this);
160 m_labelBrushTool = new BrushTool("Label brush", this);
161 m_labelPosition = new QComboBox(this);
161 m_labelPosition = new QComboBox(this);
162 m_labelPosition->addItem("Outside", QPieSlice::LabelOutside);
162 m_labelPosition->addItem("Outside", QPieSlice::LabelOutside);
163 m_labelPosition->addItem("Inside", QPieSlice::LabelInside);
163 m_labelPosition->addItem("Inside", QPieSlice::LabelInside);
164 m_labelPosition->addItem("Inside tangential", QPieSlice::LabelInsideTangential);
165 m_labelPosition->addItem("Inside normal", QPieSlice::LabelInsideNormal);
164
166
165 QFormLayout* sliceSettingsLayout = new QFormLayout();
167 QFormLayout* sliceSettingsLayout = new QFormLayout();
166 sliceSettingsLayout->addRow("Label", m_sliceName);
168 sliceSettingsLayout->addRow("Label", m_sliceName);
167 sliceSettingsLayout->addRow("Value", m_sliceValue);
169 sliceSettingsLayout->addRow("Value", m_sliceValue);
168 sliceSettingsLayout->addRow("Pen", m_pen);
170 sliceSettingsLayout->addRow("Pen", m_pen);
169 sliceSettingsLayout->addRow("Brush", m_brush);
171 sliceSettingsLayout->addRow("Brush", m_brush);
170 sliceSettingsLayout->addRow("Label visible", m_sliceLabelVisible);
172 sliceSettingsLayout->addRow("Label visible", m_sliceLabelVisible);
171 sliceSettingsLayout->addRow("Label font", m_font);
173 sliceSettingsLayout->addRow("Label font", m_font);
172 sliceSettingsLayout->addRow("Label brush", m_labelBrush);
174 sliceSettingsLayout->addRow("Label brush", m_labelBrush);
173 sliceSettingsLayout->addRow("Label position", m_labelPosition);
175 sliceSettingsLayout->addRow("Label position", m_labelPosition);
174 sliceSettingsLayout->addRow("Label arm length", m_sliceLabelArmFactor);
176 sliceSettingsLayout->addRow("Label arm length", m_sliceLabelArmFactor);
175 sliceSettingsLayout->addRow("Exploded", m_sliceExploded);
177 sliceSettingsLayout->addRow("Exploded", m_sliceExploded);
176 sliceSettingsLayout->addRow("Explode distance", m_sliceExplodedFactor);
178 sliceSettingsLayout->addRow("Explode distance", m_sliceExplodedFactor);
177 QGroupBox* sliceSettings = new QGroupBox("Selected slice");
179 QGroupBox* sliceSettings = new QGroupBox("Selected slice");
178 sliceSettings->setLayout(sliceSettingsLayout);
180 sliceSettings->setLayout(sliceSettingsLayout);
179
181
180 connect(m_sliceName, SIGNAL(textChanged(QString)), this, SLOT(updateSliceSettings()));
182 connect(m_sliceName, SIGNAL(textChanged(QString)), this, SLOT(updateSliceSettings()));
181 connect(m_sliceValue, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
183 connect(m_sliceValue, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
182 connect(m_pen, SIGNAL(clicked()), m_penTool, SLOT(show()));
184 connect(m_pen, SIGNAL(clicked()), m_penTool, SLOT(show()));
183 connect(m_penTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
185 connect(m_penTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
184 connect(m_brush, SIGNAL(clicked()), m_brushTool, SLOT(show()));
186 connect(m_brush, SIGNAL(clicked()), m_brushTool, SLOT(show()));
185 connect(m_brushTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
187 connect(m_brushTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
186 connect(m_font, SIGNAL(clicked()), this, SLOT(showFontDialog()));
188 connect(m_font, SIGNAL(clicked()), this, SLOT(showFontDialog()));
187 connect(m_labelBrush, SIGNAL(clicked()), m_labelBrushTool, SLOT(show()));
189 connect(m_labelBrush, SIGNAL(clicked()), m_labelBrushTool, SLOT(show()));
188 connect(m_labelBrushTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
190 connect(m_labelBrushTool, SIGNAL(changed()), this, SLOT(updateSliceSettings()));
189 connect(m_sliceLabelVisible, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
191 connect(m_sliceLabelVisible, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
190 connect(m_sliceLabelVisible, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
192 connect(m_sliceLabelVisible, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
191 connect(m_sliceLabelArmFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
193 connect(m_sliceLabelArmFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
192 connect(m_sliceExploded, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
194 connect(m_sliceExploded, SIGNAL(toggled(bool)), this, SLOT(updateSliceSettings()));
193 connect(m_sliceExplodedFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
195 connect(m_sliceExplodedFactor, SIGNAL(valueChanged(double)), this, SLOT(updateSliceSettings()));
194 connect(m_labelPosition, SIGNAL(currentIndexChanged(int)), this, SLOT(updateSliceSettings()));
196 connect(m_labelPosition, SIGNAL(currentIndexChanged(int)), this, SLOT(updateSliceSettings()));
195
197
196 // create chart view
198 // create chart view
197 m_chartView = new QChartView(chart);
199 m_chartView = new QChartView(chart);
198
200
199 // create main layout
201 // create main layout
200 QVBoxLayout *settingsLayout = new QVBoxLayout();
202 QVBoxLayout *settingsLayout = new QVBoxLayout();
201 settingsLayout->addWidget(chartSettings);
203 settingsLayout->addWidget(chartSettings);
202 settingsLayout->addWidget(seriesSettings);
204 settingsLayout->addWidget(seriesSettings);
203 settingsLayout->addWidget(sliceSettings);
205 settingsLayout->addWidget(sliceSettings);
204 settingsLayout->addStretch();
206 settingsLayout->addStretch();
205
207
206 QGridLayout* baseLayout = new QGridLayout();
208 QGridLayout* baseLayout = new QGridLayout();
207 baseLayout->addLayout(settingsLayout, 0, 0);
209 baseLayout->addLayout(settingsLayout, 0, 0);
208 baseLayout->addWidget(m_chartView, 0, 1);
210 baseLayout->addWidget(m_chartView, 0, 1);
209 setLayout(baseLayout);
211 setLayout(baseLayout);
210
212
211 updateSerieSettings();
213 updateSerieSettings();
212 updateChartSettings();
214 updateChartSettings();
213 }
215 }
214
216
215
217
216 void MainWidget::updateChartSettings()
218 void MainWidget::updateChartSettings()
217 {
219 {
218 QChart::ChartTheme theme = (QChart::ChartTheme) m_themeComboBox->itemData(m_themeComboBox->currentIndex()).toInt();
220 QChart::ChartTheme theme = (QChart::ChartTheme) m_themeComboBox->itemData(m_themeComboBox->currentIndex()).toInt();
219 m_chartView->chart()->setTheme(theme);
221 m_chartView->chart()->setTheme(theme);
220 m_chartView->setRenderHint(QPainter::Antialiasing, m_aaCheckBox->isChecked());
222 m_chartView->setRenderHint(QPainter::Antialiasing, m_aaCheckBox->isChecked());
221
223
222 if (m_animationsCheckBox->checkState() == Qt::Checked)
224 if (m_animationsCheckBox->checkState() == Qt::Checked)
223 m_chartView->chart()->setAnimationOptions(QChart::AllAnimations);
225 m_chartView->chart()->setAnimationOptions(QChart::AllAnimations);
224 else
226 else
225 m_chartView->chart()->setAnimationOptions(QChart::NoAnimation);
227 m_chartView->chart()->setAnimationOptions(QChart::NoAnimation);
226
228
227 if (m_legendCheckBox->checkState() == Qt::Checked)
229 if (m_legendCheckBox->checkState() == Qt::Checked)
228 m_chartView->chart()->legend()->show();
230 m_chartView->chart()->legend()->show();
229 else
231 else
230 m_chartView->chart()->legend()->hide();
232 m_chartView->chart()->legend()->hide();
231 }
233 }
232
234
233 void MainWidget::updateSerieSettings()
235 void MainWidget::updateSerieSettings()
234 {
236 {
235 m_series->setHorizontalPosition(m_hPosition->value());
237 m_series->setHorizontalPosition(m_hPosition->value());
236 m_series->setVerticalPosition(m_vPosition->value());
238 m_series->setVerticalPosition(m_vPosition->value());
237 m_series->setPieSize(m_sizeFactor->value());
239 m_series->setPieSize(m_sizeFactor->value());
238 m_series->setPieStartAngle(m_startAngle->value());
240 m_series->setPieStartAngle(m_startAngle->value());
239 m_series->setPieEndAngle(m_endAngle->value());
241 m_series->setPieEndAngle(m_endAngle->value());
240 }
242 }
241
243
242 void MainWidget::updateSliceSettings()
244 void MainWidget::updateSliceSettings()
243 {
245 {
244 if (!m_slice)
246 if (!m_slice)
245 return;
247 return;
246
248
247 m_slice->setLabel(m_sliceName->text());
249 m_slice->setLabel(m_sliceName->text());
248
250
249 m_slice->setValue(m_sliceValue->value());
251 m_slice->setValue(m_sliceValue->value());
250
252
251 m_slice->setPen(m_penTool->pen());
253 m_slice->setPen(m_penTool->pen());
252 m_slice->setBrush(m_brushTool->brush());
254 m_slice->setBrush(m_brushTool->brush());
253
255
254 m_slice->setLabelBrush(m_labelBrushTool->brush());
256 m_slice->setLabelBrush(m_labelBrushTool->brush());
255 m_slice->setLabelVisible(m_sliceLabelVisible->isChecked());
257 m_slice->setLabelVisible(m_sliceLabelVisible->isChecked());
256 m_slice->setLabelArmLengthFactor(m_sliceLabelArmFactor->value());
258 m_slice->setLabelArmLengthFactor(m_sliceLabelArmFactor->value());
257 m_slice->setLabelPosition((QPieSlice::LabelPosition)m_labelPosition->currentIndex()); // assumes that index is in sync with the enum
259 m_slice->setLabelPosition((QPieSlice::LabelPosition)m_labelPosition->currentIndex()); // assumes that index is in sync with the enum
258
260
259 m_slice->setExploded(m_sliceExploded->isChecked());
261 m_slice->setExploded(m_sliceExploded->isChecked());
260 m_slice->setExplodeDistanceFactor(m_sliceExplodedFactor->value());
262 m_slice->setExplodeDistanceFactor(m_sliceExplodedFactor->value());
261 }
263 }
262
264
263 void MainWidget::handleSliceClicked(QPieSlice* slice)
265 void MainWidget::handleSliceClicked(QPieSlice* slice)
264 {
266 {
265 m_slice = static_cast<CustomSlice*>(slice);
267 m_slice = static_cast<CustomSlice*>(slice);
266
268
267 // name
269 // name
268 m_sliceName->blockSignals(true);
270 m_sliceName->blockSignals(true);
269 m_sliceName->setText(slice->label());
271 m_sliceName->setText(slice->label());
270 m_sliceName->blockSignals(false);
272 m_sliceName->blockSignals(false);
271
273
272 // value
274 // value
273 m_sliceValue->blockSignals(true);
275 m_sliceValue->blockSignals(true);
274 m_sliceValue->setValue(slice->value());
276 m_sliceValue->setValue(slice->value());
275 m_sliceValue->blockSignals(false);
277 m_sliceValue->blockSignals(false);
276
278
277 // pen
279 // pen
278 m_pen->setText(PenTool::name(m_slice->pen()));
280 m_pen->setText(PenTool::name(m_slice->pen()));
279 m_penTool->setPen(m_slice->pen());
281 m_penTool->setPen(m_slice->pen());
280
282
281 // brush
283 // brush
282 m_brush->setText(m_slice->originalBrush().color().name());
284 m_brush->setText(m_slice->originalBrush().color().name());
283 m_brushTool->setBrush(m_slice->originalBrush());
285 m_brushTool->setBrush(m_slice->originalBrush());
284
286
285 // label
287 // label
286 m_labelBrush->setText(BrushTool::name(m_slice->labelBrush()));
288 m_labelBrush->setText(BrushTool::name(m_slice->labelBrush()));
287 m_labelBrushTool->setBrush(m_slice->labelBrush());
289 m_labelBrushTool->setBrush(m_slice->labelBrush());
288 m_font->setText(slice->labelFont().toString());
290 m_font->setText(slice->labelFont().toString());
289 m_sliceLabelVisible->blockSignals(true);
291 m_sliceLabelVisible->blockSignals(true);
290 m_sliceLabelVisible->setChecked(slice->isLabelVisible());
292 m_sliceLabelVisible->setChecked(slice->isLabelVisible());
291 m_sliceLabelVisible->blockSignals(false);
293 m_sliceLabelVisible->blockSignals(false);
292 m_sliceLabelArmFactor->blockSignals(true);
294 m_sliceLabelArmFactor->blockSignals(true);
293 m_sliceLabelArmFactor->setValue(slice->labelArmLengthFactor());
295 m_sliceLabelArmFactor->setValue(slice->labelArmLengthFactor());
294 m_sliceLabelArmFactor->blockSignals(false);
296 m_sliceLabelArmFactor->blockSignals(false);
295 m_labelPosition->blockSignals(true);
297 m_labelPosition->blockSignals(true);
296 m_labelPosition->setCurrentIndex(slice->labelPosition()); // assumes that index is in sync with the enum
298 m_labelPosition->setCurrentIndex(slice->labelPosition()); // assumes that index is in sync with the enum
297 m_labelPosition->blockSignals(false);
299 m_labelPosition->blockSignals(false);
298
300
299 // exploded
301 // exploded
300 m_sliceExploded->blockSignals(true);
302 m_sliceExploded->blockSignals(true);
301 m_sliceExploded->setChecked(slice->isExploded());
303 m_sliceExploded->setChecked(slice->isExploded());
302 m_sliceExploded->blockSignals(false);
304 m_sliceExploded->blockSignals(false);
303 m_sliceExplodedFactor->blockSignals(true);
305 m_sliceExplodedFactor->blockSignals(true);
304 m_sliceExplodedFactor->setValue(slice->explodeDistanceFactor());
306 m_sliceExplodedFactor->setValue(slice->explodeDistanceFactor());
305 m_sliceExplodedFactor->blockSignals(false);
307 m_sliceExplodedFactor->blockSignals(false);
306 }
308 }
307
309
308 void MainWidget::showFontDialog()
310 void MainWidget::showFontDialog()
309 {
311 {
310 if (!m_slice)
312 if (!m_slice)
311 return;
313 return;
312
314
313 QFontDialog dialog(m_slice->labelFont());
315 QFontDialog dialog(m_slice->labelFont());
314 dialog.show();
316 dialog.show();
315 dialog.exec();
317 dialog.exec();
316
318
317 m_slice->setLabelFont(dialog.currentFont());
319 m_slice->setLabelFont(dialog.currentFont());
318 m_font->setText(dialog.currentFont().toString());
320 m_font->setText(dialog.currentFont().toString());
319 }
321 }
320
322
321 void MainWidget::appendSlice()
323 void MainWidget::appendSlice()
322 {
324 {
323 *m_series << new CustomSlice("Slice " + QString::number(m_series->count()+1), 10.0);
325 *m_series << new CustomSlice("Slice " + QString::number(m_series->count()+1), 10.0);
324 }
326 }
325
327
326 void MainWidget::insertSlice()
328 void MainWidget::insertSlice()
327 {
329 {
328 if (!m_slice)
330 if (!m_slice)
329 return;
331 return;
330
332
331 int i = m_series->slices().indexOf(m_slice);
333 int i = m_series->slices().indexOf(m_slice);
332
334
333 m_series->insert(i, new CustomSlice("Slice " + QString::number(m_series->count()+1), 10.0));
335 m_series->insert(i, new CustomSlice("Slice " + QString::number(m_series->count()+1), 10.0));
334 }
336 }
335
337
336 void MainWidget::removeSlice()
338 void MainWidget::removeSlice()
337 {
339 {
338 if (!m_slice)
340 if (!m_slice)
339 return;
341 return;
340
342
341 m_sliceName->setText("<click a slice>");
343 m_sliceName->setText("<click a slice>");
342
344
343 m_series->remove(m_slice);
345 m_series->remove(m_slice);
344 m_slice = 0;
346 m_slice = 0;
345 }
347 }
346
348
347 #include "moc_mainwidget.cpp"
349 #include "moc_mainwidget.cpp"
@@ -1,121 +1,121
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 <QApplication>
21 #include <QApplication>
22 #include <QMainWindow>
22 #include <QMainWindow>
23 #include <QChartView>
23 #include <QChartView>
24 #include <QLineSeries>
24 #include <QLineSeries>
25 #include <QIntervalsAxis>
25 #include <QIntervalsAxis>
26
26
27 QTCOMMERCIALCHART_USE_NAMESPACE
27 QTCOMMERCIALCHART_USE_NAMESPACE
28
28
29 int main(int argc, char *argv[])
29 int main(int argc, char *argv[])
30 {
30 {
31 QApplication a(argc, argv);
31 QApplication a(argc, argv);
32
32
33 //![1]
33 //![1]
34 QLineSeries* series = new QLineSeries();
34 QLineSeries* series = new QLineSeries();
35 *series << QPointF(0, 6) << QPointF(9, 4) << QPointF(15, 20) << QPointF(25, 12) << QPointF(39, 36);
35 *series << QPointF(0, 6) << QPointF(9, 4) << QPointF(15, 20) << QPointF(25, 12) << QPointF(29, 26);
36 QChart* chart = new QChart();
36 QChart* chart = new QChart();
37 chart->legend()->hide();
37 chart->legend()->hide();
38 chart->addSeries(series);
38 chart->addSeries(series);
39 //![1]
39 //![1]
40
40
41 //![2]
41 //![2]
42 // Customize series
42 // Customize series
43 QPen pen(QRgb(0xfdb157));
43 QPen pen(QRgb(0xfdb157));
44 pen.setWidth(5);
44 pen.setWidth(5);
45 series->setPen(pen);
45 series->setPen(pen);
46
46
47 // Customize chart title
47 // Customize chart title
48 QFont font;
48 QFont font;
49 font.setPixelSize(18);
49 font.setPixelSize(18);
50 chart->setTitleFont(font);
50 chart->setTitleFont(font);
51 chart->setTitleBrush(QBrush(Qt::white));
51 chart->setTitleBrush(QBrush(Qt::white));
52 chart->setTitle("Customchart example");
52 chart->setTitle("Customchart example");
53
53
54 // Customize chart background
54 // Customize chart background
55 QLinearGradient backgroundGradient;
55 QLinearGradient backgroundGradient;
56 backgroundGradient.setStart(QPointF(0,0));
56 backgroundGradient.setStart(QPointF(0,0));
57 backgroundGradient.setFinalStop(QPointF(0,1));
57 backgroundGradient.setFinalStop(QPointF(0,1));
58 backgroundGradient.setColorAt(0.0, QRgb(0xd2d0d1));
58 backgroundGradient.setColorAt(0.0, QRgb(0xd2d0d1));
59 backgroundGradient.setColorAt(1.0, QRgb(0x4c4547));
59 backgroundGradient.setColorAt(1.0, QRgb(0x4c4547));
60 backgroundGradient.setCoordinateMode(QGradient::ObjectBoundingMode);
60 backgroundGradient.setCoordinateMode(QGradient::ObjectBoundingMode);
61 chart->setBackgroundBrush(backgroundGradient);
61 chart->setBackgroundBrush(backgroundGradient);
62 //![2]
62 //![2]
63
63
64 //![3]
64 //![3]
65 QIntervalsAxis* axisX = new QIntervalsAxis();
65 QIntervalsAxis* axisX = new QIntervalsAxis();
66 QIntervalsAxis* axisY = new QIntervalsAxis();
66 QIntervalsAxis* axisY = new QIntervalsAxis();
67
67
68 // Customize axis label font
68 // Customize axis label font
69 QFont labelsFont;
69 QFont labelsFont;
70 labelsFont.setPixelSize(12);
70 labelsFont.setPixelSize(12);
71 axisX->setLabelsFont(labelsFont);
71 axisX->setLabelsFont(labelsFont);
72 axisY->setLabelsFont(labelsFont);
72 axisY->setLabelsFont(labelsFont);
73
73
74 // Customize axis colors
74 // Customize axis colors
75 QPen axisPen(QRgb(0xd18952));
75 QPen axisPen(QRgb(0xd18952));
76 axisPen.setWidth(2);
76 axisPen.setWidth(2);
77 axisX->setAxisPen(axisPen);
77 axisX->setAxisPen(axisPen);
78 axisY->setAxisPen(axisPen);
78 axisY->setAxisPen(axisPen);
79
79
80 // Customize axis label colors
80 // Customize axis label colors
81 QBrush axisBrush(Qt::white);
81 QBrush axisBrush(Qt::white);
82 axisX->setLabelsBrush(axisBrush);
82 axisX->setLabelsBrush(axisBrush);
83 axisY->setLabelsBrush(axisBrush);
83 axisY->setLabelsBrush(axisBrush);
84
84
85 // Customize grid lines and shades
85 // Customize grid lines and shades
86 axisX->setGridLineVisible(false);
86 axisX->setGridLineVisible(false);
87 axisY->setGridLineVisible(false);
87 axisY->setGridLineVisible(false);
88 axisY->setShadesPen(Qt::NoPen);
88 axisY->setShadesPen(Qt::NoPen);
89 axisY->setShadesBrush(QBrush(QRgb(0xa5a2a3)));
89 axisY->setShadesBrush(QBrush(QRgb(0xa5a2a3)));
90 axisY->setShadesVisible(true);
90 axisY->setShadesVisible(true);
91 //![3]
91 //![3]
92
92
93 //![4]
93 //![4]
94 axisX->append("low", 10);
94 axisX->append("low", 10);
95 axisX->append("optimal", 20);
95 axisX->append("optimal", 20);
96 axisX->append("high", 30);
96 axisX->append("high", 30);
97 axisX->setRange(0, 30);
97 axisX->setRange(0, 30);
98
98
99 axisY->append("slow", 10);
99 axisY->append("slow", 10);
100 axisY->append("med", 20);
100 axisY->append("med", 20);
101 axisY->append("fast", 30);
101 axisY->append("fast", 30);
102 axisY->setRange(0, 30);
102 axisY->setRange(0, 30);
103
103
104 chart->setAxisX(axisX, series);
104 chart->setAxisX(axisX, series);
105 chart->setAxisY(axisY, series);
105 chart->setAxisY(axisY, series);
106 //![4]
106 //![4]
107
107
108 //![5]
108 //![5]
109 QChartView* chartView = new QChartView(chart);
109 QChartView* chartView = new QChartView(chart);
110 chartView->setRenderHint(QPainter::Antialiasing);
110 chartView->setRenderHint(QPainter::Antialiasing);
111 //![5]
111 //![5]
112
112
113 //![6]
113 //![6]
114 QMainWindow window;
114 QMainWindow window;
115 window.setCentralWidget(chartView);
115 window.setCentralWidget(chartView);
116 window.resize(400, 300);
116 window.resize(400, 300);
117 window.show();
117 window.show();
118 //![6]
118 //![6]
119
119
120 return a.exec();
120 return a.exec();
121 }
121 }
@@ -1,95 +1,96
1 #include "widget.h"
1 #include "widget.h"
2 #include <QChartView>
2 #include <QChartView>
3 #include <QPieSeries>
3 #include <QPieSeries>
4 #include <QPieSlice>
4 #include <QPieSlice>
5 #include <QTime>
5 #include <QTime>
6 #include <QGridLayout>
6 #include <QGridLayout>
7 #include <QTimer>
7 #include <QTimer>
8
8
9 QTCOMMERCIALCHART_USE_NAMESPACE
9 QTCOMMERCIALCHART_USE_NAMESPACE
10
10
11 Widget::Widget(QWidget *parent)
11 Widget::Widget(QWidget *parent)
12 : QWidget(parent)
12 : QWidget(parent)
13 {
13 {
14 setMinimumSize(800, 600);
14 setMinimumSize(800, 600);
15 qsrand(QTime(0,0,0).secsTo(QTime::currentTime()));
15 qsrand(QTime(0,0,0).secsTo(QTime::currentTime()));
16
16
17 QChartView *chartView = new QChartView;
17 QChartView *chartView = new QChartView;
18 chartView->setRenderHint(QPainter::Antialiasing);
18 chartView->setRenderHint(QPainter::Antialiasing);
19
19
20 qreal minSize = 0.1;
20 qreal minSize = 0.1;
21 qreal maxSize = 0.9;
21 qreal maxSize = 0.9;
22 int donutsCount = 5;
22 int donutsCount = 5;
23 for (int i = 0; i < donutsCount; i++) {
23 for (int i = 0; i < donutsCount; i++) {
24 QPieSeries *donut = new QPieSeries;
24 QPieSeries *donut = new QPieSeries;
25 donut->setDonut();
25 donut->setDonut();
26 donut->setLabelsVisible();
26 donut->setLabelsVisible();
27 int sliceCount = 3 + qrand() % 3;
27 int sliceCount = 3 + qrand() % 3;
28 for (int j = 0; j < sliceCount; j++) {
28 for (int j = 0; j < sliceCount; j++) {
29 qreal value = 100 + qrand() % 100;
29 qreal value = 100 + qrand() % 100;
30 QPieSlice *slice = new QPieSlice(QString("%1").arg(value), value);
30 QPieSlice *slice = new QPieSlice(QString("%1").arg(value), value);
31 connect(slice, SIGNAL(hovered(bool)), this, SLOT(explodeSlice(bool)));
31 connect(slice, SIGNAL(hovered(bool)), this, SLOT(explodeSlice(bool)));
32 donut->append(slice);
32 donut->append(slice);
33 donut->slices().last()->setLabelVisible(true);
33 donut->slices().last()->setLabelVisible(true);
34 donut->slices().last()->setLabelColor(Qt::white);
34 donut->slices().last()->setLabelColor(Qt::white);
35 donut->setDonutInnerSize(minSize + i * (maxSize - minSize) / donutsCount);
35 donut->setDonutInnerSize(minSize + i * (maxSize - minSize) / donutsCount);
36 donut->setPieSize(minSize + (i + 1) * (maxSize - minSize) / donutsCount);
36 donut->setPieSize(minSize + (i + 1) * (maxSize - minSize) / donutsCount);
37 }
37 }
38 m_donuts.append(donut);
38 m_donuts.append(donut);
39 qreal phase = qrand() % 180;
39 qreal phase = qrand() % 180;
40 donut->setLabelsPosition(QPieSlice::LabelInsideTangential);
40 donut->setPieStartAngle(phase);
41 donut->setPieStartAngle(phase);
41 donut->setPieEndAngle(360 + phase);
42 donut->setPieEndAngle(360 + phase);
42 chartView->chart()->addSeries(donut);
43 chartView->chart()->addSeries(donut);
43 }
44 }
44
45
45 // create main layout
46 // create main layout
46 QGridLayout* mainLayout = new QGridLayout;
47 QGridLayout* mainLayout = new QGridLayout;
47 mainLayout->addWidget(chartView, 1, 1);
48 mainLayout->addWidget(chartView, 1, 1);
48 setLayout(mainLayout);
49 setLayout(mainLayout);
49
50
50 chartView->chart()->setAnimationOptions(QChart::AllAnimations);
51 chartView->chart()->setAnimationOptions(QChart::AllAnimations);
51
52
52 updateTimer = new QTimer(this);
53 updateTimer = new QTimer(this);
53 connect(updateTimer, SIGNAL(timeout()), this, SLOT(updateRotation()));
54 connect(updateTimer, SIGNAL(timeout()), this, SLOT(updateRotation()));
54 updateTimer->start(750);
55 updateTimer->start(1500);
55 }
56 }
56
57
57 Widget::~Widget()
58 Widget::~Widget()
58 {
59 {
59
60
60 }
61 }
61
62
62 void Widget::updateRotation()
63 void Widget::updateRotation()
63 {
64 {
64 // int tobeupdated = qrand() % m_donutsGroup.count();
65 // int tobeupdated = qrand() % m_donutsGroup.count();
65 for (int i = 0; i < m_donuts.count(); i++) {
66 for (int i = 0; i < m_donuts.count(); i++) {
66 QPieSeries *donut = m_donuts.at(i);
67 QPieSeries *donut = m_donuts.at(i);
67 qreal phaseShift = -50 + qrand() % 100;
68 qreal phaseShift = -50 + qrand() % 100;
68 donut->setPieStartAngle(donut->pieStartAngle() + phaseShift);
69 donut->setPieStartAngle(donut->pieStartAngle() + phaseShift);
69 donut->setPieEndAngle(donut->pieEndAngle() + phaseShift);
70 donut->setPieEndAngle(donut->pieEndAngle() + phaseShift);
70 }
71 }
71 }
72 }
72
73
73 void Widget::explodeSlice(bool exploded)
74 void Widget::explodeSlice(bool exploded)
74 {
75 {
75 QPieSlice *slice = qobject_cast<QPieSlice *>(sender());
76 QPieSlice *slice = qobject_cast<QPieSlice *>(sender());
76 if (exploded) {
77 if (exploded) {
77 updateTimer->stop();
78 updateTimer->stop();
78 qreal sliceStartAngle = slice->startAngle();
79 qreal sliceStartAngle = slice->startAngle();
79 qreal sliceEndAngle = slice->startAngle() + slice->angleSpan();
80 qreal sliceEndAngle = slice->startAngle() + slice->angleSpan();
80
81
81 QPieSeries *donut = slice->series();
82 QPieSeries *donut = slice->series();
82 qreal seriesIndex = m_donuts.indexOf(donut);
83 qreal seriesIndex = m_donuts.indexOf(donut);
83 for (int i = seriesIndex + 1; i < m_donuts.count(); i++) {
84 for (int i = seriesIndex + 1; i < m_donuts.count(); i++) {
84 m_donuts.at(i)->setPieStartAngle(sliceEndAngle);
85 m_donuts.at(i)->setPieStartAngle(sliceEndAngle);
85 m_donuts.at(i)->setPieEndAngle(360 + sliceStartAngle);
86 m_donuts.at(i)->setPieEndAngle(360 + sliceStartAngle);
86 }
87 }
87 } else {
88 } else {
88 for (int i = 0; i < m_donuts.count(); i++) {
89 for (int i = 0; i < m_donuts.count(); i++) {
89 m_donuts.at(i)->setPieStartAngle(0);
90 m_donuts.at(i)->setPieStartAngle(0);
90 m_donuts.at(i)->setPieEndAngle(360);
91 m_donuts.at(i)->setPieEndAngle(360);
91 }
92 }
92 updateTimer->start();
93 updateTimer->start();
93 }
94 }
94 slice->setExploded(exploded);
95 slice->setExploded(exploded);
95 }
96 }
@@ -1,120 +1,119
1 #include "widget.h"
1 #include "widget.h"
2 #include <QGridLayout>
2 #include <QGridLayout>
3
3
4 #include <QPieSlice>
4 #include <QPieSlice>
5 #include <QTime>
5 #include <QTime>
6 #include <QChartView>
6 #include <QChartView>
7 #include <QTimer>
7 #include <QTimer>
8
8
9 QTCOMMERCIALCHART_USE_NAMESPACE
9 QTCOMMERCIALCHART_USE_NAMESPACE
10
10
11 Widget::Widget(QWidget *parent)
11 Widget::Widget(QWidget *parent)
12 : QWidget(parent),
12 : QWidget(parent),
13 mainData(0)
13 mainData(0)
14 {
14 {
15 setMinimumSize(800, 600);
15 setMinimumSize(800, 600);
16 qsrand(QTime(0,0,0).secsTo(QTime::currentTime()));
16 qsrand(QTime(0,0,0).secsTo(QTime::currentTime()));
17
17
18 QChartView *chartView = new QChartView;
18 QChartView *chartView = new QChartView;
19 chartView->setRenderHint(QPainter::Antialiasing);
19 chartView->setRenderHint(QPainter::Antialiasing);
20 chartView->chart()->setAnimationOptions(QChart::AllAnimations);
20 chartView->chart()->setAnimationOptions(QChart::AllAnimations);
21
21
22 mainData = new QPieSeries;
22 mainData = new QPieSeries;
23 mainData->setPieSize(0.6);
23 for (int j = 0; j < 4; j++) {
24 for (int j = 0; j < 4; j++) {
24
25 // create new slice for the mainData
25 // create new slice for the mainData
26 QPieSlice *slice = new QPieSlice;
26 QPieSlice *slice = new QPieSlice;
27 slice->setLabelPosition(QPieSlice::LabelInside);
28 slice->setLabelColor(Qt::white);
27 slice->setLabelColor(Qt::white);
29 mainData->append(slice);
28 mainData->append(slice);
30
29
31 // create a new detailed data for the slice
30 // create a new detailed data for the slice
32 QPieSeries *donut = new QPieSeries;
31 QPieSeries *donut = new QPieSeries;
33 donut->setDonut();
32 donut->setDonut();
34 donut->setLabelsVisible();
35 donut->setDonutInnerSize(mainData->pieSize());
33 donut->setDonutInnerSize(mainData->pieSize());
36 donut->setPieSize(mainData->pieSize() + 0.2);
34 donut->setPieSize(mainData->pieSize() + 0.15);
37
35
38 // when mainData slice is redrawn make sure the detailed data slices are aligned with it
36 // when mainData slice is redrawn make sure the detailed data slices are aligned with it
39 connect(slice, SIGNAL(startAngleChanged()), this, SLOT(updatedStartAngle()));
37 connect(slice, SIGNAL(startAngleChanged()), this, SLOT(updatedStartAngle()));
40 connect(slice, SIGNAL(angleSpanChanged()), this, SLOT(updatedAngleSpan()));
38 connect(slice, SIGNAL(angleSpanChanged()), this, SLOT(updatedAngleSpan()));
41
39
42 // create the detailed data
40 // create the detailed data
43 for (int j = 0; j < 3; j++) {
41 for (int j = 0; j < 3; j++) {
44 qreal value = 10 + qrand() % 100;
42 qreal value = 10 + qrand() % 100;
45 QPieSlice *slice = new QPieSlice(QString("%1").arg(value), value);
43 QPieSlice *slice = new QPieSlice(QString("%1").arg(value), value);
46 donut->append(slice);
44 donut->append(slice);
47 donut->slices().last()->setLabelVisible(true);
48 donut->slices().last()->setLabelColor(Qt::white);
49 }
45 }
46 donut->setLabelsPosition(QPieSlice::LabelOutside);
47 donut->setLabelsVisible();
50 detailedData.append(donut);
48 detailedData.append(donut);
51
49
52 // update the value and label of mainData
50 // update the value and label of mainData
53 slice->setValue(donut->sum());
51 slice->setValue(donut->sum());
54 slice->setLabel(QString("%1").arg(donut->sum()));
52 slice->setLabel(QString("%1").arg(donut->sum()));
55 }
53 }
56
54
57 mainData->setLabelsVisible();
55 mainData->setLabelsVisible();
56 mainData->setLabelsPosition(QPieSlice::LabelInside);
58 chartView->chart()->addSeries(mainData);
57 chartView->chart()->addSeries(mainData);
59 for (int i = 0; i < detailedData.count(); i++)
58 for (int i = 0; i < detailedData.count(); i++)
60 chartView->chart()->addSeries(detailedData.at(i));
59 chartView->chart()->addSeries(detailedData.at(i));
61
60
62 // create main layout
61 // create main layout
63 QGridLayout* mainLayout = new QGridLayout;
62 QGridLayout* mainLayout = new QGridLayout;
64 mainLayout->addWidget(chartView, 1, 1);
63 mainLayout->addWidget(chartView, 1, 1);
65 setLayout(mainLayout);
64 setLayout(mainLayout);
66
65
67 // modify the value of one detailed slice every 2.5 sec
66 // modify the value of one detailed slice every 2.5 sec
68 QTimer *updateTimer = new QTimer(this);
67 QTimer *updateTimer = new QTimer(this);
69 connect(updateTimer, SIGNAL(timeout()), this, SLOT(highlight()));
68 connect(updateTimer, SIGNAL(timeout()), this, SLOT(highlight()));
70 updateTimer->start(2500);
69 updateTimer->start(2500);
71 }
70 }
72
71
73 Widget::~Widget()
72 Widget::~Widget()
74 {
73 {
75
74
76 }
75 }
77
76
78 void Widget::updatedStartAngle()
77 void Widget::updatedStartAngle()
79 {
78 {
80 // when the mainData slice has been updated the detailed data QPieSeries object as well
79 // when the mainData slice has been updated the detailed data QPieSeries object as well
81 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
80 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
82 QPieSeries *detailsDonut = detailedData.at(slice->series()->slices().indexOf(slice));
81 QPieSeries *detailsDonut = detailedData.at(slice->series()->slices().indexOf(slice));
83 detailsDonut->setPieStartAngle(slice->startAngle());
82 detailsDonut->setPieStartAngle(slice->startAngle());
84 }
83 }
85
84
86 void Widget::updatedAngleSpan()
85 void Widget::updatedAngleSpan()
87 {
86 {
88 // when the mainData slice has been updated the detailed data QPieSeries object as well
87 // when the mainData slice has been updated the detailed data QPieSeries object as well
89 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
88 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
90 QPieSeries *detailsDonut = detailedData.at(slice->series()->slices().indexOf(slice));
89 QPieSeries *detailsDonut = detailedData.at(slice->series()->slices().indexOf(slice));
91 detailsDonut->setPieEndAngle(slice->startAngle() + slice->angleSpan());
90 detailsDonut->setPieEndAngle(slice->startAngle() + slice->angleSpan());
92 }
91 }
93
92
94 void Widget::updateRotation()
93 void Widget::updateRotation()
95 {
94 {
96 // update the selected slice
95 // update the selected slice
97 qreal newValue = 10 + qrand() % 100;
96 qreal newValue = 10 + qrand() % 100;
98 detailedData.at(detailIndex)->slices().at(sliceIndex)->setValue(newValue);
97 detailedData.at(detailIndex)->slices().at(sliceIndex)->setValue(newValue);
99 detailedData.at(detailIndex)->slices().at(sliceIndex)->setLabel(QString("%1").arg(newValue));
98 detailedData.at(detailIndex)->slices().at(sliceIndex)->setLabel(QString("%1").arg(newValue));
100
99
101 // update the mainData slice with a new sum of the detailed data values
100 // update the mainData slice with a new sum of the detailed data values
102 mainData->slices().at(detailIndex)->setValue(detailedData.at(detailIndex)->sum());
101 mainData->slices().at(detailIndex)->setValue(detailedData.at(detailIndex)->sum());
103 mainData->slices().at(detailIndex)->setLabel(QString("%1").arg(detailedData.at(detailIndex)->sum()));
102 mainData->slices().at(detailIndex)->setLabel(QString("%1").arg(detailedData.at(detailIndex)->sum()));
104
103
105 // change the explode state of the selected slice back to normal
104 // change the explode state of the selected slice back to normal
106 detailedData.at(detailIndex)->slices().at(sliceIndex)->setExploded(false);
105 detailedData.at(detailIndex)->slices().at(sliceIndex)->setExploded(false);
107 }
106 }
108
107
109 void Widget::highlight()
108 void Widget::highlight()
110 {
109 {
111 // choose one random detailed data slice to be updated.
110 // choose one random detailed data slice to be updated.
112 detailIndex = qrand() % mainData->count();
111 detailIndex = qrand() % mainData->count();
113 sliceIndex = qrand() % detailedData.at(detailIndex)->count();
112 sliceIndex = qrand() % detailedData.at(detailIndex)->count();
114
113
115 // set the slice to exploded to make the change easier to observe
114 // set the slice to exploded to make the change easier to observe
116 detailedData.at(detailIndex)->slices().at(sliceIndex)->setExploded();
115 detailedData.at(detailIndex)->slices().at(sliceIndex)->setExploded();
117
116
118 // give the user time to focus on the slice that will be changed
117 // give the user time to focus on the slice that will be changed
119 QTimer::singleShot(1000, this, SLOT(updateRotation()));
118 QTimer::singleShot(1000, this, SLOT(updateRotation()));
120 }
119 }
@@ -1,250 +1,274
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 "piesliceitem_p.h"
21 #include "piesliceitem_p.h"
22 #include "piechartitem_p.h"
22 #include "piechartitem_p.h"
23 #include "qpieseries.h"
23 #include "qpieseries.h"
24 #include "qpieslice.h"
24 #include "qpieslice.h"
25 #include "chartpresenter_p.h"
25 #include "chartpresenter_p.h"
26 #include <QPainter>
26 #include <QPainter>
27 #include <qmath.h>
27 #include <qmath.h>
28 #include <QGraphicsSceneEvent>
28 #include <QGraphicsSceneEvent>
29 #include <QTime>
29 #include <QTime>
30 #include <QDebug>
30 #include <QDebug>
31
31
32 QTCOMMERCIALCHART_BEGIN_NAMESPACE
32 QTCOMMERCIALCHART_BEGIN_NAMESPACE
33
33
34 QPointF offset(qreal angle, qreal length)
34 QPointF offset(qreal angle, qreal length)
35 {
35 {
36 qreal dx = qSin(angle*(M_PI/180)) * length;
36 qreal dx = qSin(angle*(M_PI/180)) * length;
37 qreal dy = qCos(angle*(M_PI/180)) * length;
37 qreal dy = qCos(angle*(M_PI/180)) * length;
38 return QPointF(dx, -dy);
38 return QPointF(dx, -dy);
39 }
39 }
40
40
41 PieSliceItem::PieSliceItem(QGraphicsItem* parent)
41 PieSliceItem::PieSliceItem(QGraphicsItem* parent)
42 :QGraphicsObject(parent),
42 :QGraphicsObject(parent),
43 m_hovered(false)
43 m_hovered(false)
44 {
44 {
45 setAcceptHoverEvents(true);
45 setAcceptHoverEvents(true);
46 setAcceptedMouseButtons(Qt::MouseButtonMask);
46 setAcceptedMouseButtons(Qt::MouseButtonMask);
47 setZValue(ChartPresenter::PieSeriesZValue);
47 setZValue(ChartPresenter::PieSeriesZValue);
48 }
48 }
49
49
50 PieSliceItem::~PieSliceItem()
50 PieSliceItem::~PieSliceItem()
51 {
51 {
52 // If user is hovering over the slice and it gets destroyed we do
52 // If user is hovering over the slice and it gets destroyed we do
53 // not get a hover leave event. So we must emit the signal here.
53 // not get a hover leave event. So we must emit the signal here.
54 if (m_hovered)
54 if (m_hovered)
55 emit hovered(false);
55 emit hovered(false);
56 }
56 }
57
57
58 QRectF PieSliceItem::boundingRect() const
58 QRectF PieSliceItem::boundingRect() const
59 {
59 {
60 return m_boundingRect;
60 return m_boundingRect;
61 }
61 }
62
62
63 QPainterPath PieSliceItem::shape() const
63 QPainterPath PieSliceItem::shape() const
64 {
64 {
65 // Don't include the label and label arm.
65 // Don't include the label and label arm.
66 // This is used to detect a mouse clicks. We do not want clicks from label.
66 // This is used to detect a mouse clicks. We do not want clicks from label.
67 return m_slicePath;
67 return m_slicePath;
68 }
68 }
69
69
70 void PieSliceItem::paint(QPainter* painter, const QStyleOptionGraphicsItem* /*option*/, QWidget* /*widget*/)
70 void PieSliceItem::paint(QPainter* painter, const QStyleOptionGraphicsItem* /*option*/, QWidget* /*widget*/)
71 {
71 {
72 painter->save();
72 painter->save();
73 painter->setClipRect(parentItem()->boundingRect());
73 painter->setClipRect(parentItem()->boundingRect());
74 painter->setPen(m_data.m_slicePen);
74 painter->setPen(m_data.m_slicePen);
75 painter->setBrush(m_data.m_sliceBrush);
75 painter->setBrush(m_data.m_sliceBrush);
76 painter->drawPath(m_slicePath);
76 painter->drawPath(m_slicePath);
77 painter->restore();
77 painter->restore();
78
78
79 if (m_data.m_isLabelVisible) {
79 if (m_data.m_isLabelVisible) {
80 painter->save();
80 painter->save();
81
81
82 // Pen for label arm not defined in the QPieSeries api, let's use brush's color instead
82 // Pen for label arm not defined in the QPieSeries api, let's use brush's color instead
83 // Also, the drawText actually uses the pen color for the text color (unlike QGraphicsSimpleTextItem)
83 // Also, the drawText actually uses the pen color for the text color (unlike QGraphicsSimpleTextItem)
84 painter->setPen(m_data.m_labelBrush.color());
84 painter->setPen(m_data.m_labelBrush.color());
85 painter->setBrush(m_data.m_labelBrush);
85 painter->setBrush(m_data.m_labelBrush);
86 painter->setFont(m_data.m_labelFont);
86 painter->setFont(m_data.m_labelFont);
87 if (m_data.m_donut) {
87
88 painter->translate(m_labelTextRect.center());
88 switch (m_data.m_labelPosition)
89 painter->rotate(m_data.m_startAngle + m_data.m_angleSpan / 2);
89 {
90 painter->drawText(-m_labelTextRect.width() / 2, -m_labelTextRect.height() / 2, m_labelTextRect.width(), m_labelTextRect.height(), Qt::AlignCenter, m_data.m_labelText);
90 case QPieSlice::LabelOutside:
91 } else if (m_data.m_labelPosition == QPieSlice::LabelOutside) {
92 painter->setClipRect(parentItem()->boundingRect());
91 painter->setClipRect(parentItem()->boundingRect());
93 painter->strokePath(m_labelArmPath, m_data.m_labelBrush.color());
92 painter->strokePath(m_labelArmPath, m_data.m_labelBrush.color());
94 painter->drawText(m_labelTextRect, Qt::AlignCenter, m_data.m_labelText);
93 painter->drawText(m_labelTextRect, Qt::AlignCenter, m_data.m_labelText);
95 } else { // QPieSlice::LabelInside
94 break;
95 case QPieSlice::LabelInside:
96 painter->setClipPath(m_slicePath);
96 painter->setClipPath(m_slicePath);
97 painter->drawText(m_labelTextRect, Qt::AlignCenter, m_data.m_labelText);
97 painter->drawText(m_labelTextRect, Qt::AlignCenter, m_data.m_labelText);
98 break;
99 case QPieSlice::LabelInsideTangential:
100 painter->setClipPath(m_slicePath);
101 painter->translate(m_labelTextRect.center());
102 painter->rotate(m_data.m_startAngle + m_data.m_angleSpan / 2);
103 painter->drawText(-m_labelTextRect.width() / 2, -m_labelTextRect.height() / 2, m_labelTextRect.width(), m_labelTextRect.height(), Qt::AlignCenter, m_data.m_labelText);
104 break;
105 case QPieSlice::LabelInsideNormal:
106 painter->setClipPath(m_slicePath);
107 painter->translate(m_labelTextRect.center());
108 if (m_data.m_startAngle + m_data.m_angleSpan / 2 < 180)
109 painter->rotate(m_data.m_startAngle + m_data.m_angleSpan / 2 - 90);
110 else
111 painter->rotate(m_data.m_startAngle + m_data.m_angleSpan / 2 + 90);
112 painter->drawText(-m_labelTextRect.width() / 2, -m_labelTextRect.height() / 2, m_labelTextRect.width(), m_labelTextRect.height(), Qt::AlignCenter, m_data.m_labelText);
113 break;
98 }
114 }
99
115
100 painter->restore();
116 painter->restore();
101 }
117 }
102 }
118 }
103
119
104 void PieSliceItem::hoverEnterEvent(QGraphicsSceneHoverEvent* /*event*/)
120 void PieSliceItem::hoverEnterEvent(QGraphicsSceneHoverEvent* /*event*/)
105 {
121 {
106 m_hovered = true;
122 m_hovered = true;
107 emit hovered(true);
123 emit hovered(true);
108 }
124 }
109
125
110 void PieSliceItem::hoverLeaveEvent(QGraphicsSceneHoverEvent* /*event*/)
126 void PieSliceItem::hoverLeaveEvent(QGraphicsSceneHoverEvent* /*event*/)
111 {
127 {
112 m_hovered = false;
128 m_hovered = false;
113 emit hovered(false);
129 emit hovered(false);
114 }
130 }
115
131
116 void PieSliceItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
132 void PieSliceItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
117 {
133 {
118 emit clicked(event->buttons());
134 emit clicked(event->buttons());
119 }
135 }
120
136
121 void PieSliceItem::setLayout(const PieSliceData &sliceData)
137 void PieSliceItem::setLayout(const PieSliceData &sliceData)
122 {
138 {
123 m_data = sliceData;
139 m_data = sliceData;
124 updateGeometry();
140 updateGeometry();
125 update();
141 update();
126 }
142 }
127
143
128 void PieSliceItem::updateGeometry()
144 void PieSliceItem::updateGeometry()
129 {
145 {
130 if (m_data.m_radius <= 0)
146 if (m_data.m_radius <= 0)
131 return;
147 return;
132
148
133 prepareGeometryChange();
149 prepareGeometryChange();
134
150
135 // slice path
151 // slice path
136 qreal centerAngle;
152 qreal centerAngle;
137 QPointF armStart;
153 QPointF armStart;
138 m_slicePath = slicePath(m_data.m_center, m_data.m_radius, m_data.m_startAngle, m_data.m_angleSpan, &centerAngle, &armStart);
154 m_slicePath = slicePath(m_data.m_center, m_data.m_radius, m_data.m_startAngle, m_data.m_angleSpan, &centerAngle, &armStart);
139
155
140 // text rect
156 // text rect
141 QFontMetricsF fm(m_data.m_labelFont);
157 QFontMetricsF fm(m_data.m_labelFont);
142 m_labelTextRect = QRectF(0, 0, fm.width(m_data.m_labelText), fm.height());
158 m_labelTextRect = QRectF(0, 0, fm.width(m_data.m_labelText), fm.height());
143
159
144 // label arm path
160 // label arm path
145 QPointF labelTextStart;
161 QPointF labelTextStart;
146 m_labelArmPath = labelArmPath(armStart, centerAngle, m_data.m_radius * m_data.m_labelArmLengthFactor, m_labelTextRect.width(), &labelTextStart);
162 m_labelArmPath = labelArmPath(armStart, centerAngle, m_data.m_radius * m_data.m_labelArmLengthFactor, m_labelTextRect.width(), &labelTextStart);
147
163
148 // text position
164 // text position
149 if (m_data.m_donut) {
165 switch (m_data.m_labelPosition)
150 QPointF donutCenter = m_data.m_center + offset(centerAngle, m_data.m_innerRadius + (m_data.m_radius - m_data.m_innerRadius) / 2);
166 {
151 m_labelTextRect.moveCenter(donutCenter);
167 case QPieSlice::LabelOutside:
152 } else if (m_data.m_labelPosition == QPieSlice::LabelOutside) {
153 m_labelTextRect.moveBottomLeft(labelTextStart);
168 m_labelTextRect.moveBottomLeft(labelTextStart);
154 } else {// QPieSlice::LabelInside
169 break;
155 QPointF sliceCenter = m_data.m_center + offset(centerAngle, m_data.m_radius / 2);
170 case QPieSlice::LabelInside:
156 m_labelTextRect.moveCenter(sliceCenter);
171 case QPieSlice::LabelInsideTangential:
172 case QPieSlice::LabelInsideNormal:{
173 QPointF textCenter;
174 if (m_data.m_donut)
175 textCenter = m_data.m_center + offset(centerAngle, m_data.m_innerRadius + (m_data.m_radius - m_data.m_innerRadius) / 2);
176 else
177 textCenter = m_data.m_center + offset(centerAngle, m_data.m_radius / 2);
178 m_labelTextRect.moveCenter(textCenter);
179 break;
180 }
157 }
181 }
158
182
159 // bounding rect
183 // bounding rect
160 if (m_data.m_isLabelVisible)
184 if (m_data.m_isLabelVisible)
161 m_boundingRect = m_slicePath.boundingRect().united(m_labelArmPath.boundingRect()).united(m_labelTextRect);
185 m_boundingRect = m_slicePath.boundingRect().united(m_labelArmPath.boundingRect()).united(m_labelTextRect);
162 else
186 else
163 m_boundingRect = m_slicePath.boundingRect();
187 m_boundingRect = m_slicePath.boundingRect();
164 }
188 }
165
189
166 QPointF PieSliceItem::sliceCenter(QPointF point, qreal radius, QPieSlice *slice)
190 QPointF PieSliceItem::sliceCenter(QPointF point, qreal radius, QPieSlice *slice)
167 {
191 {
168 if (slice->isExploded()) {
192 if (slice->isExploded()) {
169 qreal centerAngle = slice->startAngle() + (slice->angleSpan()/2);
193 qreal centerAngle = slice->startAngle() + (slice->angleSpan()/2);
170 qreal len = radius * slice->explodeDistanceFactor();
194 qreal len = radius * slice->explodeDistanceFactor();
171 point += offset(centerAngle, len);
195 point += offset(centerAngle, len);
172 }
196 }
173 return point;
197 return point;
174 }
198 }
175
199
176 QPainterPath PieSliceItem::slicePath(QPointF center, qreal radius, qreal startAngle, qreal angleSpan, qreal *centerAngle, QPointF* armStart)
200 QPainterPath PieSliceItem::slicePath(QPointF center, qreal radius, qreal startAngle, qreal angleSpan, qreal *centerAngle, QPointF* armStart)
177 {
201 {
178 // calculate center angle
202 // calculate center angle
179 *centerAngle = startAngle + (angleSpan/2);
203 *centerAngle = startAngle + (angleSpan/2);
180
204
181 // calculate slice rectangle
205 // calculate slice rectangle
182 QRectF rect(center.x()-radius, center.y()-radius, radius*2, radius*2);
206 QRectF rect(center.x()-radius, center.y()-radius, radius*2, radius*2);
183
207
184 // slice path
208 // slice path
185 QPainterPath path;
209 QPainterPath path;
186 if (m_data.m_donut) {
210 if (m_data.m_donut) {
187 QRectF insideRect(center.x() - m_data.m_innerRadius, center.y()-m_data.m_innerRadius, m_data.m_innerRadius*2, m_data.m_innerRadius*2);
211 QRectF insideRect(center.x() - m_data.m_innerRadius, center.y()-m_data.m_innerRadius, m_data.m_innerRadius*2, m_data.m_innerRadius*2);
188 path.arcMoveTo(rect, -startAngle + 90);
212 path.arcMoveTo(rect, -startAngle + 90);
189 path.arcTo(rect, -startAngle + 90, -angleSpan);
213 path.arcTo(rect, -startAngle + 90, -angleSpan);
190 path.arcTo(insideRect, -startAngle + 90 - angleSpan, angleSpan);
214 path.arcTo(insideRect, -startAngle + 90 - angleSpan, angleSpan);
191 path.closeSubpath();
215 path.closeSubpath();
192 } else {
216 } else {
193 path.moveTo(rect.center());
217 path.moveTo(rect.center());
194 path.arcTo(rect, -startAngle + 90, -angleSpan);
218 path.arcTo(rect, -startAngle + 90, -angleSpan);
195 path.closeSubpath();
219 path.closeSubpath();
196 }
220 }
197
221
198 // calculate label arm start point
222 // calculate label arm start point
199 *armStart = center;
223 *armStart = center;
200 *armStart += offset(*centerAngle, radius + PIESLICE_LABEL_GAP);
224 *armStart += offset(*centerAngle, radius + PIESLICE_LABEL_GAP);
201
225
202 return path;
226 return path;
203 }
227 }
204
228
205 QPainterPath PieSliceItem::labelArmPath(QPointF start, qreal angle, qreal length, qreal textWidth, QPointF *textStart)
229 QPainterPath PieSliceItem::labelArmPath(QPointF start, qreal angle, qreal length, qreal textWidth, QPointF *textStart)
206 {
230 {
207 // Normalize the angle to 0-360 range
231 // Normalize the angle to 0-360 range
208 // NOTE: We are using int here on purpose. Depenging on platform and hardware
232 // NOTE: We are using int here on purpose. Depenging on platform and hardware
209 // qreal can be a double, float or something the user gives to the Qt configure
233 // qreal can be a double, float or something the user gives to the Qt configure
210 // (QT_COORD_TYPE). Compilers do not seem to support modulo for double or float
234 // (QT_COORD_TYPE). Compilers do not seem to support modulo for double or float
211 // but there are fmod() and fmodf() functions for that. So instead of some #ifdef
235 // but there are fmod() and fmodf() functions for that. So instead of some #ifdef
212 // that might break we just use int. Precision for this is just fine for our needs.
236 // that might break we just use int. Precision for this is just fine for our needs.
213 int normalized = angle * 10.0;
237 int normalized = angle * 10.0;
214 normalized = normalized % 3600;
238 normalized = normalized % 3600;
215 if (normalized < 0)
239 if (normalized < 0)
216 normalized += 3600;
240 normalized += 3600;
217 angle = (qreal) normalized / 10.0;
241 angle = (qreal) normalized / 10.0;
218
242
219 // prevent label arm pointing straight down because it will look bad
243 // prevent label arm pointing straight down because it will look bad
220 if (angle < 180 && angle > 170)
244 if (angle < 180 && angle > 170)
221 angle = 170;
245 angle = 170;
222 if (angle > 180 && angle < 190)
246 if (angle > 180 && angle < 190)
223 angle = 190;
247 angle = 190;
224
248
225 // line from slice to label
249 // line from slice to label
226 QPointF parm1 = start + offset(angle, length);
250 QPointF parm1 = start + offset(angle, length);
227
251
228 // line to underline the label
252 // line to underline the label
229 QPointF parm2 = parm1;
253 QPointF parm2 = parm1;
230 if (angle < 180) { // arm swings the other way on the left side
254 if (angle < 180) { // arm swings the other way on the left side
231 parm2 += QPointF(textWidth, 0);
255 parm2 += QPointF(textWidth, 0);
232 *textStart = parm1;
256 *textStart = parm1;
233 }
257 }
234 else {
258 else {
235 parm2 += QPointF(-textWidth,0);
259 parm2 += QPointF(-textWidth,0);
236 *textStart = parm2;
260 *textStart = parm2;
237 }
261 }
238
262
239 QPainterPath path;
263 QPainterPath path;
240 path.moveTo(start);
264 path.moveTo(start);
241 path.lineTo(parm1);
265 path.lineTo(parm1);
242 path.lineTo(parm2);
266 path.lineTo(parm2);
243
267
244 return path;
268 return path;
245 }
269 }
246
270
247 #include "moc_piesliceitem_p.cpp"
271 #include "moc_piesliceitem_p.cpp"
248
272
249 QTCOMMERCIALCHART_END_NAMESPACE
273 QTCOMMERCIALCHART_END_NAMESPACE
250
274
@@ -1,807 +1,814
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 "qpieseries.h"
21 #include "qpieseries.h"
22 #include "qpieseries_p.h"
22 #include "qpieseries_p.h"
23 #include "qpieslice.h"
23 #include "qpieslice.h"
24 #include "qpieslice_p.h"
24 #include "qpieslice_p.h"
25 #include "pieslicedata_p.h"
25 #include "pieslicedata_p.h"
26 #include "chartdataset_p.h"
26 #include "chartdataset_p.h"
27 #include "charttheme_p.h"
27 #include "charttheme_p.h"
28 #include "chartanimator_p.h"
28 #include "chartanimator_p.h"
29 #include "legendmarker_p.h"
29 #include "legendmarker_p.h"
30 #include "qabstractaxis.h"
30 #include "qabstractaxis.h"
31
31
32 QTCOMMERCIALCHART_BEGIN_NAMESPACE
32 QTCOMMERCIALCHART_BEGIN_NAMESPACE
33
33
34 /*!
34 /*!
35 \class QPieSeries
35 \class QPieSeries
36 \brief Pie series API for QtCommercial Charts
36 \brief Pie series API for QtCommercial Charts
37
37
38 The pie series defines a pie chart which consists of pie slices which are defined as QPieSlice objects.
38 The pie series defines a pie chart which consists of pie slices which are defined as QPieSlice objects.
39 The slices can have any values as the QPieSeries will calculate its relative value to the sum of all slices.
39 The slices can have any values as the QPieSeries will calculate its relative value to the sum of all slices.
40 The actual slice size is determined by that relative value.
40 The actual slice size is determined by that relative value.
41
41
42 Pie size and position on the chart is controlled by using relative values which range from 0.0 to 1.0
42 Pie size and position on the chart is controlled by using relative values which range from 0.0 to 1.0
43 These relate to the actual chart rectangle.
43 These relate to the actual chart rectangle.
44
44
45 By default the pie is defined as a full pie but it can also be a partial pie.
45 By default the pie is defined as a full pie but it can also be a partial pie.
46 This can be done by setting a starting angle and angle span to the series.
46 This can be done by setting a starting angle and angle span to the series.
47 Full pie is 360 degrees where 0 is at 12 a'clock.
47 Full pie is 360 degrees where 0 is at 12 a'clock.
48
48
49 See the \l {PieChart Example} {pie chart example} to learn how to create a simple pie chart.
49 See the \l {PieChart Example} {pie chart example} to learn how to create a simple pie chart.
50 \image examples_piechart.png
50 \image examples_piechart.png
51 */
51 */
52 /*!
52 /*!
53 \qmlclass PieSeries QPieSeries
53 \qmlclass PieSeries QPieSeries
54 \inherits AbstractSeries
54 \inherits AbstractSeries
55
55
56 The following QML shows how to create a simple pie chart.
56 The following QML shows how to create a simple pie chart.
57
57
58 \snippet ../demos/qmlchart/qml/qmlchart/View1.qml 1
58 \snippet ../demos/qmlchart/qml/qmlchart/View1.qml 1
59
59
60 \beginfloatleft
60 \beginfloatleft
61 \image demos_qmlchart1.png
61 \image demos_qmlchart1.png
62 \endfloat
62 \endfloat
63 \clearfloat
63 \clearfloat
64 */
64 */
65
65
66 /*!
66 /*!
67 \property QPieSeries::horizontalPosition
67 \property QPieSeries::horizontalPosition
68 \brief Defines the horizontal position of the pie.
68 \brief Defines the horizontal position of the pie.
69
69
70 The value is a relative value to the chart rectangle where:
70 The value is a relative value to the chart rectangle where:
71
71
72 \list
72 \list
73 \o 0.0 is the absolute left.
73 \o 0.0 is the absolute left.
74 \o 1.0 is the absolute right.
74 \o 1.0 is the absolute right.
75 \endlist
75 \endlist
76 Default value is 0.5 (center).
76 Default value is 0.5 (center).
77 \sa verticalPosition
77 \sa verticalPosition
78 */
78 */
79
79
80 /*!
80 /*!
81 \qmlproperty real PieSeries::horizontalPosition
81 \qmlproperty real PieSeries::horizontalPosition
82
82
83 Defines the horizontal position of the pie.
83 Defines the horizontal position of the pie.
84
84
85 The value is a relative value to the chart rectangle where:
85 The value is a relative value to the chart rectangle where:
86
86
87 \list
87 \list
88 \o 0.0 is the absolute left.
88 \o 0.0 is the absolute left.
89 \o 1.0 is the absolute right.
89 \o 1.0 is the absolute right.
90 \endlist
90 \endlist
91 Default value is 0.5 (center).
91 Default value is 0.5 (center).
92 \sa verticalPosition
92 \sa verticalPosition
93 */
93 */
94
94
95 /*!
95 /*!
96 \property QPieSeries::verticalPosition
96 \property QPieSeries::verticalPosition
97 \brief Defines the vertical position of the pie.
97 \brief Defines the vertical position of the pie.
98
98
99 The value is a relative value to the chart rectangle where:
99 The value is a relative value to the chart rectangle where:
100
100
101 \list
101 \list
102 \o 0.0 is the absolute top.
102 \o 0.0 is the absolute top.
103 \o 1.0 is the absolute bottom.
103 \o 1.0 is the absolute bottom.
104 \endlist
104 \endlist
105 Default value is 0.5 (center).
105 Default value is 0.5 (center).
106 \sa horizontalPosition
106 \sa horizontalPosition
107 */
107 */
108
108
109 /*!
109 /*!
110 \qmlproperty real PieSeries::verticalPosition
110 \qmlproperty real PieSeries::verticalPosition
111
111
112 Defines the vertical position of the pie.
112 Defines the vertical position of the pie.
113
113
114 The value is a relative value to the chart rectangle where:
114 The value is a relative value to the chart rectangle where:
115
115
116 \list
116 \list
117 \o 0.0 is the absolute top.
117 \o 0.0 is the absolute top.
118 \o 1.0 is the absolute bottom.
118 \o 1.0 is the absolute bottom.
119 \endlist
119 \endlist
120 Default value is 0.5 (center).
120 Default value is 0.5 (center).
121 \sa horizontalPosition
121 \sa horizontalPosition
122 */
122 */
123
123
124 /*!
124 /*!
125 \property QPieSeries::size
125 \property QPieSeries::size
126 \brief Defines the pie size.
126 \brief Defines the pie size.
127
127
128 The value is a relative value to the chart rectangle where:
128 The value is a relative value to the chart rectangle where:
129
129
130 \list
130 \list
131 \o 0.0 is the minimum size (pie not drawn).
131 \o 0.0 is the minimum size (pie not drawn).
132 \o 1.0 is the maximum size that can fit the chart.
132 \o 1.0 is the maximum size that can fit the chart.
133 \endlist
133 \endlist
134
134
135 Default value is 0.7.
135 Default value is 0.7.
136 */
136 */
137
137
138 /*!
138 /*!
139 \qmlproperty real PieSeries::size
139 \qmlproperty real PieSeries::size
140
140
141 Defines the pie size.
141 Defines the pie size.
142
142
143 The value is a relative value to the chart rectangle where:
143 The value is a relative value to the chart rectangle where:
144
144
145 \list
145 \list
146 \o 0.0 is the minimum size (pie not drawn).
146 \o 0.0 is the minimum size (pie not drawn).
147 \o 1.0 is the maximum size that can fit the chart.
147 \o 1.0 is the maximum size that can fit the chart.
148 \endlist
148 \endlist
149
149
150 Default value is 0.7.
150 Default value is 0.7.
151 */
151 */
152
152
153 /*!
153 /*!
154 \property QPieSeries::startAngle
154 \property QPieSeries::startAngle
155 \brief Defines the starting angle of the pie.
155 \brief Defines the starting angle of the pie.
156
156
157 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
157 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
158
158
159 Default is value is 0.
159 Default is value is 0.
160 */
160 */
161
161
162 /*!
162 /*!
163 \qmlproperty real PieSeries::startAngle
163 \qmlproperty real PieSeries::startAngle
164
164
165 Defines the starting angle of the pie.
165 Defines the starting angle of the pie.
166
166
167 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
167 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
168
168
169 Default is value is 0.
169 Default is value is 0.
170 */
170 */
171
171
172 /*!
172 /*!
173 \property QPieSeries::endAngle
173 \property QPieSeries::endAngle
174 \brief Defines the ending angle of the pie.
174 \brief Defines the ending angle of the pie.
175
175
176 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
176 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
177
177
178 Default is value is 360.
178 Default is value is 360.
179 */
179 */
180
180
181 /*!
181 /*!
182 \qmlproperty real PieSeries::endAngle
182 \qmlproperty real PieSeries::endAngle
183
183
184 Defines the ending angle of the pie.
184 Defines the ending angle of the pie.
185
185
186 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
186 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
187
187
188 Default is value is 360.
188 Default is value is 360.
189 */
189 */
190
190
191 /*!
191 /*!
192 \property QPieSeries::count
192 \property QPieSeries::count
193
193
194 Number of slices in the series.
194 Number of slices in the series.
195 */
195 */
196
196
197 /*!
197 /*!
198 \qmlproperty int PieSeries::count
198 \qmlproperty int PieSeries::count
199
199
200 Number of slices in the series.
200 Number of slices in the series.
201 */
201 */
202
202
203 /*!
203 /*!
204 \fn void QPieSeries::countChanged()
204 \fn void QPieSeries::countChanged()
205 Emitted when the slice count has changed.
205 Emitted when the slice count has changed.
206 \sa count
206 \sa count
207 */
207 */
208 /*!
208 /*!
209 \qmlsignal PieSeries::onCountChanged()
209 \qmlsignal PieSeries::onCountChanged()
210 Emitted when the slice count has changed.
210 Emitted when the slice count has changed.
211 */
211 */
212
212
213 /*!
213 /*!
214 \property QPieSeries::sum
214 \property QPieSeries::sum
215
215
216 Sum of all slices.
216 Sum of all slices.
217
217
218 The series keeps track of the sum of all slices it holds.
218 The series keeps track of the sum of all slices it holds.
219 */
219 */
220
220
221 /*!
221 /*!
222 \qmlproperty real PieSeries::sum
222 \qmlproperty real PieSeries::sum
223
223
224 Sum of all slices.
224 Sum of all slices.
225
225
226 The series keeps track of the sum of all slices it holds.
226 The series keeps track of the sum of all slices it holds.
227 */
227 */
228
228
229 /*!
229 /*!
230 \fn void QPieSeries::sumChanged()
230 \fn void QPieSeries::sumChanged()
231 Emitted when the sum of all slices has changed.
231 Emitted when the sum of all slices has changed.
232 \sa sum
232 \sa sum
233 */
233 */
234 /*!
234 /*!
235 \qmlsignal PieSeries::onSumChanged()
235 \qmlsignal PieSeries::onSumChanged()
236 Emitted when the sum of all slices has changed. This may happen for example if you add or remove slices, or if you
236 Emitted when the sum of all slices has changed. This may happen for example if you add or remove slices, or if you
237 change value of a slice.
237 change value of a slice.
238 */
238 */
239
239
240 /*!
240 /*!
241 \fn void QPieSeries::added(QList<QPieSlice*> slices)
241 \fn void QPieSeries::added(QList<QPieSlice*> slices)
242
242
243 This signal is emitted when \a slices have been added to the series.
243 This signal is emitted when \a slices have been added to the series.
244
244
245 \sa append(), insert()
245 \sa append(), insert()
246 */
246 */
247 /*!
247 /*!
248 \qmlsignal PieSeries::onAdded(PieSlice slice)
248 \qmlsignal PieSeries::onAdded(PieSlice slice)
249 Emitted when \a slice has been added to the series.
249 Emitted when \a slice has been added to the series.
250 */
250 */
251
251
252 /*!
252 /*!
253 \fn void QPieSeries::removed(QList<QPieSlice*> slices)
253 \fn void QPieSeries::removed(QList<QPieSlice*> slices)
254 This signal is emitted when \a slices have been removed from the series.
254 This signal is emitted when \a slices have been removed from the series.
255 \sa remove()
255 \sa remove()
256 */
256 */
257 /*!
257 /*!
258 \qmlsignal PieSeries::onRemoved(PieSlice slice)
258 \qmlsignal PieSeries::onRemoved(PieSlice slice)
259 Emitted when \a slice has been removed from the series.
259 Emitted when \a slice has been removed from the series.
260 */
260 */
261
261
262 /*!
262 /*!
263 \fn void QPieSeries::clicked(QPieSlice* slice)
263 \fn void QPieSeries::clicked(QPieSlice* slice)
264 This signal is emitted when a \a slice has been clicked.
264 This signal is emitted when a \a slice has been clicked.
265 \sa QPieSlice::clicked()
265 \sa QPieSlice::clicked()
266 */
266 */
267 /*!
267 /*!
268 \qmlsignal PieSeries::onClicked(PieSlice slice)
268 \qmlsignal PieSeries::onClicked(PieSlice slice)
269 This signal is emitted when a \a slice has been clicked.
269 This signal is emitted when a \a slice has been clicked.
270 */
270 */
271
271
272 /*!
272 /*!
273 \fn void QPieSeries::hovered(QPieSlice* slice, bool state)
273 \fn void QPieSeries::hovered(QPieSlice* slice, bool state)
274 This signal is emitted when user has hovered over or away from the \a slice.
274 This signal is emitted when user has hovered over or away from the \a slice.
275 \a state is true when user has hovered over the slice and false when hover has moved away from the slice.
275 \a state is true when user has hovered over the slice and false when hover has moved away from the slice.
276 \sa QPieSlice::hovered()
276 \sa QPieSlice::hovered()
277 */
277 */
278 /*!
278 /*!
279 \qmlsignal PieSeries::onHovered(PieSlice slice, bool state)
279 \qmlsignal PieSeries::onHovered(PieSlice slice, bool state)
280 This signal is emitted when user has hovered over or away from the \a slice. \a state is true when user has hovered
280 This signal is emitted when user has hovered over or away from the \a slice. \a state is true when user has hovered
281 over the slice and false when hover has moved away from the slice.
281 over the slice and false when hover has moved away from the slice.
282 */
282 */
283
283
284 /*!
284 /*!
285 \qmlmethod PieSlice PieSeries::at(int index)
285 \qmlmethod PieSlice PieSeries::at(int index)
286 Returns slice at \a index. Returns null if the index is not valid.
286 Returns slice at \a index. Returns null if the index is not valid.
287 */
287 */
288
288
289 /*!
289 /*!
290 \qmlmethod PieSlice PieSeries::find(string label)
290 \qmlmethod PieSlice PieSeries::find(string label)
291 Returns the first slice with \a label. Returns null if the index is not valid.
291 Returns the first slice with \a label. Returns null if the index is not valid.
292 */
292 */
293
293
294 /*!
294 /*!
295 \qmlmethod PieSlice PieSeries::append(string label, real value)
295 \qmlmethod PieSlice PieSeries::append(string label, real value)
296 Adds a new slice with \a label and \a value to the pie.
296 Adds a new slice with \a label and \a value to the pie.
297 */
297 */
298
298
299 /*!
299 /*!
300 \qmlmethod bool PieSeries::remove(PieSlice slice)
300 \qmlmethod bool PieSeries::remove(PieSlice slice)
301 Removes the \a slice from the pie. Returns true if the removal was successfull, false otherwise.
301 Removes the \a slice from the pie. Returns true if the removal was successfull, false otherwise.
302 */
302 */
303
303
304 /*!
304 /*!
305 \qmlmethod PieSeries::clear()
305 \qmlmethod PieSeries::clear()
306 Removes all slices from the pie.
306 Removes all slices from the pie.
307 */
307 */
308
308
309 /*!
309 /*!
310 Constructs a series object which is a child of \a parent.
310 Constructs a series object which is a child of \a parent.
311 */
311 */
312 QPieSeries::QPieSeries(QObject *parent) :
312 QPieSeries::QPieSeries(QObject *parent) :
313 QAbstractSeries(*new QPieSeriesPrivate(this),parent)
313 QAbstractSeries(*new QPieSeriesPrivate(this),parent)
314 {
314 {
315
315
316 }
316 }
317
317
318 /*!
318 /*!
319 Destroys the series and its slices.
319 Destroys the series and its slices.
320 */
320 */
321 QPieSeries::~QPieSeries()
321 QPieSeries::~QPieSeries()
322 {
322 {
323 // NOTE: d_prt destroyed by QObject
323 // NOTE: d_prt destroyed by QObject
324 }
324 }
325
325
326 /*!
326 /*!
327 Returns QChartSeries::SeriesTypePie.
327 Returns QChartSeries::SeriesTypePie.
328 */
328 */
329 QAbstractSeries::SeriesType QPieSeries::type() const
329 QAbstractSeries::SeriesType QPieSeries::type() const
330 {
330 {
331 return QAbstractSeries::SeriesTypePie;
331 return QAbstractSeries::SeriesTypePie;
332 }
332 }
333
333
334 /*!
334 /*!
335 Appends a single \a slice to the series.
335 Appends a single \a slice to the series.
336 Slice ownership is passed to the series.
336 Slice ownership is passed to the series.
337
337
338 Returns true if append was succesfull.
338 Returns true if append was succesfull.
339 */
339 */
340 bool QPieSeries::append(QPieSlice* slice)
340 bool QPieSeries::append(QPieSlice* slice)
341 {
341 {
342 return append(QList<QPieSlice*>() << slice);
342 return append(QList<QPieSlice*>() << slice);
343 }
343 }
344
344
345 /*!
345 /*!
346 Appends an array of \a slices to the series.
346 Appends an array of \a slices to the series.
347 Slice ownership is passed to the series.
347 Slice ownership is passed to the series.
348
348
349 Returns true if append was successfull.
349 Returns true if append was successfull.
350 */
350 */
351 bool QPieSeries::append(QList<QPieSlice*> slices)
351 bool QPieSeries::append(QList<QPieSlice*> slices)
352 {
352 {
353 Q_D(QPieSeries);
353 Q_D(QPieSeries);
354
354
355 if (slices.count() == 0)
355 if (slices.count() == 0)
356 return false;
356 return false;
357
357
358 foreach (QPieSlice* s, slices) {
358 foreach (QPieSlice* s, slices) {
359 if (!s || d->m_slices.contains(s))
359 if (!s || d->m_slices.contains(s))
360 return false;
360 return false;
361 if (s->series()) // already added to some series
361 if (s->series()) // already added to some series
362 return false;
362 return false;
363 }
363 }
364
364
365 foreach (QPieSlice* s, slices) {
365 foreach (QPieSlice* s, slices) {
366 s->setParent(this);
366 s->setParent(this);
367 QPieSlicePrivate::fromSlice(s)->m_series = this;
367 QPieSlicePrivate::fromSlice(s)->m_series = this;
368 d->m_slices << s;
368 d->m_slices << s;
369 }
369 }
370
370
371 d->updateDerivativeData();
371 d->updateDerivativeData();
372
372
373 foreach (QPieSlice* s, slices) {
373 foreach (QPieSlice* s, slices) {
374 connect(s, SIGNAL(valueChanged()), d, SLOT(sliceValueChanged()));
374 connect(s, SIGNAL(valueChanged()), d, SLOT(sliceValueChanged()));
375 connect(s, SIGNAL(clicked()), d, SLOT(sliceClicked()));
375 connect(s, SIGNAL(clicked()), d, SLOT(sliceClicked()));
376 connect(s, SIGNAL(hovered(bool)), d, SLOT(sliceHovered(bool)));
376 connect(s, SIGNAL(hovered(bool)), d, SLOT(sliceHovered(bool)));
377 }
377 }
378
378
379 emit added(slices);
379 emit added(slices);
380 emit countChanged();
380 emit countChanged();
381
381
382 return true;
382 return true;
383 }
383 }
384
384
385 /*!
385 /*!
386 Appends a single \a slice to the series and returns a reference to the series.
386 Appends a single \a slice to the series and returns a reference to the series.
387 Slice ownership is passed to the series.
387 Slice ownership is passed to the series.
388 */
388 */
389 QPieSeries& QPieSeries::operator << (QPieSlice* slice)
389 QPieSeries& QPieSeries::operator << (QPieSlice* slice)
390 {
390 {
391 append(slice);
391 append(slice);
392 return *this;
392 return *this;
393 }
393 }
394
394
395
395
396 /*!
396 /*!
397 Appends a single slice to the series with give \a value and \a label.
397 Appends a single slice to the series with give \a value and \a label.
398 Slice ownership is passed to the series.
398 Slice ownership is passed to the series.
399 */
399 */
400 QPieSlice* QPieSeries::append(QString label, qreal value)
400 QPieSlice* QPieSeries::append(QString label, qreal value)
401 {
401 {
402 QPieSlice* slice = new QPieSlice(label, value);
402 QPieSlice* slice = new QPieSlice(label, value);
403 append(slice);
403 append(slice);
404 return slice;
404 return slice;
405 }
405 }
406
406
407 /*!
407 /*!
408 Inserts a single \a slice to the series before the slice at \a index position.
408 Inserts a single \a slice to the series before the slice at \a index position.
409 Slice ownership is passed to the series.
409 Slice ownership is passed to the series.
410
410
411 Returns true if insert was successfull.
411 Returns true if insert was successfull.
412 */
412 */
413 bool QPieSeries::insert(int index, QPieSlice* slice)
413 bool QPieSeries::insert(int index, QPieSlice* slice)
414 {
414 {
415 Q_D(QPieSeries);
415 Q_D(QPieSeries);
416
416
417 if (index < 0 || index > d->m_slices.count())
417 if (index < 0 || index > d->m_slices.count())
418 return false;
418 return false;
419
419
420 if (!slice || d->m_slices.contains(slice))
420 if (!slice || d->m_slices.contains(slice))
421 return false;
421 return false;
422
422
423 if (slice->series()) // already added to some series
423 if (slice->series()) // already added to some series
424 return false;
424 return false;
425
425
426 slice->setParent(this);
426 slice->setParent(this);
427 QPieSlicePrivate::fromSlice(slice)->m_series = this;
427 QPieSlicePrivate::fromSlice(slice)->m_series = this;
428 d->m_slices.insert(index, slice);
428 d->m_slices.insert(index, slice);
429
429
430 d->updateDerivativeData();
430 d->updateDerivativeData();
431
431
432 connect(slice, SIGNAL(valueChanged()), d, SLOT(sliceValueChanged()));
432 connect(slice, SIGNAL(valueChanged()), d, SLOT(sliceValueChanged()));
433 connect(slice, SIGNAL(clicked()), d, SLOT(sliceClicked()));
433 connect(slice, SIGNAL(clicked()), d, SLOT(sliceClicked()));
434 connect(slice, SIGNAL(hovered(bool)), d, SLOT(sliceHovered(bool)));
434 connect(slice, SIGNAL(hovered(bool)), d, SLOT(sliceHovered(bool)));
435
435
436 emit added(QList<QPieSlice*>() << slice);
436 emit added(QList<QPieSlice*>() << slice);
437 emit countChanged();
437 emit countChanged();
438
438
439 return true;
439 return true;
440 }
440 }
441
441
442 /*!
442 /*!
443 Removes a single \a slice from the series and deletes the slice.
443 Removes a single \a slice from the series and deletes the slice.
444
444
445 Do not reference the pointer after this call.
445 Do not reference the pointer after this call.
446
446
447 Returns true if remove was successfull.
447 Returns true if remove was successfull.
448 */
448 */
449 bool QPieSeries::remove(QPieSlice* slice)
449 bool QPieSeries::remove(QPieSlice* slice)
450 {
450 {
451 Q_D(QPieSeries);
451 Q_D(QPieSeries);
452
452
453 if (!d->m_slices.removeOne(slice))
453 if (!d->m_slices.removeOne(slice))
454 return false;
454 return false;
455
455
456 d->updateDerivativeData();
456 d->updateDerivativeData();
457
457
458 emit removed(QList<QPieSlice*>() << slice);
458 emit removed(QList<QPieSlice*>() << slice);
459 emit countChanged();
459 emit countChanged();
460
460
461 delete slice;
461 delete slice;
462 slice = 0;
462 slice = 0;
463
463
464 return true;
464 return true;
465 }
465 }
466
466
467 /*!
467 /*!
468 Clears all slices from the series.
468 Clears all slices from the series.
469 */
469 */
470 void QPieSeries::clear()
470 void QPieSeries::clear()
471 {
471 {
472 Q_D(QPieSeries);
472 Q_D(QPieSeries);
473 if (d->m_slices.count() == 0)
473 if (d->m_slices.count() == 0)
474 return;
474 return;
475
475
476 QList<QPieSlice*> slices = d->m_slices;
476 QList<QPieSlice*> slices = d->m_slices;
477 foreach (QPieSlice* s, d->m_slices) {
477 foreach (QPieSlice* s, d->m_slices) {
478 d->m_slices.removeOne(s);
478 d->m_slices.removeOne(s);
479 delete s;
479 delete s;
480 }
480 }
481
481
482 d->updateDerivativeData();
482 d->updateDerivativeData();
483
483
484 emit removed(slices);
484 emit removed(slices);
485 emit countChanged();
485 emit countChanged();
486 }
486 }
487
487
488 /*!
488 /*!
489 Returns a list of slices that belong to this series.
489 Returns a list of slices that belong to this series.
490 */
490 */
491 QList<QPieSlice*> QPieSeries::slices() const
491 QList<QPieSlice*> QPieSeries::slices() const
492 {
492 {
493 Q_D(const QPieSeries);
493 Q_D(const QPieSeries);
494 return d->m_slices;
494 return d->m_slices;
495 }
495 }
496
496
497 /*!
497 /*!
498 returns the number of the slices in this series.
498 returns the number of the slices in this series.
499 */
499 */
500 int QPieSeries::count() const
500 int QPieSeries::count() const
501 {
501 {
502 Q_D(const QPieSeries);
502 Q_D(const QPieSeries);
503 return d->m_slices.count();
503 return d->m_slices.count();
504 }
504 }
505
505
506 /*!
506 /*!
507 Returns true is the series is empty.
507 Returns true is the series is empty.
508 */
508 */
509 bool QPieSeries::isEmpty() const
509 bool QPieSeries::isEmpty() const
510 {
510 {
511 Q_D(const QPieSeries);
511 Q_D(const QPieSeries);
512 return d->m_slices.isEmpty();
512 return d->m_slices.isEmpty();
513 }
513 }
514
514
515 /*!
515 /*!
516 Returns the sum of all slice values in this series.
516 Returns the sum of all slice values in this series.
517
517
518 \sa QPieSlice::value(), QPieSlice::setValue(), QPieSlice::percentage()
518 \sa QPieSlice::value(), QPieSlice::setValue(), QPieSlice::percentage()
519 */
519 */
520 qreal QPieSeries::sum() const
520 qreal QPieSeries::sum() const
521 {
521 {
522 Q_D(const QPieSeries);
522 Q_D(const QPieSeries);
523 return d->m_sum;
523 return d->m_sum;
524 }
524 }
525
525
526 void QPieSeries::setDonut(bool donut)
526 void QPieSeries::setDonut(bool donut)
527 {
527 {
528 Q_D(QPieSeries);
528 Q_D(QPieSeries);
529 d->m_donutChart = donut;
529 d->m_donutChart = donut;
530 d->updateDerivativeData();
530 d->updateDerivativeData();
531 }
531 }
532
532
533 bool QPieSeries::donut() const
533 bool QPieSeries::donut() const
534 {
534 {
535 Q_D(const QPieSeries);
535 Q_D(const QPieSeries);
536 return d->m_donutChart;
536 return d->m_donutChart;
537 }
537 }
538
538
539 void QPieSeries::setDonutInnerSize(qreal innerSize)
539 void QPieSeries::setDonutInnerSize(qreal innerSize)
540 {
540 {
541 Q_D(QPieSeries);
541 Q_D(QPieSeries);
542
542
543 if (innerSize < 0.0)
543 if (innerSize < 0.0)
544 innerSize = 0.0;
544 innerSize = 0.0;
545 if (innerSize > 1.0)
545 if (innerSize > 1.0)
546 innerSize = 1.0;
546 innerSize = 1.0;
547
547
548 d->m_donutRelativeInnerSize = innerSize;
548 d->m_donutRelativeInnerSize = innerSize;
549 d->updateDerivativeData();
549 d->updateDerivativeData();
550 emit d->pieSizeChanged();
550 emit d->pieSizeChanged();
551 }
551 }
552
552
553 qreal QPieSeries::donutInnerSize() const
553 qreal QPieSeries::donutInnerSize() const
554 {
554 {
555 Q_D(const QPieSeries);
555 Q_D(const QPieSeries);
556 return d->m_donutRelativeInnerSize;
556 return d->m_donutRelativeInnerSize;
557 }
557 }
558
558
559 void QPieSeries::setHorizontalPosition(qreal relativePosition)
559 void QPieSeries::setHorizontalPosition(qreal relativePosition)
560 {
560 {
561 Q_D(QPieSeries);
561 Q_D(QPieSeries);
562
562
563 if (relativePosition < 0.0)
563 if (relativePosition < 0.0)
564 relativePosition = 0.0;
564 relativePosition = 0.0;
565 if (relativePosition > 1.0)
565 if (relativePosition > 1.0)
566 relativePosition = 1.0;
566 relativePosition = 1.0;
567
567
568 if (!qFuzzyIsNull(d->m_pieRelativeHorPos - relativePosition)) {
568 if (!qFuzzyIsNull(d->m_pieRelativeHorPos - relativePosition)) {
569 d->m_pieRelativeHorPos = relativePosition;
569 d->m_pieRelativeHorPos = relativePosition;
570 emit d->horizontalPositionChanged();
570 emit d->horizontalPositionChanged();
571 }
571 }
572 }
572 }
573
573
574 qreal QPieSeries::horizontalPosition() const
574 qreal QPieSeries::horizontalPosition() const
575 {
575 {
576 Q_D(const QPieSeries);
576 Q_D(const QPieSeries);
577 return d->m_pieRelativeHorPos;
577 return d->m_pieRelativeHorPos;
578 }
578 }
579
579
580 void QPieSeries::setVerticalPosition(qreal relativePosition)
580 void QPieSeries::setVerticalPosition(qreal relativePosition)
581 {
581 {
582 Q_D(QPieSeries);
582 Q_D(QPieSeries);
583
583
584 if (relativePosition < 0.0)
584 if (relativePosition < 0.0)
585 relativePosition = 0.0;
585 relativePosition = 0.0;
586 if (relativePosition > 1.0)
586 if (relativePosition > 1.0)
587 relativePosition = 1.0;
587 relativePosition = 1.0;
588
588
589 if (!qFuzzyIsNull(d->m_pieRelativeVerPos - relativePosition)) {
589 if (!qFuzzyIsNull(d->m_pieRelativeVerPos - relativePosition)) {
590 d->m_pieRelativeVerPos = relativePosition;
590 d->m_pieRelativeVerPos = relativePosition;
591 emit d->verticalPositionChanged();
591 emit d->verticalPositionChanged();
592 }
592 }
593 }
593 }
594
594
595 qreal QPieSeries::verticalPosition() const
595 qreal QPieSeries::verticalPosition() const
596 {
596 {
597 Q_D(const QPieSeries);
597 Q_D(const QPieSeries);
598 return d->m_pieRelativeVerPos;
598 return d->m_pieRelativeVerPos;
599 }
599 }
600
600
601 void QPieSeries::setPieSize(qreal relativeSize)
601 void QPieSeries::setPieSize(qreal relativeSize)
602 {
602 {
603 Q_D(QPieSeries);
603 Q_D(QPieSeries);
604
604
605 if (relativeSize < 0.0)
605 if (relativeSize < 0.0)
606 relativeSize = 0.0;
606 relativeSize = 0.0;
607 if (relativeSize > 1.0)
607 if (relativeSize > 1.0)
608 relativeSize = 1.0;
608 relativeSize = 1.0;
609
609
610 if (!qFuzzyIsNull(d->m_pieRelativeSize - relativeSize)) {
610 if (!qFuzzyIsNull(d->m_pieRelativeSize - relativeSize)) {
611 d->m_pieRelativeSize = relativeSize;
611 d->m_pieRelativeSize = relativeSize;
612 emit d->pieSizeChanged();
612 emit d->pieSizeChanged();
613 }
613 }
614 }
614 }
615
615
616 qreal QPieSeries::pieSize() const
616 qreal QPieSeries::pieSize() const
617 {
617 {
618 Q_D(const QPieSeries);
618 Q_D(const QPieSeries);
619 return d->m_pieRelativeSize;
619 return d->m_pieRelativeSize;
620 }
620 }
621
621
622
622
623 void QPieSeries::setPieStartAngle(qreal angle)
623 void QPieSeries::setPieStartAngle(qreal angle)
624 {
624 {
625 Q_D(QPieSeries);
625 Q_D(QPieSeries);
626 if (qFuzzyIsNull(d->m_pieStartAngle - angle))
626 if (qFuzzyIsNull(d->m_pieStartAngle - angle))
627 return;
627 return;
628 d->m_pieStartAngle = angle;
628 d->m_pieStartAngle = angle;
629 d->updateDerivativeData();
629 d->updateDerivativeData();
630 emit d->pieStartAngleChanged();
630 emit d->pieStartAngleChanged();
631 }
631 }
632
632
633 qreal QPieSeries::pieStartAngle() const
633 qreal QPieSeries::pieStartAngle() const
634 {
634 {
635 Q_D(const QPieSeries);
635 Q_D(const QPieSeries);
636 return d->m_pieStartAngle;
636 return d->m_pieStartAngle;
637 }
637 }
638
638
639 /*!
639 /*!
640 Sets the end angle of the pie.
640 Sets the end angle of the pie.
641
641
642 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
642 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
643
643
644 \a angle must be greater than start angle.
644 \a angle must be greater than start angle.
645
645
646 \sa pieEndAngle(), pieStartAngle(), setPieStartAngle()
646 \sa pieEndAngle(), pieStartAngle(), setPieStartAngle()
647 */
647 */
648 void QPieSeries::setPieEndAngle(qreal angle)
648 void QPieSeries::setPieEndAngle(qreal angle)
649 {
649 {
650 Q_D(QPieSeries);
650 Q_D(QPieSeries);
651 if (qFuzzyIsNull(d->m_pieEndAngle - angle))
651 if (qFuzzyIsNull(d->m_pieEndAngle - angle))
652 return;
652 return;
653 d->m_pieEndAngle = angle;
653 d->m_pieEndAngle = angle;
654 d->updateDerivativeData();
654 d->updateDerivativeData();
655 emit d->pieEndAngleChanged();
655 emit d->pieEndAngleChanged();
656 }
656 }
657
657
658 /*!
658 /*!
659 Returns the end angle of the pie.
659 Returns the end angle of the pie.
660
660
661 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
661 Full pie is 360 degrees where 0 degrees is at 12 a'clock.
662
662
663 \sa setPieEndAngle(), pieStartAngle(), setPieStartAngle()
663 \sa setPieEndAngle(), pieStartAngle(), setPieStartAngle()
664 */
664 */
665 qreal QPieSeries::pieEndAngle() const
665 qreal QPieSeries::pieEndAngle() const
666 {
666 {
667 Q_D(const QPieSeries);
667 Q_D(const QPieSeries);
668 return d->m_pieEndAngle;
668 return d->m_pieEndAngle;
669 }
669 }
670
670
671 /*!
671 /*!
672 Sets the all the slice labels \a visible or invisible.
672 Sets the all the slice labels \a visible or invisible.
673
673
674 Note that this affects only the current slices in the series.
674 Note that this affects only the current slices in the series.
675 If user adds a new slice the default label visibility is false.
675 If user adds a new slice the default label visibility is false.
676
676
677 \sa QPieSlice::isLabelVisible(), QPieSlice::setLabelVisible()
677 \sa QPieSlice::isLabelVisible(), QPieSlice::setLabelVisible()
678 */
678 */
679 void QPieSeries::setLabelsVisible(bool visible)
679 void QPieSeries::setLabelsVisible(bool visible)
680 {
680 {
681 Q_D(QPieSeries);
681 Q_D(QPieSeries);
682 foreach (QPieSlice* s, d->m_slices)
682 foreach (QPieSlice* s, d->m_slices)
683 s->setLabelVisible(visible);
683 s->setLabelVisible(visible);
684 }
684 }
685
685
686 void QPieSeries::setLabelsPosition(QPieSlice::LabelPosition position)
687 {
688 Q_D(QPieSeries);
689 foreach (QPieSlice* s, d->m_slices)
690 s->setLabelPosition(position);
691 }
692
686 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
693 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
687
694
688
695
689 QPieSeriesPrivate::QPieSeriesPrivate(QPieSeries *parent) :
696 QPieSeriesPrivate::QPieSeriesPrivate(QPieSeries *parent) :
690 QAbstractSeriesPrivate(parent),
697 QAbstractSeriesPrivate(parent),
691 m_pieRelativeHorPos(0.5),
698 m_pieRelativeHorPos(0.5),
692 m_pieRelativeVerPos(0.5),
699 m_pieRelativeVerPos(0.5),
693 m_pieRelativeSize(0.7),
700 m_pieRelativeSize(0.7),
694 m_pieStartAngle(0),
701 m_pieStartAngle(0),
695 m_pieEndAngle(360),
702 m_pieEndAngle(360),
696 m_sum(0),
703 m_sum(0),
697 m_donutChart(false),
704 m_donutChart(false),
698 m_donutRelativeInnerSize(0.5)
705 m_donutRelativeInnerSize(0.5)
699 {
706 {
700 }
707 }
701
708
702 QPieSeriesPrivate::~QPieSeriesPrivate()
709 QPieSeriesPrivate::~QPieSeriesPrivate()
703 {
710 {
704 }
711 }
705
712
706 void QPieSeriesPrivate::updateDerivativeData()
713 void QPieSeriesPrivate::updateDerivativeData()
707 {
714 {
708 // calculate sum of all slices
715 // calculate sum of all slices
709 qreal sum = 0;
716 qreal sum = 0;
710 foreach (QPieSlice* s, m_slices)
717 foreach (QPieSlice* s, m_slices)
711 sum += s->value();
718 sum += s->value();
712
719
713 if (!qFuzzyIsNull(m_sum - sum)) {
720 if (!qFuzzyIsNull(m_sum - sum)) {
714 m_sum = sum;
721 m_sum = sum;
715 emit q_func()->sumChanged();
722 emit q_func()->sumChanged();
716 }
723 }
717
724
718 // nothing to show..
725 // nothing to show..
719 if (qFuzzyIsNull(m_sum))
726 if (qFuzzyIsNull(m_sum))
720 return;
727 return;
721
728
722 // update slice attributes
729 // update slice attributes
723 qreal sliceAngle = m_pieStartAngle;
730 qreal sliceAngle = m_pieStartAngle;
724 qreal pieSpan = m_pieEndAngle - m_pieStartAngle;
731 qreal pieSpan = m_pieEndAngle - m_pieStartAngle;
725 QVector<QPieSlice*> changed;
732 QVector<QPieSlice*> changed;
726 foreach (QPieSlice* s, m_slices) {
733 foreach (QPieSlice* s, m_slices) {
727 QPieSlicePrivate *d = QPieSlicePrivate::fromSlice(s);
734 QPieSlicePrivate *d = QPieSlicePrivate::fromSlice(s);
728 d->setPercentage(s->value() / m_sum);
735 d->setPercentage(s->value() / m_sum);
729 d->setStartAngle(sliceAngle);
736 d->setStartAngle(sliceAngle);
730 d->setAngleSpan(pieSpan * s->percentage());
737 d->setAngleSpan(pieSpan * s->percentage());
731 sliceAngle += s->angleSpan();
738 sliceAngle += s->angleSpan();
732 }
739 }
733
740
734
741
735 emit calculatedDataChanged();
742 emit calculatedDataChanged();
736 }
743 }
737
744
738 QPieSeriesPrivate* QPieSeriesPrivate::fromSeries(QPieSeries *series)
745 QPieSeriesPrivate* QPieSeriesPrivate::fromSeries(QPieSeries *series)
739 {
746 {
740 return series->d_func();
747 return series->d_func();
741 }
748 }
742
749
743 void QPieSeriesPrivate::sliceValueChanged()
750 void QPieSeriesPrivate::sliceValueChanged()
744 {
751 {
745 Q_ASSERT(m_slices.contains(qobject_cast<QPieSlice *>(sender())));
752 Q_ASSERT(m_slices.contains(qobject_cast<QPieSlice *>(sender())));
746 updateDerivativeData();
753 updateDerivativeData();
747 }
754 }
748
755
749 void QPieSeriesPrivate::sliceClicked()
756 void QPieSeriesPrivate::sliceClicked()
750 {
757 {
751 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
758 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
752 Q_ASSERT(m_slices.contains(slice));
759 Q_ASSERT(m_slices.contains(slice));
753 Q_Q(QPieSeries);
760 Q_Q(QPieSeries);
754 emit q->clicked(slice);
761 emit q->clicked(slice);
755 }
762 }
756
763
757 void QPieSeriesPrivate::sliceHovered(bool state)
764 void QPieSeriesPrivate::sliceHovered(bool state)
758 {
765 {
759 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
766 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
760 Q_ASSERT(m_slices.contains(slice));
767 Q_ASSERT(m_slices.contains(slice));
761 Q_Q(QPieSeries);
768 Q_Q(QPieSeries);
762 emit q->hovered(slice, state);
769 emit q->hovered(slice, state);
763 }
770 }
764
771
765 void QPieSeriesPrivate::scaleDomain(Domain& domain)
772 void QPieSeriesPrivate::scaleDomain(Domain& domain)
766 {
773 {
767 Q_UNUSED(domain);
774 Q_UNUSED(domain);
768 // does not apply to pie
775 // does not apply to pie
769 }
776 }
770
777
771 Chart* QPieSeriesPrivate::createGraphics(ChartPresenter* presenter)
778 Chart* QPieSeriesPrivate::createGraphics(ChartPresenter* presenter)
772 {
779 {
773 Q_Q(QPieSeries);
780 Q_Q(QPieSeries);
774 PieChartItem* pie = new PieChartItem(q,presenter);
781 PieChartItem* pie = new PieChartItem(q,presenter);
775 if(presenter->animationOptions().testFlag(QChart::SeriesAnimations)) {
782 if(presenter->animationOptions().testFlag(QChart::SeriesAnimations)) {
776 presenter->animator()->addAnimation(pie);
783 presenter->animator()->addAnimation(pie);
777 }
784 }
778 presenter->chartTheme()->decorate(q, presenter->dataSet()->seriesIndex(q));
785 presenter->chartTheme()->decorate(q, presenter->dataSet()->seriesIndex(q));
779 return pie;
786 return pie;
780 }
787 }
781
788
782 QList<LegendMarker*> QPieSeriesPrivate::createLegendMarker(QLegend* legend)
789 QList<LegendMarker*> QPieSeriesPrivate::createLegendMarker(QLegend* legend)
783 {
790 {
784 Q_Q(QPieSeries);
791 Q_Q(QPieSeries);
785 QList<LegendMarker*> markers;
792 QList<LegendMarker*> markers;
786 foreach(QPieSlice* slice, q->slices()) {
793 foreach(QPieSlice* slice, q->slices()) {
787 PieLegendMarker* marker = new PieLegendMarker(q,slice,legend);
794 PieLegendMarker* marker = new PieLegendMarker(q,slice,legend);
788 markers << marker;
795 markers << marker;
789 }
796 }
790 return markers;
797 return markers;
791 }
798 }
792
799
793 void QPieSeriesPrivate::initializeAxis(QAbstractAxis* axis)
800 void QPieSeriesPrivate::initializeAxis(QAbstractAxis* axis)
794 {
801 {
795 Q_UNUSED(axis);
802 Q_UNUSED(axis);
796 }
803 }
797
804
798 QAbstractAxis::AxisType QPieSeriesPrivate::defaultAxisType(Qt::Orientation orientation) const
805 QAbstractAxis::AxisType QPieSeriesPrivate::defaultAxisType(Qt::Orientation orientation) const
799 {
806 {
800 Q_UNUSED(orientation);
807 Q_UNUSED(orientation);
801 return QAbstractAxis::AxisTypeNoAxis;
808 return QAbstractAxis::AxisTypeNoAxis;
802 }
809 }
803
810
804 #include "moc_qpieseries.cpp"
811 #include "moc_qpieseries.cpp"
805 #include "moc_qpieseries_p.cpp"
812 #include "moc_qpieseries_p.cpp"
806
813
807 QTCOMMERCIALCHART_END_NAMESPACE
814 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,102 +1,104
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 PIESERIES_H
21 #ifndef PIESERIES_H
22 #define PIESERIES_H
22 #define PIESERIES_H
23
23
24 #include <qabstractseries.h>
24 #include <qabstractseries.h>
25 #include <QPieSlice>
25
26
26 QTCOMMERCIALCHART_BEGIN_NAMESPACE
27 QTCOMMERCIALCHART_BEGIN_NAMESPACE
27 class QPieSeriesPrivate;
28 class QPieSeriesPrivate;
28 class QPieSlice;
29 //class QPieSlice;
29
30
30 class QTCOMMERCIALCHART_EXPORT QPieSeries : public QAbstractSeries
31 class QTCOMMERCIALCHART_EXPORT QPieSeries : public QAbstractSeries
31 {
32 {
32 Q_OBJECT
33 Q_OBJECT
33 Q_PROPERTY(qreal horizontalPosition READ horizontalPosition WRITE setHorizontalPosition)
34 Q_PROPERTY(qreal horizontalPosition READ horizontalPosition WRITE setHorizontalPosition)
34 Q_PROPERTY(qreal verticalPosition READ verticalPosition WRITE setVerticalPosition)
35 Q_PROPERTY(qreal verticalPosition READ verticalPosition WRITE setVerticalPosition)
35 Q_PROPERTY(qreal size READ pieSize WRITE setPieSize)
36 Q_PROPERTY(qreal size READ pieSize WRITE setPieSize)
36 Q_PROPERTY(qreal startAngle READ pieStartAngle WRITE setPieStartAngle)
37 Q_PROPERTY(qreal startAngle READ pieStartAngle WRITE setPieStartAngle)
37 Q_PROPERTY(qreal endAngle READ pieEndAngle WRITE setPieEndAngle)
38 Q_PROPERTY(qreal endAngle READ pieEndAngle WRITE setPieEndAngle)
38 Q_PROPERTY(int count READ count NOTIFY countChanged)
39 Q_PROPERTY(int count READ count NOTIFY countChanged)
39 Q_PROPERTY(qreal sum READ sum NOTIFY sumChanged)
40 Q_PROPERTY(qreal sum READ sum NOTIFY sumChanged)
40
41
41 public:
42 public:
42 explicit QPieSeries(QObject *parent = 0);
43 explicit QPieSeries(QObject *parent = 0);
43 virtual ~QPieSeries();
44 virtual ~QPieSeries();
44
45
45 QAbstractSeries::SeriesType type() const;
46 QAbstractSeries::SeriesType type() const;
46
47
47 bool append(QPieSlice* slice);
48 bool append(QPieSlice* slice);
48 bool append(QList<QPieSlice*> slices);
49 bool append(QList<QPieSlice*> slices);
49 QPieSeries& operator << (QPieSlice* slice);
50 QPieSeries& operator << (QPieSlice* slice);
50 QPieSlice* append(QString label, qreal value);
51 QPieSlice* append(QString label, qreal value);
51
52
52 bool insert(int index, QPieSlice* slice);
53 bool insert(int index, QPieSlice* slice);
53
54
54 bool remove(QPieSlice* slice);
55 bool remove(QPieSlice* slice);
55 void clear();
56 void clear();
56
57
57 QList<QPieSlice*> slices() const;
58 QList<QPieSlice*> slices() const;
58 int count() const;
59 int count() const;
59
60
60 bool isEmpty() const;
61 bool isEmpty() const;
61
62
62 qreal sum() const;
63 qreal sum() const;
63
64
64 void setDonut(bool donut = true);
65 void setDonut(bool donut = true);
65 bool donut() const;
66 bool donut() const;
66
67
67 void setDonutInnerSize(qreal innerSize);
68 void setDonutInnerSize(qreal innerSize);
68 qreal donutInnerSize() const;
69 qreal donutInnerSize() const;
69
70
70 void setHorizontalPosition(qreal relativePosition);
71 void setHorizontalPosition(qreal relativePosition);
71 qreal horizontalPosition() const;
72 qreal horizontalPosition() const;
72
73
73 void setVerticalPosition(qreal relativePosition);
74 void setVerticalPosition(qreal relativePosition);
74 qreal verticalPosition() const;
75 qreal verticalPosition() const;
75
76
76 void setPieSize(qreal relativeSize);
77 void setPieSize(qreal relativeSize);
77 qreal pieSize() const;
78 qreal pieSize() const;
78
79
79 void setPieStartAngle(qreal startAngle);
80 void setPieStartAngle(qreal startAngle);
80 qreal pieStartAngle() const;
81 qreal pieStartAngle() const;
81
82
82 void setPieEndAngle(qreal endAngle);
83 void setPieEndAngle(qreal endAngle);
83 qreal pieEndAngle() const;
84 qreal pieEndAngle() const;
84
85
85 void setLabelsVisible(bool visible = true);
86 void setLabelsVisible(bool visible = true);
87 void setLabelsPosition(QPieSlice::LabelPosition position);
86
88
87 Q_SIGNALS:
89 Q_SIGNALS:
88 void added(QList<QPieSlice*> slices);
90 void added(QList<QPieSlice*> slices);
89 void removed(QList<QPieSlice*> slices);
91 void removed(QList<QPieSlice*> slices);
90 void clicked(QPieSlice* slice);
92 void clicked(QPieSlice* slice);
91 void hovered(QPieSlice* slice, bool state);
93 void hovered(QPieSlice* slice, bool state);
92 void countChanged();
94 void countChanged();
93 void sumChanged();
95 void sumChanged();
94
96
95 private:
97 private:
96 Q_DECLARE_PRIVATE(QPieSeries)
98 Q_DECLARE_PRIVATE(QPieSeries)
97 Q_DISABLE_COPY(QPieSeries)
99 Q_DISABLE_COPY(QPieSeries)
98 };
100 };
99
101
100 QTCOMMERCIALCHART_END_NAMESPACE
102 QTCOMMERCIALCHART_END_NAMESPACE
101
103
102 #endif // PIESERIES_H
104 #endif // PIESERIES_H
@@ -1,145 +1,147
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 QPIESLICE_H
21 #ifndef QPIESLICE_H
22 #define QPIESLICE_H
22 #define QPIESLICE_H
23
23
24 #include <qchartglobal.h>
24 #include <qchartglobal.h>
25 #include <QObject>
25 #include <QObject>
26 #include <QPen>
26 #include <QPen>
27 #include <QBrush>
27 #include <QBrush>
28 #include <QFont>
28 #include <QFont>
29
29
30 QTCOMMERCIALCHART_BEGIN_NAMESPACE
30 QTCOMMERCIALCHART_BEGIN_NAMESPACE
31 class QPieSlicePrivate;
31 class QPieSlicePrivate;
32 class QPieSeries;
32 class QPieSeries;
33
33
34 class QTCOMMERCIALCHART_EXPORT QPieSlice : public QObject
34 class QTCOMMERCIALCHART_EXPORT QPieSlice : public QObject
35 {
35 {
36 Q_OBJECT
36 Q_OBJECT
37 Q_ENUMS(LabelPosition)
37 Q_ENUMS(LabelPosition)
38 Q_PROPERTY(QString label READ label WRITE setLabel NOTIFY labelChanged)
38 Q_PROPERTY(QString label READ label WRITE setLabel NOTIFY labelChanged)
39 Q_PROPERTY(qreal value READ value WRITE setValue NOTIFY valueChanged)
39 Q_PROPERTY(qreal value READ value WRITE setValue NOTIFY valueChanged)
40 Q_PROPERTY(bool labelVisible READ isLabelVisible WRITE setLabelVisible NOTIFY labelVisibleChanged)
40 Q_PROPERTY(bool labelVisible READ isLabelVisible WRITE setLabelVisible NOTIFY labelVisibleChanged)
41 Q_PROPERTY(LabelPosition labelPosition READ labelPosition WRITE setLabelPosition)
41 Q_PROPERTY(LabelPosition labelPosition READ labelPosition WRITE setLabelPosition)
42 Q_PROPERTY(bool exploded READ isExploded WRITE setExploded)
42 Q_PROPERTY(bool exploded READ isExploded WRITE setExploded)
43 Q_PROPERTY(QPen pen READ pen WRITE setPen NOTIFY penChanged)
43 Q_PROPERTY(QPen pen READ pen WRITE setPen NOTIFY penChanged)
44 Q_PROPERTY(QColor borderColor READ borderColor WRITE setBorderColor NOTIFY borderColorChanged)
44 Q_PROPERTY(QColor borderColor READ borderColor WRITE setBorderColor NOTIFY borderColorChanged)
45 Q_PROPERTY(int borderWidth READ borderWidth WRITE setBorderWidth NOTIFY borderWidthChanged)
45 Q_PROPERTY(int borderWidth READ borderWidth WRITE setBorderWidth NOTIFY borderWidthChanged)
46 Q_PROPERTY(QBrush brush READ brush WRITE setBrush NOTIFY brushChanged)
46 Q_PROPERTY(QBrush brush READ brush WRITE setBrush NOTIFY brushChanged)
47 Q_PROPERTY(QColor color READ color WRITE setColor NOTIFY colorChanged)
47 Q_PROPERTY(QColor color READ color WRITE setColor NOTIFY colorChanged)
48 Q_PROPERTY(QBrush labelBrush READ labelBrush WRITE setLabelBrush NOTIFY labelBrushChanged)
48 Q_PROPERTY(QBrush labelBrush READ labelBrush WRITE setLabelBrush NOTIFY labelBrushChanged)
49 Q_PROPERTY(QColor labelColor READ labelColor WRITE setLabelColor NOTIFY labelColorChanged)
49 Q_PROPERTY(QColor labelColor READ labelColor WRITE setLabelColor NOTIFY labelColorChanged)
50 Q_PROPERTY(QFont labelFont READ labelFont WRITE setLabelFont NOTIFY labelFontChanged)
50 Q_PROPERTY(QFont labelFont READ labelFont WRITE setLabelFont NOTIFY labelFontChanged)
51 Q_PROPERTY(qreal labelArmLengthFactor READ labelArmLengthFactor WRITE setLabelArmLengthFactor)
51 Q_PROPERTY(qreal labelArmLengthFactor READ labelArmLengthFactor WRITE setLabelArmLengthFactor)
52 Q_PROPERTY(qreal explodeDistanceFactor READ explodeDistanceFactor WRITE setExplodeDistanceFactor)
52 Q_PROPERTY(qreal explodeDistanceFactor READ explodeDistanceFactor WRITE setExplodeDistanceFactor)
53 Q_PROPERTY(qreal percentage READ percentage NOTIFY percentageChanged)
53 Q_PROPERTY(qreal percentage READ percentage NOTIFY percentageChanged)
54 Q_PROPERTY(qreal startAngle READ startAngle NOTIFY startAngleChanged)
54 Q_PROPERTY(qreal startAngle READ startAngle NOTIFY startAngleChanged)
55 Q_PROPERTY(qreal angleSpan READ angleSpan NOTIFY angleSpanChanged)
55 Q_PROPERTY(qreal angleSpan READ angleSpan NOTIFY angleSpanChanged)
56
56
57 public:
57 public:
58 enum LabelPosition {
58 enum LabelPosition {
59 LabelOutside,
59 LabelOutside,
60 LabelInside
60 LabelInside,
61 LabelInsideTangential,
62 LabelInsideNormal
61 };
63 };
62
64
63 public:
65 public:
64 explicit QPieSlice(QObject *parent = 0);
66 explicit QPieSlice(QObject *parent = 0);
65 QPieSlice(QString label, qreal value, QObject *parent = 0);
67 QPieSlice(QString label, qreal value, QObject *parent = 0);
66 virtual ~QPieSlice();
68 virtual ~QPieSlice();
67
69
68 void setLabel(QString label);
70 void setLabel(QString label);
69 QString label() const;
71 QString label() const;
70
72
71 void setValue(qreal value);
73 void setValue(qreal value);
72 qreal value() const;
74 qreal value() const;
73
75
74 void setLabelVisible(bool visible = true);
76 void setLabelVisible(bool visible = true);
75 bool isLabelVisible() const;
77 bool isLabelVisible() const;
76
78
77 LabelPosition labelPosition();
79 LabelPosition labelPosition();
78 void setLabelPosition(LabelPosition position);
80 void setLabelPosition(LabelPosition position);
79
81
80 void setExploded(bool exploded = true);
82 void setExploded(bool exploded = true);
81 bool isExploded() const;
83 bool isExploded() const;
82
84
83 void setPen(const QPen &pen);
85 void setPen(const QPen &pen);
84 QPen pen() const;
86 QPen pen() const;
85
87
86 QColor borderColor();
88 QColor borderColor();
87 void setBorderColor(QColor color);
89 void setBorderColor(QColor color);
88
90
89 int borderWidth();
91 int borderWidth();
90 void setBorderWidth(int width);
92 void setBorderWidth(int width);
91
93
92 void setBrush(const QBrush &brush);
94 void setBrush(const QBrush &brush);
93 QBrush brush() const;
95 QBrush brush() const;
94
96
95 QColor color();
97 QColor color();
96 void setColor(QColor color);
98 void setColor(QColor color);
97
99
98 void setLabelBrush(const QBrush &brush);
100 void setLabelBrush(const QBrush &brush);
99 QBrush labelBrush() const;
101 QBrush labelBrush() const;
100
102
101 QColor labelColor();
103 QColor labelColor();
102 void setLabelColor(QColor color);
104 void setLabelColor(QColor color);
103
105
104 void setLabelFont(const QFont &font);
106 void setLabelFont(const QFont &font);
105 QFont labelFont() const;
107 QFont labelFont() const;
106
108
107 void setLabelArmLengthFactor(qreal factor);
109 void setLabelArmLengthFactor(qreal factor);
108 qreal labelArmLengthFactor() const;
110 qreal labelArmLengthFactor() const;
109
111
110 void setExplodeDistanceFactor(qreal factor);
112 void setExplodeDistanceFactor(qreal factor);
111 qreal explodeDistanceFactor() const;
113 qreal explodeDistanceFactor() const;
112
114
113 qreal percentage() const;
115 qreal percentage() const;
114 qreal startAngle() const;
116 qreal startAngle() const;
115 qreal angleSpan() const;
117 qreal angleSpan() const;
116
118
117 QPieSeries *series() const;
119 QPieSeries *series() const;
118
120
119 Q_SIGNALS:
121 Q_SIGNALS:
120 void clicked();
122 void clicked();
121 void hovered(bool state);
123 void hovered(bool state);
122 void labelChanged();
124 void labelChanged();
123 void valueChanged();
125 void valueChanged();
124 void labelVisibleChanged();
126 void labelVisibleChanged();
125 void penChanged();
127 void penChanged();
126 void brushChanged();
128 void brushChanged();
127 void labelBrushChanged();
129 void labelBrushChanged();
128 void labelFontChanged();
130 void labelFontChanged();
129 void percentageChanged();
131 void percentageChanged();
130 void startAngleChanged();
132 void startAngleChanged();
131 void angleSpanChanged();
133 void angleSpanChanged();
132 void colorChanged();
134 void colorChanged();
133 void borderColorChanged();
135 void borderColorChanged();
134 void borderWidthChanged();
136 void borderWidthChanged();
135 void labelColorChanged();
137 void labelColorChanged();
136
138
137 private:
139 private:
138 QPieSlicePrivate * const d_ptr;
140 QPieSlicePrivate * const d_ptr;
139 Q_DECLARE_PRIVATE(QPieSlice)
141 Q_DECLARE_PRIVATE(QPieSlice)
140 Q_DISABLE_COPY(QPieSlice)
142 Q_DISABLE_COPY(QPieSlice)
141 };
143 };
142
144
143 QTCOMMERCIALCHART_END_NAMESPACE
145 QTCOMMERCIALCHART_END_NAMESPACE
144
146
145 #endif // QPIESLICE_H
147 #endif // QPIESLICE_H
General Comments 0
You need to be logged in to leave comments. Login now