qboxplotseries.cpp
280 lines
| 7.9 KiB
| text/x-c
|
CppLexer
Mika Salmela
|
r2461 | /**************************************************************************** | ||
** | ||||
** Copyright (C) 2012 Digia Plc | ||||
** All rights reserved. | ||||
** For any questions to Digia, please use contact form at http://qt.digia.com | ||||
** | ||||
** This file is part of the Qt Commercial Charts Add-on. | ||||
** | ||||
** $QT_BEGIN_LICENSE$ | ||||
** Licensees holding valid Qt Commercial licenses may use this file in | ||||
** accordance with the Qt Commercial License Agreement provided with the | ||||
** Software or, alternatively, in accordance with the terms contained in | ||||
** a written agreement between you and Digia. | ||||
** | ||||
** If you have questions regarding the use of this file, please use | ||||
** contact form at http://qt.digia.com | ||||
** $QT_END_LICENSE$ | ||||
** | ||||
****************************************************************************/ | ||||
#include "qboxplotseries.h" | ||||
#include "qboxplotseries_p.h" | ||||
#include "qboxplotlegendmarker.h" | ||||
#include "boxplotchartitem_p.h" | ||||
#include "chartdataset_p.h" | ||||
#include "charttheme_p.h" | ||||
#include "qvalueaxis.h" | ||||
#include "charttheme_p.h" | ||||
#include "boxplotanimation_p.h" | ||||
#include "qchart_p.h" | ||||
#include <QDebug> | ||||
QTCOMMERCIALCHART_BEGIN_NAMESPACE | ||||
/*! | ||||
\class QBoxPlotSeries | ||||
\brief Series for creating stacked bar chart | ||||
\mainclass | ||||
QBoxPlotSeries represents a series of data shown as bars. The purpose of this class is to draw bars | ||||
as stacks, where bars in same category are stacked on top of each other. | ||||
QBoxPlotSeries groups the data from sets to categories, which are defined by QStringList. | ||||
See the \l {BoxPlotChart Example} {stacked bar chart example} to learn how to create a stacked bar chart. | ||||
\image examples_boxplotchart.png | ||||
\sa QBarSet, QPercentBarSeries, QAbstractBarSeries | ||||
*/ | ||||
/*! | ||||
\qmlclass BoxPlotSeries QBoxPlotSeries | ||||
\inherits AbstractBarSeries | ||||
The following QML shows how to create a simple stacked bar chart: | ||||
\snippet ../demos/qmlchart/qml/qmlchart/View7.qml 1 | ||||
\beginfloatleft | ||||
\image demos_qmlchart7.png | ||||
\endfloat | ||||
\clearfloat | ||||
*/ | ||||
/*! | ||||
Constructs empty QBoxPlotSeries. | ||||
QBoxPlotSeries is QObject which is a child of a \a parent. | ||||
*/ | ||||
QBoxPlotSeries::QBoxPlotSeries(QObject *parent) | ||||
: QAbstractBarSeries(*new QBoxPlotSeriesPrivate(this), parent) | ||||
{ | ||||
} | ||||
/*! | ||||
Destructor. Removes series from chart. | ||||
*/ | ||||
QBoxPlotSeries::~QBoxPlotSeries() | ||||
{ | ||||
qDebug() << "QBoxPlotSeries::~QBoxPlotSeries"; | ||||
Q_D(QBoxPlotSeries); | ||||
if (d->m_chart) | ||||
d->m_chart->removeSeries(this); | ||||
} | ||||
/*! | ||||
Returns QChartSeries::SeriesTypeBoxPlot. | ||||
*/ | ||||
QAbstractSeries::SeriesType QBoxPlotSeries::type() const | ||||
{ | ||||
return QAbstractSeries::SeriesTypeBoxPlot; | ||||
} | ||||
void QBoxPlotSeries::setBrush(const QBrush &brush) | ||||
{ | ||||
Q_D(QBoxPlotSeries); | ||||
if (d->m_brush != brush) { | ||||
d->m_brush = brush; | ||||
emit d->updated(); | ||||
} | ||||
} | ||||
QBrush QBoxPlotSeries::brush() const | ||||
{ | ||||
Q_D(const QBoxPlotSeries); | ||||
return d->m_brush; | ||||
} | ||||
void QBoxPlotSeries::setPen(const QPen &pen) | ||||
{ | ||||
Q_D(QBoxPlotSeries); | ||||
if (d->m_pen != pen) { | ||||
d->m_pen = pen; | ||||
emit d->updated(); | ||||
} | ||||
} | ||||
QPen QBoxPlotSeries::pen() const | ||||
{ | ||||
Q_D(const QBoxPlotSeries); | ||||
return d->m_pen; | ||||
} | ||||
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// | ||||
QBoxPlotSeriesPrivate::QBoxPlotSeriesPrivate(QBoxPlotSeries *q) | ||||
: QAbstractBarSeriesPrivate(q), | ||||
m_pen(QPen(Qt::NoPen)), | ||||
m_brush(QBrush(Qt::NoBrush)) | ||||
{ | ||||
} | ||||
QBoxPlotSeriesPrivate::~QBoxPlotSeriesPrivate() | ||||
{ | ||||
qDebug() << "QBoxPlotSeriesPrivate::~QBoxPlotSeriesPrivate()"; | ||||
disconnect(this, 0, 0, 0); | ||||
} | ||||
void QBoxPlotSeriesPrivate::initializeDomain() | ||||
{ | ||||
qreal minX(domain()->minX()); | ||||
qreal minY(domain()->minY()); | ||||
qreal maxX(domain()->maxX()); | ||||
qreal maxY(domain()->maxY()); | ||||
qreal x = categoryCount(); | ||||
minX = qMin(minX, - (qreal)0.5); | ||||
minY = qMin(minY, bottom()); | ||||
maxX = qMax(maxX, x - (qreal)0.5); | ||||
//maxY = qMax(maxY, top()); | ||||
maxY = qMax(maxY, max()); | ||||
domain()->setRange(minX, maxX, minY, maxY); | ||||
} | ||||
void QBoxPlotSeriesPrivate::initializeGraphics(QGraphicsItem* parent) | ||||
{ | ||||
Q_Q(QBoxPlotSeries); | ||||
BoxPlotChartItem *boxPlot = new BoxPlotChartItem(q,parent); | ||||
m_item.reset(boxPlot); | ||||
QAbstractSeriesPrivate::initializeGraphics(parent); | ||||
if (m_chart) { | ||||
connect(m_chart->d_ptr->m_dataset, SIGNAL(seriesAdded(QAbstractSeries*)), this, SLOT(handleSeriesChange(QAbstractSeries*)) ); | ||||
connect(m_chart->d_ptr->m_dataset, SIGNAL(seriesRemoved(QAbstractSeries*)), this, SLOT(handleSeriesRemove(QAbstractSeries*)) ); | ||||
QList<QAbstractSeries *> serieses = m_chart->series(); | ||||
boxPlot->m_seriesCount = serieses.count(); | ||||
// Tries to find this series from the Chart's list of serieses and deduce the index | ||||
int index = 0; | ||||
foreach (QAbstractSeries *s, serieses) { | ||||
if (q == static_cast<QBoxPlotSeries *>(s)) { | ||||
boxPlot->m_seriesIndex = index; | ||||
m_index = index; | ||||
} | ||||
index++; | ||||
} | ||||
} | ||||
// Make BoxPlotChartItem to instantiate box & whisker items | ||||
boxPlot->handleDataStructureChanged(); | ||||
} | ||||
void QBoxPlotSeriesPrivate::initializeTheme(int index, ChartTheme* theme, bool forced) | ||||
{ | ||||
Q_Q(QBoxPlotSeries); | ||||
const QList<QGradient> gradients = theme->seriesGradients(); | ||||
if (forced || m_brush == QBrush(Qt::NoBrush)) { | ||||
QColor brushColor = ChartThemeManager::colorAt(gradients.at(index % gradients.size()), 0.1); | ||||
q->setBrush(brushColor); | ||||
} | ||||
if (forced || m_pen == QPen(Qt::NoPen)) { | ||||
QPen pen; | ||||
pen.setColor(ChartThemeManager::colorAt(gradients.at(index % gradients.size()), 1.0)); | ||||
pen.setWidthF(1.0); | ||||
pen.setCosmetic(true); | ||||
q->setPen(pen); | ||||
} | ||||
} | ||||
void QBoxPlotSeriesPrivate::initializeAnimations(QtCommercialChart::QChart::AnimationOptions options) | ||||
{ | ||||
BoxPlotChartItem *item = static_cast<BoxPlotChartItem *>(m_item.data()); | ||||
Q_ASSERT(item); | ||||
if (options.testFlag(QChart::SeriesAnimations)) { | ||||
item->setAnimation(new BoxPlotAnimation(item)); | ||||
}else{ | ||||
item->setAnimation((BoxPlotAnimation *)0); | ||||
} | ||||
QAbstractSeriesPrivate::initializeAnimations(options); | ||||
} | ||||
QList<QLegendMarker*> QBoxPlotSeriesPrivate::createLegendMarkers(QLegend *legend) | ||||
{ | ||||
Q_Q(QBoxPlotSeries); | ||||
QList<QLegendMarker*> list; | ||||
return list << new QBoxPlotLegendMarker(q, legend); | ||||
} | ||||
void QBoxPlotSeriesPrivate::handleSeriesRemove(QAbstractSeries *series) | ||||
{ | ||||
qDebug() << "QBoxPlotSeriesPrivate::handleSeriesRemove"; | ||||
Q_Q(QBoxPlotSeries); | ||||
QBoxPlotSeries *removedSeries = static_cast<QBoxPlotSeries *>(series); | ||||
QObject::disconnect(m_chart->d_ptr->m_dataset, 0, removedSeries->d_func(), 0); | ||||
// Test if series removed is me, then don't do anything | ||||
if (q != removedSeries) { | ||||
BoxPlotChartItem *item = static_cast<BoxPlotChartItem *>(m_item.data()); | ||||
if (item) { | ||||
item->m_seriesCount = item->m_seriesCount - 1; | ||||
if (removedSeries->d_func()->m_index < m_index) { | ||||
m_index--; | ||||
item->m_seriesIndex = m_index; | ||||
} | ||||
item->handleDataStructureChanged(); | ||||
} | ||||
} | ||||
} | ||||
void QBoxPlotSeriesPrivate::handleSeriesChange(QAbstractSeries *series) | ||||
{ | ||||
Q_UNUSED(series); | ||||
Q_Q(QBoxPlotSeries); | ||||
BoxPlotChartItem *boxPlot = static_cast<BoxPlotChartItem *>(m_item.data()); | ||||
if (m_chart) { | ||||
QList<QAbstractSeries *> serieses = m_chart->series(); | ||||
boxPlot->m_seriesCount = serieses.count(); | ||||
// Tries to find this series from the Chart's list of serieses and deduce the index | ||||
int index = 0; | ||||
foreach (QAbstractSeries *s, serieses) { | ||||
if (q == static_cast<QBoxPlotSeries *>(s)) { | ||||
boxPlot->m_seriesIndex = index; | ||||
m_index = index; | ||||
} | ||||
index++; | ||||
} | ||||
} | ||||
boxPlot->handleDataStructureChanged(); | ||||
} | ||||
#include "moc_qboxplotseries.cpp" | ||||
#include "moc_qboxplotseries_p.cpp" | ||||
QTCOMMERCIALCHART_END_NAMESPACE | ||||