diff options
author | Miikka Heikkinen <miikka.heikkinen@qt.io> | 2016-09-29 13:48:09 +0300 |
---|---|---|
committer | Miikka Heikkinen <miikka.heikkinen@qt.io> | 2016-10-04 12:58:40 +0000 |
commit | 4e2698c9aee2594faaacb4d3f835e2189c7631ef (patch) | |
tree | 68177f4a6d0cf25515ee3d2984af589c8abca809 /src/charts/barchart/vertical/percent | |
parent | 3cb2c5e7572a75a4fae8883c9c0f3141cdf207b9 (diff) |
Add support for more than one bar series
Now charts properly positions bars if there are more than one bar
series in the chart. Theming was changed to account for more than
one bar series in the chart.
This patch also fixes various animation errors that were exposed
by adding/removing the series to/from an existing chart.
Task-number: QTBUG-52379
Change-Id: I4a8bc7e1675191ff87966ec4ca3d01e2b7cb815d
Reviewed-by: Tomi Korpipää <tomi.korpipaa@qt.io>
Reviewed-by: Miikka Heikkinen <miikka.heikkinen@qt.io>
Diffstat (limited to 'src/charts/barchart/vertical/percent')
-rw-r--r-- | src/charts/barchart/vertical/percent/percentbarchartitem.cpp | 86 | ||||
-rw-r--r-- | src/charts/barchart/vertical/percent/percentbarchartitem_p.h | 4 |
2 files changed, 55 insertions, 35 deletions
diff --git a/src/charts/barchart/vertical/percent/percentbarchartitem.cpp b/src/charts/barchart/vertical/percent/percentbarchartitem.cpp index 2cd06f51..95867c78 100644 --- a/src/charts/barchart/vertical/percent/percentbarchartitem.cpp +++ b/src/charts/barchart/vertical/percent/percentbarchartitem.cpp @@ -63,33 +63,30 @@ QString PercentBarChartItem::generateLabelText(int set, int category, qreal valu return valueLabel; } -void PercentBarChartItem::initializeLayout(int set, int category, int layoutIndex, - bool resetAnimation) +void PercentBarChartItem::initializeLayout(int set, int category, + int layoutIndex, bool resetAnimation) { Q_UNUSED(set) Q_UNUSED(resetAnimation) QRectF rect; - int previousSetIndex = layoutIndex - m_categoryCount; - if (previousSetIndex >= 0) { - rect = m_layout.at(previousSetIndex); + if (set > 0) { + QBarSet *barSet = m_series->barSets().at(set - 1); + Bar *bar = m_indexForBarMap.value(barSet).value(category); + rect = m_layout.at(bar->layoutIndex()); rect.setBottom(rect.top()); } else { QPointF topLeft; QPointF bottomRight; - qreal barWidth = m_series->d_func()->barWidth(); + const qreal barWidth = m_series->d_func()->barWidth() * m_seriesWidth; if (domain()->type() == AbstractDomain::XLogYDomain || domain()->type() == AbstractDomain::LogXLogYDomain) { - topLeft = domain()->calculateGeometryPoint( - QPointF(category - barWidth / 2, domain()->minY()), m_validData); - bottomRight = domain()->calculateGeometryPoint( - QPointF(category + barWidth / 2, domain()->minY()), m_validData); + topLeft = topLeftPoint(category, barWidth, domain()->minY()); + bottomRight = bottomRightPoint(category, barWidth, domain()->minY()); } else { - topLeft = domain()->calculateGeometryPoint( - QPointF(category - barWidth / 2, 0), m_validData); - bottomRight = domain()->calculateGeometryPoint( - QPointF(category + barWidth / 2, 0), m_validData); + topLeft = topLeftPoint(category, barWidth, 0.0); + bottomRight = bottomRightPoint(category, barWidth, 0.0); } if (m_validData) { rect.setTopLeft(topLeft); @@ -100,52 +97,73 @@ void PercentBarChartItem::initializeLayout(int set, int category, int layoutInde m_layout[layoutIndex] = rect.normalized(); } -void PercentBarChartItem::markLabelsDirty(QBarSet *barset, int visualIndex, int count) +void PercentBarChartItem::markLabelsDirty(QBarSet *barset, int index, int count) { Q_UNUSED(barset) // Percent series need to dirty all labels of the stack QList<QBarSet *> sets = m_barMap.keys(); for (int set = 0; set < sets.size(); set++) - AbstractBarChartItem::markLabelsDirty(sets.at(set), visualIndex, count); + AbstractBarChartItem::markLabelsDirty(sets.at(set), index, count); +} + +QPointF PercentBarChartItem::topLeftPoint(int category, qreal barWidth, qreal value) +{ + return domain()->calculateGeometryPoint( + QPointF(m_seriesPosAdjustment + category - (barWidth / 2.0), value), m_validData); +} + +QPointF PercentBarChartItem::bottomRightPoint(int category, qreal barWidth, qreal value) +{ + return domain()->calculateGeometryPoint( + QPointF(m_seriesPosAdjustment + category + (barWidth / 2.0), value), m_validData); } QVector<QRectF> PercentBarChartItem::calculateLayout() { QVector<QRectF> layout; - layout.reserve(m_layout.size()); + layout.resize(m_layout.size()); - // Use temporary qreals for accuracy - qreal setCount = m_series->count(); - qreal barWidth = m_series->d_func()->barWidth(); + const int setCount = m_series->count(); + const qreal barWidth = m_series->d_func()->barWidth() * m_seriesWidth; QVector<qreal> categorySums(m_categoryCount); QVector<qreal> tempSums(m_categoryCount, 0.0); + for (int category = 0; category < m_categoryCount; category++) categorySums[category] = m_series->d_func()->categorySum(category + m_firstCategory); + for (int set = 0; set < setCount; set++) { - const QBarSet *barSet = m_series->barSets().at(set); - for (int category = m_firstCategory; category <= m_lastCategory; category++) { + QBarSet *barSet = m_series->barSets().at(set); + const QList<Bar *> bars = m_barMap.value(barSet); + for (int i = 0; i < m_categoryCount; i++) { + Bar *bar = bars.at(i); + const int category = bar->index(); qreal &sum = tempSums[category - m_firstCategory]; const qreal &categorySum = categorySums.at(category - m_firstCategory); qreal value = barSet->at(category); QRectF rect; - qreal topY = 0; + qreal topY = 0.0; qreal newSum = value + sum; - if (newSum > 0) - topY = 100 * newSum / categorySum; - qreal bottomY = 0; - if (sum > 0) - bottomY = 100 * sum / categorySum; - QPointF topLeft = domain()->calculateGeometryPoint(QPointF(category - barWidth/2, topY), m_validData); + qreal bottomY = 0.0; + if (categorySum != 0.0) { + if (newSum > 0.0) + topY = 100.0 * newSum / categorySum; + if (sum > 0.0) + bottomY = 100.0 * sum / categorySum; + } + QPointF topLeft = topLeftPoint(category, barWidth, topY); QPointF bottomRight; - if (domain()->type() == AbstractDomain::XLogYDomain || domain()->type() == AbstractDomain::LogXLogYDomain) - bottomRight = domain()->calculateGeometryPoint(QPointF(category + barWidth/2, set ? bottomY : domain()->minY()), m_validData); - else - bottomRight = domain()->calculateGeometryPoint(QPointF(category + barWidth/2, set ? bottomY : 0), m_validData); + if (domain()->type() == AbstractDomain::XLogYDomain + || domain()->type() == AbstractDomain::LogXLogYDomain) { + bottomRight = bottomRightPoint(category, barWidth, + set ? bottomY : domain()->minY()); + } else { + bottomRight = bottomRightPoint(category, barWidth, bottomY); + } rect.setTopLeft(topLeft); rect.setBottomRight(bottomRight); - layout.append(rect.normalized()); + layout[bar->layoutIndex()] = rect.normalized(); sum = newSum; } } diff --git a/src/charts/barchart/vertical/percent/percentbarchartitem_p.h b/src/charts/barchart/vertical/percent/percentbarchartitem_p.h index c46697ef..80016613 100644 --- a/src/charts/barchart/vertical/percent/percentbarchartitem_p.h +++ b/src/charts/barchart/vertical/percent/percentbarchartitem_p.h @@ -61,7 +61,9 @@ private Q_SLOTS: private: virtual QVector<QRectF> calculateLayout(); void initializeLayout(int set, int category, int layoutIndex, bool resetAnimation); - void markLabelsDirty(QBarSet *barset, int visualIndex, int count); + void markLabelsDirty(QBarSet *barset, int index, int count); + QPointF topLeftPoint(int category, qreal barWidth, qreal value); + QPointF bottomRightPoint(int category, qreal barWidth, qreal value); }; QT_CHARTS_END_NAMESPACE |