Scatter series marker visuals

This commit is contained in:
Tero Ahola 2012-02-15 21:42:44 +02:00
parent c7a6b06985
commit 3f425cc482
8 changed files with 133 additions and 48 deletions

View File

@ -14,20 +14,38 @@ int main(int argc, char *argv[])
// Create chart widget
QChartView *chartWidget = new QChartView();
// Create scatter series with simple test data
// Add scatter series with simple test data
QScatterSeries *scatter = new QScatterSeries();
*scatter << QPointF(0.5, 2.0)
<< QPointF(1.0, 2.5)
<< QPointF(1.5, 2.0)
<< QPointF(2.0, 2.5);
*scatter << QPointF(0.5, 5.0)
<< QPointF(1.0, 4.5)
<< QPointF(1.0, 5.5)
<< QPointF(1.5, 5.0)
<< QPointF(2.0, 4.5)
<< QPointF(2.0, 5.5)
<< QPointF(2.5, 5.0);
chartWidget->addSeries(scatter);
// Add another scatter series with more complex data with random component
// Add another scatter series
// - more data with random component
QScatterSeries *scatter2 = new QScatterSeries();
for (qreal i(0.0); i < 20; i += 0.5)
for (qreal i(0.0); i < 20; i += 0.05) {
(*scatter2) << QPointF(i + (qreal)(rand() % 100) / 100.0,
i + (qreal)(rand() % 100) / 100.0);
i + (qreal)(rand() % 100) / 100.0);
}
chartWidget->addSeries(scatter2);
// Custom pen and brush (not those defined by the chart theme)
// - uses opaque color
QColor color("#2685BF");
color.setAlpha(80);
QBrush brush(Qt::SolidPattern);
brush.setColor(color);
scatter2->setMarkerBrush(brush);
QPen pen;
pen.setColor(color);
pen.setWidth(2);
scatter2->setMarkerPen(pen);
// use a rectangle as the marker shape
scatter2->setMarkerShape(QScatterSeries::MarkerShapeRectangle);
// Use the chart widget as the central widget
QMainWindow w;

View File

@ -127,9 +127,6 @@ void ChartPresenter::handleSeriesAdded(QChartSeries* series)
QObject::connect(m_dataset, SIGNAL(domainChanged(const Domain&)),
scatterPresenter, SLOT(handleDomainChanged(const Domain&)));
m_chartTheme->decorate(scatterPresenter, scatterSeries, m_chartItems.count());
// scatterSeries->d->m_theme = m_chartTheme->themeForSeries();
// scatterSeries->d->setParentItem(this);
// scatterSeries->d->m_boundingRect = m_rect.adjusted(margin(),margin(), -margin(), -margin());
m_chartItems.insert(scatterSeries, scatterPresenter);
break;
}

View File

@ -104,6 +104,14 @@ void ChartTheme::decorate(ChartItem* item, QChartSeries* series,int count)
decorate(i,s,count);
break;
}
case QChartSeries::SeriesTypeScatter: {
QScatterSeries* s = qobject_cast<QScatterSeries*>(series);
Q_ASSERT(s);
ScatterPresenter* i = static_cast<ScatterPresenter*>(item);
Q_ASSERT(i);
decorate(i, s, count);
break;
}
case QChartSeries::SeriesTypePie: {
QPieSeries* s = static_cast<QPieSeries*>(series);
PiePresenter* i = static_cast<PiePresenter*>(item);
@ -179,16 +187,16 @@ void ChartTheme::decorate(ScatterPresenter* presenter, QScatterSeries* series, i
Q_ASSERT(presenter);
Q_ASSERT(series);
presenter->m_markerPen.setColor(m_seriesColor.at(count % m_seriesColor.size()));
QColor color = m_seriesColor.at(count % m_seriesColor.size());
// TODO: define alpha in the theme? or in the series?
color.setAlpha(120);
// QPen pen;
// if(pen != series->pen()){
// item->setPen(series->pen());
// return;
// }
// pen.setColor(m_seriesColor.at(count%m_seriesColor.size()));
// pen.setWidthF(2);
// item->setPen(pen);
QBrush brush(color, Qt::SolidPattern);
presenter->m_markerBrush = brush;
QPen pen(brush, 1);
pen.setColor(color);
presenter->m_markerPen = pen;
}
void ChartTheme::decorate(PiePresenter* item, QPieSeries* series, int /*count*/)

View File

@ -5,8 +5,14 @@
QTCOMMERCIALCHART_BEGIN_NAMESPACE
QScatterSeriesPrivate::QScatterSeriesPrivate() :
m_data(QList<QPointF>())
m_data(QList<QPointF>()),
m_markerPen(QPen()),
m_markerBrush(QBrush()),
m_markerShape(QScatterSeries::MarkerShapeDefault)
{
// Initialize pen color to invalid to use a theme color by default
m_markerPen.setColor(QColor::Invalid);
m_markerBrush.setColor(QColor::Invalid);
}
QScatterSeries::QScatterSeries(QObject *parent) :
@ -54,6 +60,26 @@ QPen QScatterSeries::markerPen()
return d->m_markerPen;
}
void QScatterSeries::setMarkerBrush(QBrush brush)
{
d->m_markerBrush = brush;
}
QBrush QScatterSeries::markerBrush()
{
return d->m_markerBrush;
}
void QScatterSeries::setMarkerShape(MarkerShape shape)
{
d->m_markerShape = shape;
}
QScatterSeries::MarkerShape QScatterSeries::markerShape()
{
return (QScatterSeries::MarkerShape) d->m_markerShape;
}
#include "moc_qscatterseries.cpp"
QTCOMMERCIALCHART_END_NAMESPACE

