##// END OF EJS Templates
Refactoring pie series and animations.
Jani Honkonen -
r621:f4b980d7defa
parent child
Show More
@@ -351,6 +351,7 public:
351 m_endAngle->setSingleStep(1);
351 m_endAngle->setSingleStep(1);
352
352
353 QPushButton *addSlice = new QPushButton("Add slice");
353 QPushButton *addSlice = new QPushButton("Add slice");
354 QPushButton *insertSlice = new QPushButton("Insert slice");
354
355
355 QFormLayout* seriesSettingsLayout = new QFormLayout();
356 QFormLayout* seriesSettingsLayout = new QFormLayout();
356 seriesSettingsLayout->addRow("Horizontal position", m_hPosition);
357 seriesSettingsLayout->addRow("Horizontal position", m_hPosition);
@@ -359,6 +360,7 public:
359 seriesSettingsLayout->addRow("Start angle", m_startAngle);
360 seriesSettingsLayout->addRow("Start angle", m_startAngle);
360 seriesSettingsLayout->addRow("End angle", m_endAngle);
361 seriesSettingsLayout->addRow("End angle", m_endAngle);
361 seriesSettingsLayout->addRow(addSlice);
362 seriesSettingsLayout->addRow(addSlice);
363 seriesSettingsLayout->addRow(insertSlice);
362 QGroupBox* seriesSettings = new QGroupBox("Series");
364 QGroupBox* seriesSettings = new QGroupBox("Series");
363 seriesSettings->setLayout(seriesSettingsLayout);
365 seriesSettings->setLayout(seriesSettingsLayout);
364
366
@@ -368,6 +370,7 public:
368 connect(m_startAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
370 connect(m_startAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
369 connect(m_endAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
371 connect(m_endAngle, SIGNAL(valueChanged(double)), this, SLOT(updateSerieSettings()));
370 connect(addSlice, SIGNAL(clicked()), this, SLOT(addSlice()));
372 connect(addSlice, SIGNAL(clicked()), this, SLOT(addSlice()));
373 connect(insertSlice, SIGNAL(clicked()), this, SLOT(insertSlice()));
371
374
372 // slice settings
375 // slice settings
373 m_sliceName = new QLabel("<click a slice>");
376 m_sliceName = new QLabel("<click a slice>");
@@ -526,6 +529,16 public Q_SLOTS:
526 *m_series << new CustomSlice(10.0, "Slice " + QString::number(m_series->count()));
529 *m_series << new CustomSlice(10.0, "Slice " + QString::number(m_series->count()));
527 }
530 }
528
531
532 void insertSlice()
533 {
534 if (!m_slice)
535 return;
536
537 int i = m_series->slices().indexOf(m_slice);
538
539 m_series->insert(i, new CustomSlice(10.0, "Slice " + QString::number(m_series->count())));
540 }
541
529 void removeSlice()
542 void removeSlice()
530 {
543 {
531 if (!m_slice)
544 if (!m_slice)
@@ -78,6 +78,7 int main(int argc, char *argv[])
78 DrilldownChart* drilldownChart = new DrilldownChart(&window);
78 DrilldownChart* drilldownChart = new DrilldownChart(&window);
79 drilldownChart->setRenderHint(QPainter::Antialiasing);
79 drilldownChart->setRenderHint(QPainter::Antialiasing);
80 drilldownChart->setChartTheme(QChart::ChartThemeVanilla);
80 drilldownChart->setChartTheme(QChart::ChartThemeVanilla);
81 drilldownChart->setAnimationOptions(QChart::AllAnimations);
81
82
82 QPieSeries* yearSeries = new QPieSeries(&window);
83 QPieSeries* yearSeries = new QPieSeries(&window);
83 yearSeries->setTitle("Sales by year - All");
84 yearSeries->setTitle("Sales by year - All");
@@ -184,11 +184,25 void ChartAnimator::updateLayout(XYChartItem* item, QVector<QPointF>& newPoints)
184 QTimer::singleShot(0,animation,SLOT(start()));
184 QTimer::singleShot(0,animation,SLOT(start()));
185 }
185 }
186
186
187 void ChartAnimator::applyLayout(PieChartItem* item, QVector<PieSliceLayout> &layout)
187 void ChartAnimator::addAnimation(PieChartItem* item, QPieSlice *slice, PieSliceLayout &layout)
188 {
188 {
189 PieAnimation* animation = static_cast<PieAnimation*>(m_animations.value(item));
189 PieAnimation* animation = static_cast<PieAnimation*>(m_animations.value(item));
190 Q_ASSERT(animation);
190 Q_ASSERT(animation);
191 animation->setValues(layout);
191 animation->addSlice(slice, layout);
192 }
193
194 void ChartAnimator::removeAnimation(PieChartItem* item, QPieSlice *slice)
195 {
196 PieAnimation* animation = static_cast<PieAnimation*>(m_animations.value(item));
197 Q_ASSERT(animation);
198 animation->removeSlice(slice);
199 }
200
201 void ChartAnimator::updateLayout(PieChartItem* item, QVector<PieSliceLayout> &layout)
202 {
203 PieAnimation* animation = static_cast<PieAnimation*>(m_animations.value(item));
204 Q_ASSERT(animation);
205 animation->updateValues(layout);
192 }
206 }
193
207
194 void ChartAnimator::updateLayout(PieChartItem* item, PieSliceLayout &layout)
208 void ChartAnimator::updateLayout(PieChartItem* item, PieSliceLayout &layout)
@@ -32,7 +32,9 public:
32 void updateLayout(XYChartItem* item, QVector<QPointF>& layout);
32 void updateLayout(XYChartItem* item, QVector<QPointF>& layout);
33 void applyLayout(AxisItem* item, QVector<qreal>& layout);
33 void applyLayout(AxisItem* item, QVector<qreal>& layout);
34
34
35 void applyLayout(PieChartItem* item, QVector<PieSliceLayout> &layout);
35 void addAnimation(PieChartItem* item, QPieSlice *slice, PieSliceLayout &layout);
36 void removeAnimation(PieChartItem* item, QPieSlice *slice);
37 void updateLayout(PieChartItem* item, QVector<PieSliceLayout> &layout);
36 void updateLayout(PieChartItem* item, PieSliceLayout &layout);
38 void updateLayout(PieChartItem* item, PieSliceLayout &layout);
37
39
38 void setState(State state,const QPointF& point = QPointF());
40 void setState(State state,const QPointF& point = QPointF());
@@ -16,63 +16,58 PieAnimation::~PieAnimation()
16 {
16 {
17 }
17 }
18
18
19 void PieAnimation::setValues(QVector<PieSliceLayout>& newValues)
19 void PieAnimation::updateValues(QVector<PieSliceLayout>& newValues)
20 {
20 {
21 PieSliceAnimation *animation = 0;
21 foreach (PieSliceLayout endLayout, newValues)
22 updateValue(endLayout);
23 }
22
24
23 foreach (PieSliceLayout endLayout, newValues) {
25 void PieAnimation::updateValue(PieSliceLayout& endLayout)
24 animation = m_animations.value(endLayout.m_data);
26 {
25 if (animation) {
27 PieSliceAnimation *animation = m_animations.value(endLayout.m_data);
26 // existing slice
28 Q_ASSERT(animation);
27 animation->stop();
29 animation->stop();
30
28 animation->updateValue(endLayout);
31 animation->updateValue(endLayout);
29 } else {
32 animation->setDuration(1000);
30 // new slice
33 animation->setEasingCurve(QEasingCurve::OutQuart);
31 animation = new PieSliceAnimation(m_item);
34
32 m_animations.insert(endLayout.m_data, animation);
35 QTimer::singleShot(0, animation, SLOT(start()));
36 }
37
38 void PieAnimation::addSlice(QPieSlice *slice, PieSliceLayout endLayout)
39 {
40 PieSliceAnimation *animation = new PieSliceAnimation(m_item);
41 m_animations.insert(slice, animation);
42
33 PieSliceLayout startLayout = endLayout;
43 PieSliceLayout startLayout = endLayout;
34 startLayout.m_radius = 0;
44 startLayout.m_radius = 0;
35 //startLayout.m_startAngle = 0;
45 startLayout.m_startAngle = endLayout.m_startAngle + (endLayout.m_angleSpan/2);
36 //startLayout.m_angleSpan = 0;
46 startLayout.m_angleSpan = 0;
37 animation->setValue(startLayout, endLayout);
47 animation->setValue(startLayout, endLayout);
38 }
48
39 animation->setDuration(1000);
49 animation->setDuration(1000);
40 animation->setEasingCurve(QEasingCurve::OutQuart);
50 animation->setEasingCurve(QEasingCurve::OutQuart);
41 QTimer::singleShot(0, animation, SLOT(start())); // TODO: use sequential animation?
51 QTimer::singleShot(0, animation, SLOT(start()));
42 }
52 }
43
53
44 foreach (QPieSlice *s, m_animations.keys()) {
54 void PieAnimation::removeSlice(QPieSlice *slice)
45 bool isFound = false;
55 {
46 foreach (PieSliceLayout layout, newValues) {
56 PieSliceAnimation *animation = m_animations.value(slice);
47 if (s == layout.m_data)
57 Q_ASSERT(animation);
48 isFound = true;
49 }
50 if (!isFound) {
51 // slice has been deleted
52 animation = m_animations.value(s);
53 animation->stop();
58 animation->stop();
54 PieSliceLayout endLayout = m_animations.value(s)->currentSliceValue();
59
60 PieSliceLayout endLayout = animation->currentSliceValue();
55 endLayout.m_radius = 0;
61 endLayout.m_radius = 0;
56 // TODO: find the actual angle where this slice disappears
62 // TODO: find the actual angle where this slice disappears
57 endLayout.m_startAngle = endLayout.m_startAngle + endLayout.m_angleSpan;
63 endLayout.m_startAngle = endLayout.m_startAngle + endLayout.m_angleSpan;
58 endLayout.m_angleSpan = 0;
64 endLayout.m_angleSpan = 0;
59 animation->updateValue(endLayout);
60 animation->setDuration(1000);
61 animation->setEasingCurve(QEasingCurve::OutQuart);
62 connect(animation, SIGNAL(finished()), this, SLOT(destroySliceAnimationComplete()));
63 QTimer::singleShot(0, animation, SLOT(start()));
64 }
65 }
66 }
67
65
68 void PieAnimation::updateValue(PieSliceLayout& endLayout)
69 {
70 PieSliceAnimation *animation = m_animations.value(endLayout.m_data);
71 Q_ASSERT(animation);
72 animation->stop();
73 animation->updateValue(endLayout);
66 animation->updateValue(endLayout);
74 animation->setDuration(1000);
67 animation->setDuration(1000);
75 animation->setEasingCurve(QEasingCurve::OutQuart);
68 animation->setEasingCurve(QEasingCurve::OutQuart);
69
70 connect(animation, SIGNAL(finished()), this, SLOT(destroySliceAnimationComplete()));
76 QTimer::singleShot(0, animation, SLOT(start()));
71 QTimer::singleShot(0, animation, SLOT(start()));
77 }
72 }
78
73
@@ -16,8 +16,10 class PieAnimation : public ChartAnimation
16 public:
16 public:
17 PieAnimation(PieChartItem *item);
17 PieAnimation(PieChartItem *item);
18 ~PieAnimation();
18 ~PieAnimation();
19 void setValues(QVector<PieSliceLayout>& newValues);
19 void updateValues(QVector<PieSliceLayout>& newValues);
20 void updateValue(PieSliceLayout& newValue);
20 void updateValue(PieSliceLayout& newValue);
21 void addSlice(QPieSlice *slice, PieSliceLayout endLayout);
22 void removeSlice(QPieSlice *slice);
21
23
22 public: // from QVariantAnimation
24 public: // from QVariantAnimation
23 void updateCurrentValue(const QVariant &value);
25 void updateCurrentValue(const QVariant &value);
@@ -6,7 +6,7
6 #include "chartanimator_p.h"
6 #include "chartanimator_p.h"
7 #include <QDebug>
7 #include <QDebug>
8 #include <QPainter>
8 #include <QPainter>
9
9 #include <QTimer>
10
10
11 QTCOMMERCIALCHART_BEGIN_NAMESPACE
11 QTCOMMERCIALCHART_BEGIN_NAMESPACE
12
12
@@ -15,7 +15,12 PieChartItem::PieChartItem(QGraphicsItem *parent, QPieSeries *series)
15 m_series(series)
15 m_series(series)
16 {
16 {
17 Q_ASSERT(series);
17 Q_ASSERT(series);
18 connect(series, SIGNAL(changed()), this, SLOT(handleSeriesChanged()));
18 connect(series, SIGNAL(added(QList<QPieSlice*>)), this, SLOT(handleSlicesAdded(QList<QPieSlice*>)));
19 connect(series, SIGNAL(removed(QList<QPieSlice*>)), this, SLOT(handleSlicesRemoved(QList<QPieSlice*>)));
20 connect(series, SIGNAL(piePositionChanged()), this, SLOT(handlePieLayoutChanged()));
21 connect(series, SIGNAL(pieSizeChanged()), this, SLOT(handlePieLayoutChanged()));
22
23 QTimer::singleShot(0, this, SLOT(initialize()));
19
24
20 // Note: the following does not affect as long as the item does not have anything to paint
25 // Note: the following does not affect as long as the item does not have anything to paint
21 setZValue(ChartPresenter::PieSeriesZValue);
26 setZValue(ChartPresenter::PieSeriesZValue);
@@ -35,7 +40,41 void PieChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QW
35 //painter->drawRect(m_debugRect);
40 //painter->drawRect(m_debugRect);
36 }
41 }
37
42
38 void PieChartItem::handleSeriesChanged()
43 void PieChartItem::initialize()
44 {
45 handleSlicesAdded(m_series->m_slices);
46 }
47
48 void PieChartItem::handleSlicesAdded(QList<QPieSlice*> slices)
49 {
50 foreach (QPieSlice *s, slices) {
51 PieSlice* slice = new PieSlice(this);
52 m_slices.insert(s, slice);
53 connect(s, SIGNAL(changed()), this, SLOT(handleSliceChanged()));
54 connect(slice, SIGNAL(clicked()), s, SIGNAL(clicked()));
55 connect(slice, SIGNAL(hoverEnter()), s, SIGNAL(hoverEnter()));
56 connect(slice, SIGNAL(hoverLeave()), s, SIGNAL(hoverLeave()));
57
58 PieSliceLayout layout = calculateSliceLayout(s);
59
60 if (m_animator)
61 m_animator->addAnimation(this, s, layout);
62 else
63 setLayout(layout);
64 }
65 }
66
67 void PieChartItem::handleSlicesRemoved(QList<QPieSlice*> slices)
68 {
69 foreach (QPieSlice *s, slices) {
70 if (m_animator)
71 m_animator->removeAnimation(this, s);
72 else
73 destroySlice(s);
74 }
75 }
76
77 void PieChartItem::handlePieLayoutChanged()
39 {
78 {
40 QVector<PieSliceLayout> layout = calculateLayout();
79 QVector<PieSliceLayout> layout = calculateLayout();
41 applyLayout(layout);
80 applyLayout(layout);
@@ -46,15 +85,8 void PieChartItem::handleSliceChanged()
46 {
85 {
47 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
86 QPieSlice* slice = qobject_cast<QPieSlice *>(sender());
48 Q_ASSERT(m_slices.contains(slice));
87 Q_ASSERT(m_slices.contains(slice));
49
88 PieSliceLayout layout = calculateSliceLayout(slice);
50 //qDebug() << "PieChartItem::handleSliceChanged" << slice->label();
89 updateLayout(layout);
51
52 // TODO: Optimize. No need to calculate everything.
53 QVector<PieSliceLayout> layout = calculateLayout();
54 foreach (PieSliceLayout sl, layout) {
55 if (sl.m_data == slice)
56 updateLayout(sl);
57 }
58 update();
90 update();
59 }
91 }
60
92
@@ -67,45 +99,50 void PieChartItem::handleGeometryChanged(const QRectF& rect)
67 {
99 {
68 prepareGeometryChange();
100 prepareGeometryChange();
69 m_rect = rect;
101 m_rect = rect;
70 QVector<PieSliceLayout> sliceLayout = calculateLayout();
102 handlePieLayoutChanged();
71 applyLayout(sliceLayout);
72 update();
73 }
103 }
74
104
75
105 void PieChartItem::calculatePieLayout()
76 QVector<PieSliceLayout> PieChartItem::calculateLayout()
77 {
106 {
78 // find pie center coordinates
107 // find pie center coordinates
79 QPointF center;
108 m_pieCenter.setX(m_rect.left() + (m_rect.width() * m_series->pieHorizontalPosition()));
80 center.setX(m_rect.left() + (m_rect.width() * m_series->pieHorizontalPosition()));
109 m_pieCenter.setY(m_rect.top() + (m_rect.height() * m_series->pieVerticalPosition()));
81 center.setY(m_rect.top() + (m_rect.height() * m_series->pieVerticalPosition()));
82
110
83 // find maximum radius for pie
111 // find maximum radius for pie
84 qreal radius = m_rect.height() / 2;
112 m_pieRadius = m_rect.height() / 2;
85 if (m_rect.width() < m_rect.height())
113 if (m_rect.width() < m_rect.height())
86 radius = m_rect.width() / 2;
114 m_pieRadius = m_rect.width() / 2;
87
115
88 // apply size factor
116 // apply size factor
89 radius *= m_series->pieSize();
117 m_pieRadius *= m_series->pieSize();
118 }
90
119
91 QVector<PieSliceLayout> layout;
120 PieSliceLayout PieChartItem::calculateSliceLayout(QPieSlice *slice)
92 foreach (QPieSlice* s, m_series->slices()) {
121 {
93 PieSliceLayout sliceLayout;
122 PieSliceLayout sliceLayout;
94 sliceLayout.m_data = s;
123 sliceLayout.m_data = slice;
95 sliceLayout.m_center = PieSlice::sliceCenter(center, radius, s);
124 sliceLayout.m_center = PieSlice::sliceCenter(m_pieCenter, m_pieRadius, slice);
96 sliceLayout.m_radius = radius;
125 sliceLayout.m_radius = m_pieRadius;
97 sliceLayout.m_startAngle = s->startAngle();
126 sliceLayout.m_startAngle = slice->startAngle();
98 sliceLayout.m_angleSpan = s->m_angleSpan;
127 sliceLayout.m_angleSpan = slice->m_angleSpan;
99 layout << sliceLayout;
128 return sliceLayout;
100 }
129 }
101
130
131 QVector<PieSliceLayout> PieChartItem::calculateLayout()
132 {
133 calculatePieLayout();
134 QVector<PieSliceLayout> layout;
135 foreach (QPieSlice* s, m_series->slices()) {
136 if (m_slices.contains(s)) // calculate layout only for those slices that are already visible
137 layout << calculateSliceLayout(s);
138 }
102 return layout;
139 return layout;
103 }
140 }
104
141
105 void PieChartItem::applyLayout(QVector<PieSliceLayout> &layout)
142 void PieChartItem::applyLayout(QVector<PieSliceLayout> &layout)
106 {
143 {
107 if (m_animator)
144 if (m_animator)
108 m_animator->applyLayout(this, layout);
145 m_animator->updateLayout(this, layout);
109 else
146 else
110 setLayout(layout);
147 setLayout(layout);
111 }
148 }
@@ -121,53 +158,20 void PieChartItem::updateLayout(PieSliceLayout &layout)
121 void PieChartItem::setLayout(QVector<PieSliceLayout> &layout)
158 void PieChartItem::setLayout(QVector<PieSliceLayout> &layout)
122 {
159 {
123 foreach (PieSliceLayout l, layout) {
160 foreach (PieSliceLayout l, layout) {
124
125 // find slice
126 PieSlice *slice = m_slices.value(l.m_data);
161 PieSlice *slice = m_slices.value(l.m_data);
127 if (!slice) {
162 Q_ASSERT(slice);
128 // add a new slice
129 slice = new PieSlice(this);
130 m_slices.insert(l.m_data, slice);
131
132 // connect signals
133 connect(l.m_data, SIGNAL(changed()), this, SLOT(handleSliceChanged()));
134 connect(slice, SIGNAL(clicked()), l.m_data, SIGNAL(clicked()));
135 connect(slice, SIGNAL(hoverEnter()), l.m_data, SIGNAL(hoverEnter()));
136 connect(slice, SIGNAL(hoverLeave()), l.m_data, SIGNAL(hoverLeave()));
137 }
138
139 // update
140 slice->setLayout(l);
163 slice->setLayout(l);
164 slice->updateData(l.m_data);
141 slice->updateGeometry();
165 slice->updateGeometry();
142 slice->update();
166 slice->update();
143 }
167 }
144
145 // delete slices
146 foreach (QPieSlice *s, m_slices.keys()) {
147
148 bool found = false;
149 foreach (PieSliceLayout l, layout) {
150 if (l.m_data == s)
151 found = true;
152 }
153
154 if (!found)
155 destroySlice(s);
156 }
157 }
168 }
158
169
159 void PieChartItem::setLayout(PieSliceLayout &layout)
170 void PieChartItem::setLayout(PieSliceLayout &layout)
160 {
171 {
161 // find slice
172 // find slice
162 PieSlice *slice = m_slices.value(layout.m_data);
173 PieSlice *slice = m_slices.value(layout.m_data);
163 if (!slice) {
174 Q_ASSERT(slice);
164 slice = new PieSlice(this);
165 m_slices.insert(layout.m_data, slice);
166 connect(layout.m_data, SIGNAL(changed()), this, SLOT(handleSliceChanged()));
167 connect(slice, SIGNAL(clicked()), layout.m_data, SIGNAL(clicked()));
168 connect(slice, SIGNAL(hoverEnter()), layout.m_data, SIGNAL(hoverEnter()));
169 connect(slice, SIGNAL(hoverLeave()), layout.m_data, SIGNAL(hoverLeave()));
170 }
171 slice->setLayout(layout);
175 slice->setLayout(layout);
172 if (m_series->m_slices.contains(layout.m_data)) // Slice has been deleted if not found. Animations ongoing...
176 if (m_series->m_slices.contains(layout.m_data)) // Slice has been deleted if not found. Animations ongoing...
173 slice->updateData(layout.m_data);
177 slice->updateData(layout.m_data);
@@ -23,12 +23,17 public: // from QGraphicsItem
23 void paint(QPainter *, const QStyleOptionGraphicsItem *, QWidget *);
23 void paint(QPainter *, const QStyleOptionGraphicsItem *, QWidget *);
24
24
25 public Q_SLOTS:
25 public Q_SLOTS:
26 void handleSeriesChanged();
26 void initialize();
27 void handleSlicesAdded(QList<QPieSlice*> slices);
28 void handleSlicesRemoved(QList<QPieSlice*> slices);
29 void handlePieLayoutChanged();
27 void handleSliceChanged();
30 void handleSliceChanged();
28 void handleDomainChanged(qreal, qreal, qreal, qreal);
31 void handleDomainChanged(qreal, qreal, qreal, qreal);
29 void handleGeometryChanged(const QRectF& rect);
32 void handleGeometryChanged(const QRectF& rect);
30
33
31 public:
34 public:
35 void calculatePieLayout();
36 PieSliceLayout calculateSliceLayout(QPieSlice *slice);
32 QVector<PieSliceLayout> calculateLayout();
37 QVector<PieSliceLayout> calculateLayout();
33 void applyLayout(QVector<PieSliceLayout> &layout);
38 void applyLayout(QVector<PieSliceLayout> &layout);
34 void updateLayout(PieSliceLayout &layout);
39 void updateLayout(PieSliceLayout &layout);
@@ -39,7 +39,7 PieSlice::~PieSlice()
39
39
40 QRectF PieSlice::boundingRect() const
40 QRectF PieSlice::boundingRect() const
41 {
41 {
42 return m_slicePath.boundingRect().united(m_labelTextRect);
42 return m_boundingRect;
43 }
43 }
44
44
45 QPainterPath PieSlice::shape() const
45 QPainterPath PieSlice::shape() const
@@ -112,7 +112,8 void PieSlice::updateGeometry()
112 // update text position
112 // update text position
113 m_labelTextRect.moveBottomLeft(labelTextStart);
113 m_labelTextRect.moveBottomLeft(labelTextStart);
114
114
115 //qDebug() << "PieSlice::updateGeometry" << m_labelText << boundingRect() << m_startAngle << m_startAngle + m_angleSpan;
115 // update bounding rect
116 m_boundingRect = m_slicePath.boundingRect().united(m_labelArmPath.boundingRect()).united(m_labelTextRect);
116 }
117 }
117
118
118 void PieSlice::updateData(const QPieSlice* sliceData)
119 void PieSlice::updateData(const QPieSlice* sliceData)
@@ -58,6 +58,7 public:
58
58
59 private:
59 private:
60 PieSliceLayout m_layout;
60 PieSliceLayout m_layout;
61 QRectF m_boundingRect;
61
62
62 QPainterPath m_slicePath;
63 QPainterPath m_slicePath;
63 bool m_isExploded;
64 bool m_isExploded;
@@ -77,7 +77,7 void QPieSeries::add(QList<QPieSlice*> slices)
77 connect(s, SIGNAL(hoverLeave()), this, SLOT(sliceHoverLeave()));
77 connect(s, SIGNAL(hoverLeave()), this, SLOT(sliceHoverLeave()));
78 }
78 }
79
79
80 emit changed();
80 emit added(slices);
81 }
81 }
82
82
83 /*!
83 /*!
@@ -124,7 +124,7 void QPieSeries::insert(int i, QPieSlice* slice)
124 connect(slice, SIGNAL(hoverEnter()), this, SLOT(sliceHoverEnter()));
124 connect(slice, SIGNAL(hoverEnter()), this, SLOT(sliceHoverEnter()));
125 connect(slice, SIGNAL(hoverLeave()), this, SLOT(sliceHoverLeave()));
125 connect(slice, SIGNAL(hoverLeave()), this, SLOT(sliceHoverLeave()));
126
126
127 emit changed();
127 emit added(QList<QPieSlice*>() << slice);
128 }
128 }
129
129
130 /*!
130 /*!
@@ -138,10 +138,11 void QPieSeries::remove(QPieSlice* slice)
138 Q_ASSERT(0); // TODO: how should this be reported?
138 Q_ASSERT(0); // TODO: how should this be reported?
139 return;
139 return;
140 }
140 }
141 emit changed();
142
141
143 updateDerivativeData();
142 updateDerivativeData();
144
143
144 emit removed(QList<QPieSlice*>() << slice);
145
145 delete slice;
146 delete slice;
146 slice = NULL;
147 slice = NULL;
147 }
148 }
@@ -154,14 +155,15 void QPieSeries::clear()
154 if (m_slices.count() == 0)
155 if (m_slices.count() == 0)
155 return;
156 return;
156
157
158 QList<QPieSlice*> slices = m_slices;
157 foreach (QPieSlice* s, m_slices) {
159 foreach (QPieSlice* s, m_slices) {
158 m_slices.removeOne(s);
160 m_slices.removeOne(s);
159 delete s;
161 delete s;
160 }
162 }
161
163
162 emit changed();
163
164 updateDerivativeData();
164 updateDerivativeData();
165
166 emit removed(slices);
165 }
167 }
166
168
167 /*!
169 /*!
@@ -173,6 +175,14 int QPieSeries::count() const
173 }
175 }
174
176
175 /*!
177 /*!
178 Returns true is the series is empty.
179 */
180 bool QPieSeries::isEmpty() const
181 {
182 return m_slices.isEmpty();
183 }
184
185 /*!
176 Returns a list of slices that belong to this series.
186 Returns a list of slices that belong to this series.
177 */
187 */
178 QList<QPieSlice*> QPieSeries::slices() const
188 QList<QPieSlice*> QPieSeries::slices() const
@@ -203,7 +213,7 void QPieSeries::setPiePosition(qreal relativeHorizontalPosition, qreal relative
203 if (m_pieRelativeHorPos != relativeHorizontalPosition || m_pieRelativeVerPos != relativeVerticalPosition) {
213 if (m_pieRelativeHorPos != relativeHorizontalPosition || m_pieRelativeVerPos != relativeVerticalPosition) {
204 m_pieRelativeHorPos = relativeHorizontalPosition;
214 m_pieRelativeHorPos = relativeHorizontalPosition;
205 m_pieRelativeVerPos = relativeVerticalPosition;
215 m_pieRelativeVerPos = relativeVerticalPosition;
206 emit changed();
216 emit piePositionChanged();
207 }
217 }
208 }
218 }
209
219
@@ -257,7 +267,7 void QPieSeries::setPieSize(qreal relativeSize)
257
267
258 if (m_pieRelativeSize != relativeSize) {
268 if (m_pieRelativeSize != relativeSize) {
259 m_pieRelativeSize = relativeSize;
269 m_pieRelativeSize = relativeSize;
260 emit changed();
270 emit pieSizeChanged();
261 }
271 }
262 }
272 }
263
273
@@ -427,13 +437,9 void QPieSeries::updateDerivativeData()
427 foreach (QPieSlice* s, m_slices)
437 foreach (QPieSlice* s, m_slices)
428 m_total += s->value();
438 m_total += s->value();
429
439
430 // TODO: emit totalChanged?
440 // nothing to show..
431
441 if (m_total == 0)
432 // we must have some values
442 return;
433 if (m_total == 0) {
434 qDebug() << "QPieSeries::updateDerivativeData() total == 0";
435 Q_ASSERT(m_total > 0); // TODO: is this the correct way to handle this?
436 }
437
443
438 // update slice attributes
444 // update slice attributes
439 qreal sliceAngle = m_pieStartAngle;
445 qreal sliceAngle = m_pieStartAngle;
@@ -465,6 +471,7 void QPieSeries::updateDerivativeData()
465 changed << s;
471 changed << s;
466 }
472 }
467
473
474 // emit signals
468 foreach (QPieSlice* s, changed)
475 foreach (QPieSlice* s, changed)
469 emit s->changed();
476 emit s->changed();
470 }
477 }
@@ -33,6 +33,7 public:
33
33
34 // calculated data
34 // calculated data
35 int count() const;
35 int count() const;
36 bool isEmpty() const;
36 qreal total() const;
37 qreal total() const;
37
38
38 // pie customization
39 // pie customization
@@ -70,7 +71,12 Q_SIGNALS:
70 void clicked(QPieSlice* slice);
71 void clicked(QPieSlice* slice);
71 void hoverEnter(QPieSlice* slice);
72 void hoverEnter(QPieSlice* slice);
72 void hoverLeave(QPieSlice* slice);
73 void hoverLeave(QPieSlice* slice);
73 void changed(); // TODO: hide this in PIMPL
74
75 // TODO: hide these in PIMPL
76 void added(QList<QPieSlice*> slices);
77 void removed(QList<QPieSlice*> slices);
78 void piePositionChanged();
79 void pieSizeChanged();
74
80
75 private Q_SLOTS: // TODO: should be private and not visible in the interface at all
81 private Q_SLOTS: // TODO: should be private and not visible in the interface at all
76 void sliceChanged();
82 void sliceChanged();
General Comments 0
You need to be logged in to leave comments. Login now