View File

@ -11,8 +11,21 @@ class QScatterSeriesPrivate;
class QTCOMMERCIALCHART_EXPORT QScatterSeries : public QChartSeries
{
Q_OBJECT
public:
enum MarkerShape {
// TODO: to be defined by the graphics design
// TODO: marker shapes: "x", star, rectangle, tilted rect, triangle, circle, dot
MarkerShapeDefault = 0,
MarkerShapePoint,
MarkerShapeX,
MarkerShapeRectangle,
MarkerShapeTiltedRectangle,
MarkerShapeTriangle,
MarkerShapeCircle
};
public:
//QScatterSeries(QSeriesData *data, QObject *chart);
QScatterSeries(QObject *parent = 0);
~QScatterSeries();
@ -25,17 +38,20 @@ public:
QScatterSeries& operator << (const QPointF &value);
void setData(QList<QPointF> data);
QList<QPointF> data();
//TODO? void insertData(int index, QPointF data);
//TODO: insertData?
void setMarkerPen(QPen pen);
QPen markerPen();
// TODO: marker shapes: "x", star, rectangle, tilted rect, triangle, circle, dot
//void setMarkerShape(MarkerShape shape);
void setMarkerBrush(QBrush brush);
QBrush markerBrush();
void setMarkerShape(MarkerShape shape);
MarkerShape markerShape();
// TODO: marker size?
Q_SIGNALS:
// TODO: move to PIMPL?
// TODO: move to PIMPL for simplicity or does the user ever need these signals?
// TODO: more finegrained signaling for performance reasons
// (check QPieSeries implementation with change sets)
void changed();
//public Q_SLOTS:

View File

@ -43,31 +43,48 @@ void ScatterPresenter::handleModelChanged()
void ScatterPresenter::paint(QPainter *painter, const QStyleOptionGraphicsItem */*option*/, QWidget */*widget*/)
{
// TODO: The opacity should be user definable?
//brush.setColor(QColor(255, 82, 0, 100));
//if (m_series->markerPen().isValid()) {
if (false) {
QPen pen = painter->pen();
QBrush brush = pen.brush();
brush.setColor(m_series->markerPen().color());
pen.setBrush(brush);
pen.setWidth(4);
painter->setPen(pen);
}
else {
// TODO: fix this
QPen pen = painter->pen();
QBrush brush = pen.brush();
brush.setColor(m_markerPen.color());
pen.setBrush(brush);
pen.setWidth(4);
painter->setPen(pen);
// TODO: Optimization: avoid setting on every paint method call?
// The custom settings in series override those defined by the theme
if (m_series->markerPen().color().isValid()) {
painter->setPen(m_series->markerPen());
painter->setBrush(m_series->markerBrush());
} else {
painter->setPen(m_markerPen);
painter->setBrush(m_markerBrush);
}
int shape = m_series->markerShape();
for (int i(0); i < m_scenex.count() && i < m_sceney.count(); i++) {
if (scene()->width() > m_scenex.at(i) && scene()->height() > m_sceney.at(i))
//painter->drawArc(m_scenex.at(i), m_sceney.at(i), 2, 2, 0, 5760);
painter->drawPoint(m_scenex.at(i), m_sceney.at(i));
// Paint a shape
switch (shape) {
case QScatterSeries::MarkerShapeDefault:
// Fallthrough, defaults to circle
case QScatterSeries::MarkerShapeCircle:
painter->drawChord(m_scenex.at(i), m_sceney.at(i), 9, 9, 0, 5760);
break;
case QScatterSeries::MarkerShapePoint:
painter->drawPoint(m_scenex.at(i), m_sceney.at(i));
break;
case QScatterSeries::MarkerShapeRectangle:
painter->drawRect(m_scenex.at(i), m_sceney.at(i), 9, 9);
break;
case QScatterSeries::MarkerShapeTiltedRectangle:
// TODO:
static const QPointF points[4] = {
QPointF(-1.0 + m_scenex.at(i), 0.0 + m_sceney.at(i)),
QPointF(0.0 + m_scenex.at(i), 1.0 + m_sceney.at(i)),
QPointF(1.0 + m_scenex.at(i), 0.0 + m_sceney.at(i)),
QPointF(0.0 + m_scenex.at(i), -1.0 + m_sceney.at(i))
};
painter->drawPolygon(points, 4);
break;
default:
// TODO: implement the rest of the shapes
Q_ASSERT(false);
break;
}
}
}

View File

@ -40,6 +40,7 @@ public:
QList<qreal> m_sceney;
Domain m_visibleChartArea;
QPen m_markerPen;
QBrush m_markerBrush;
};
QTCOMMERCIALCHART_END_NAMESPACE

View File

@ -18,6 +18,8 @@ public:
public:
QList<QPointF> m_data;
QPen m_markerPen;
QBrush m_markerBrush;
int m_markerShape;
};
QTCOMMERCIALCHART_END_NAMESPACE