Merge remote-tracking branch 'origin/5.6' into 5.7

Conflicts:
	.qmake.conf
	README
	src/charts/qchartglobal.h
	tests/auto/chartdataset/tst_chartdataset.cpp
	tests/auto/domain/tst_domain.cpp

Change-Id: Ib4e01f2646d87b691c7b2f8bee4ed1f5521e4f6d
This commit is contained in:
Liang Qi 2016-08-23 08:23:42 +02:00
commit d352d707f9
27 changed files with 291 additions and 207 deletions

2
README
View File

@ -1,5 +1,5 @@
---------------
Qt Charts 5.7.0
Qt Charts
---------------
Qt Charts module provides a set of easy to use chart components. It uses

25
dist/changes-2.1.2 vendored Normal file
View File

@ -0,0 +1,25 @@
Qt Charts 2.1.2
Fixed issues
------------
- [QTBUG-54914] Make OpenGL accelerated series obey series visibility
- [QTBUG-54803] Ensure the chart is drawn whenever the render node is recreated
- [QTBUG-55098] Fix partial blurriness of the gl accelerated graph
- [QTBUG-54763] Clarify QML BarSet::values documentation
- [QTBUG-53073] Fix VXYModelMapper documentation
- [QTBUG-52654] Print console warning when invalid row/column used in model mapper
- [QTBUG-52086] Fix BarSet value rounding
- [QTBUG-53949] Fix axis minimum height in case of multiple axes on same orientation
- [QTBUG-54401] Fix issues with reverse axes
- QChart mapping functions returned unreversed values
- Bounding regions of series were incorrect
- Mouse events gave wrong positions
- Chart scrolling and zooming didn't account for reversed axes
- [QTBUG-55278] Disconnect boxplot series from chart's dataset correctly
- [QTBUG-53337] Fix setting axis color properties to black for the first time
- [QTBUG-55348] Disconnect a series from ChartItem when it is removed from a chart
- Fix logarithmic axis for area chart
Fixed examples
--------------
- [QTBUG-54492] Fix resize handling in Callout example

View File

@ -32,15 +32,17 @@
#include <QtGui/QFontMetrics>
#include <QtWidgets/QGraphicsSceneMouseEvent>
#include <QtGui/QMouseEvent>
#include <QtCharts/QChart>
Callout::Callout(QGraphicsItem * parent):
QGraphicsItem(parent)
Callout::Callout(QChart *chart):
QGraphicsItem(chart),
m_chart(chart)
{
}
QRectF Callout::boundingRect() const
{
QPointF anchor = mapFromParent(m_anchor);
QPointF anchor = mapFromParent(m_chart->mapToPosition(m_anchor));
QRectF rect;
rect.setLeft(qMin(m_rect.left(), anchor.x()));
rect.setRight(qMax(m_rect.right(), anchor.x()));
@ -56,7 +58,7 @@ void Callout::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, Q
QPainterPath path;
path.addRoundedRect(m_rect, 5, 5);
QPointF anchor = mapFromParent(m_anchor);
QPointF anchor = mapFromParent(m_chart->mapToPosition(m_anchor));
if (!m_rect.contains(anchor)) {
QPointF point1, point2;
@ -88,7 +90,7 @@ void Callout::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, Q
point2.setY(y2);
path.moveTo(point1);
path.lineTo(mapFromParent(m_anchor));
path.lineTo(anchor);
path.lineTo(point2);
path = path.simplified();
}
@ -126,3 +128,9 @@ void Callout::setAnchor(QPointF point)
{
m_anchor = point;
}
void Callout::updateGeometry()
{
prepareGeometryChange();
setPos(m_chart->mapToPosition(m_anchor) + QPoint(10, -50));
}

View File

@ -30,6 +30,7 @@
#ifndef CALLOUT_H
#define CALLOUT_H
#include <QtCharts/QChartGlobal>
#include <QtWidgets/QGraphicsItem>
#include <QtGui/QFont>
@ -37,13 +38,20 @@ QT_BEGIN_NAMESPACE
class QGraphicsSceneMouseEvent;
QT_END_NAMESPACE
QT_CHARTS_BEGIN_NAMESPACE
class QChart;
QT_CHARTS_END_NAMESPACE
QT_CHARTS_USE_NAMESPACE
class Callout : public QGraphicsItem
{
public:
Callout(QGraphicsItem * parent = 0);
Callout(QChart *parent);
void setText(const QString &text);
void setAnchor(QPointF point);
void updateGeometry();
QRectF boundingRect() const;
void paint(QPainter *painter, const QStyleOptionGraphicsItem *option,QWidget *widget);
@ -58,6 +66,7 @@ private:
QRectF m_rect;
QPointF m_anchor;
QFont m_font;
QChart *m_chart;
};
#endif // CALLOUT_H

View File

@ -98,6 +98,8 @@ void View::resizeEvent(QResizeEvent *event)
m_chart->resize(event->size());
m_coordX->setPos(m_chart->size().width()/2 - 50, m_chart->size().height() - 20);
m_coordY->setPos(m_chart->size().width()/2 + 50, m_chart->size().height() - 20);
foreach (Callout *callout, m_callouts)
callout->updateGeometry();
}
QGraphicsView::resizeEvent(event);
}
@ -111,6 +113,7 @@ void View::mouseMoveEvent(QMouseEvent *event)
void View::keepCallout()
{
m_callouts.append(m_tooltip);
m_tooltip = new Callout(m_chart);
}
@ -121,10 +124,9 @@ void View::tooltip(QPointF point, bool state)
if (state) {
m_tooltip->setText(QString("X: %1 \nY: %2 ").arg(point.x()).arg(point.y()));
QXYSeries *series = qobject_cast<QXYSeries *>(sender());
m_tooltip->setAnchor(m_chart->mapToPosition(point, series));
m_tooltip->setPos(m_chart->mapToPosition(point, series) + QPoint(10, -50));
m_tooltip->setAnchor(point);
m_tooltip->setZValue(11);
m_tooltip->updateGeometry();
m_tooltip->show();
} else {
m_tooltip->hide();

View File

@ -66,6 +66,7 @@ private:
QGraphicsSimpleTextItem *m_coordY;
QChart *m_chart;
Callout *m_tooltip;
QList<Callout *> m_callouts;
};
#endif

View File

@ -33,6 +33,7 @@
#include <QtCharts/QLineSeries>
#include <private/chartpresenter_p.h>
#include <private/abstractdomain_p.h>
#include <private/chartdataset_p.h>
#include <QtGui/QPainter>
#include <QtWidgets/QGraphicsSceneMouseEvent>
#include <QtCore/QDebug>
@ -171,18 +172,26 @@ void AreaChartItem::handleUpdated()
void AreaChartItem::handleDomainUpdated()
{
if (m_upper) {
AbstractDomain* d = m_upper->domain();
d->setSize(domain()->size());
d->setRange(domain()->minX(),domain()->maxX(),domain()->minY(),domain()->maxY());
m_upper->handleDomainUpdated();
}
fixEdgeSeriesDomain(m_upper);
fixEdgeSeriesDomain(m_lower);
}
if (m_lower) {
AbstractDomain* d = m_lower->domain();
d->setSize(domain()->size());
d->setRange(domain()->minX(),domain()->maxX(),domain()->minY(),domain()->maxY());
m_lower->handleDomainUpdated();
void AreaChartItem::fixEdgeSeriesDomain(LineChartItem *edgeSeries)
{
if (edgeSeries) {
AbstractDomain* mainDomain = domain();
AbstractDomain* edgeDomain = edgeSeries->domain();
if (edgeDomain->type() != mainDomain->type()) {
// Change the domain of edge series to the same type as the area series
edgeDomain = dataSet()->createDomain(mainDomain->type());
edgeSeries->seriesPrivate()->setDomain(edgeDomain);
}
edgeDomain->setSize(mainDomain->size());
edgeDomain->setRange(mainDomain->minX(), mainDomain->maxX(), mainDomain->minY(), mainDomain->maxY());
edgeDomain->setReverseX(mainDomain->isReverseX());
edgeDomain->setReverseY(mainDomain->isReverseY());
edgeSeries->handleDomainUpdated();
}
}
@ -199,8 +208,6 @@ void AreaChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
else
painter->setClipRect(clipRect);
reversePainter(painter, clipRect);
painter->drawPath(m_path);
if (m_pointsVisible) {
painter->setPen(m_pointPen);
@ -209,8 +216,6 @@ void AreaChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
painter->drawPoints(m_lower->geometryPoints());
}
reversePainter(painter, clipRect);
// Draw series point label
if (m_pointLabelsVisible) {
static const QString xPointTag(QLatin1String("@xPoint"));
@ -239,17 +244,9 @@ void AreaChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
// Position text in relation to the point
int pointLabelWidth = fm.width(pointLabel);
QPointF position(m_upper->geometryPoints().at(i));
if (!seriesPrivate()->reverseXAxis())
position.setX(position.x() - pointLabelWidth / 2);
else
position.setX(domain()->size().width() - position.x() - pointLabelWidth / 2);
if (!seriesPrivate()->reverseYAxis()) {
position.setY(position.y() - m_series->upperSeries()->pen().width() / 2
- labelOffset);
} else {
position.setY(domain()->size().height() - position.y()
- m_series->upperSeries()->pen().width() / 2 - labelOffset);
}
position.setX(position.x() - pointLabelWidth / 2);
position.setY(position.y() - m_series->upperSeries()->pen().width() / 2
- labelOffset);
painter->drawText(position, pointLabel);
}
}
@ -265,17 +262,9 @@ void AreaChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
// Position text in relation to the point
int pointLabelWidth = fm.width(pointLabel);
QPointF position(m_lower->geometryPoints().at(i));
if (!seriesPrivate()->reverseXAxis())
position.setX(position.x() - pointLabelWidth / 2);
else
position.setX(domain()->size().width() - position.x() - pointLabelWidth / 2);
if (!seriesPrivate()->reverseYAxis()) {
position.setY(position.y() - m_series->lowerSeries()->pen().width() / 2
- labelOffset);
} else {
position.setY(domain()->size().height() - position.y()
- m_series->lowerSeries()->pen().width() / 2 - labelOffset);
}
position.setX(position.x() - pointLabelWidth / 2);
position.setY(position.y() - m_series->lowerSeries()->pen().width() / 2
- labelOffset);
painter->drawText(position, pointLabel);
}
}

View File

@ -87,6 +87,8 @@ public Q_SLOTS:
void handleDomainUpdated();
private:
void fixEdgeSeriesDomain(LineChartItem *edgeSeries);
QAreaSeries *m_series;
LineChartItem *m_upper;
LineChartItem *m_lower;

View File

@ -523,7 +523,7 @@ QPen QAbstractAxis::linePen() const
void QAbstractAxis::setLinePenColor(QColor color)
{
QPen p = linePen();
if (p.color() != color) {
if (p.color() != color || d_ptr->m_axisPen == QChartPrivate::defaultPen()) {
p.setColor(color);
setLinePen(p);
emit colorChanged(color);
@ -618,31 +618,31 @@ QPen QAbstractAxis::minorGridLinePen() const
void QAbstractAxis::setGridLineColor(const QColor &color)
{
QPen pen = gridLinePen();
if (color != pen.color()) {
if (color != pen.color() || d_ptr->m_gridLinePen == QChartPrivate::defaultPen()) {
pen.setColor(color);
d_ptr->m_gridLinePen = pen;
setGridLinePen(pen);
emit gridLineColorChanged(color);
}
}
QColor QAbstractAxis::gridLineColor()
{
return d_ptr->m_gridLinePen.color();
return gridLinePen().color();
}
void QAbstractAxis::setMinorGridLineColor(const QColor &color)
{
QPen pen = minorGridLinePen();
if (color != pen.color()) {
if (color != pen.color() || d_ptr->m_minorGridLinePen == QChartPrivate::defaultPen()) {
pen.setColor(color);
d_ptr->m_minorGridLinePen = pen;
setMinorGridLinePen(pen);
emit minorGridLineColorChanged(color);
}
}
QColor QAbstractAxis::minorGridLineColor()
{
return d_ptr->m_minorGridLinePen.color();
return minorGridLinePen().color();
}
void QAbstractAxis::setLabelsVisible(bool visible)
@ -717,7 +717,7 @@ int QAbstractAxis::labelsAngle() const
void QAbstractAxis::setLabelsColor(QColor color)
{
QBrush b = labelsBrush();
if (b.color() != color) {
if (b.color() != color || d_ptr->m_labelsBrush == QChartPrivate::defaultBrush()) {
b.setColor(color);
setLabelsBrush(b);
emit labelsColorChanged(color);
@ -860,7 +860,7 @@ QBrush QAbstractAxis::shadesBrush() const
void QAbstractAxis::setShadesColor(QColor color)
{
QBrush b = shadesBrush();
if (b.color() != color) {
if (b.color() != color || d_ptr->m_shadesBrush == QChartPrivate::defaultBrush()) {
b.setColor(color);
setShadesBrush(b);
emit shadesColorChanged(color);
@ -874,8 +874,8 @@ QColor QAbstractAxis::shadesColor() const
void QAbstractAxis::setShadesBorderColor(QColor color)
{
QPen p = d_ptr->m_shadesPen;
if (p.color() != color) {
QPen p = shadesPen();
if (p.color() != color || d_ptr->m_shadesPen == QChartPrivate::defaultPen()) {
p.setColor(color);
setShadesPen(p);
emit shadesColorChanged(color);

View File

@ -535,9 +535,10 @@ void QBoxPlotSeriesPrivate::handleSeriesRemove(QAbstractSeries *series)
QBoxPlotSeries *removedSeries = static_cast<QBoxPlotSeries *>(series);
if (q == removedSeries && m_animation) {
m_animation->stopAll();
QObject::disconnect(m_chart->d_ptr->m_dataset, 0, removedSeries->d_func(), 0);
if (q == removedSeries) {
if (m_animation)
m_animation->stopAll();
QObject::disconnect(m_chart->d_ptr->m_dataset, 0, this, 0);
}
// Test if series removed is me, then don't do anything

View File

@ -81,6 +81,8 @@ public:
GLXYSeriesDataManager *glXYSeriesDataManager() { return m_glXYSeriesDataManager; }
AbstractDomain* createDomain(AbstractDomain::DomainType type);
Q_SIGNALS:
void axisAdded(QAbstractAxis* axis);
void axisRemoved(QAbstractAxis* axis);
@ -92,7 +94,6 @@ private:
void createAxes(QAbstractAxis::AxisTypes type, Qt::Orientation orientation);
QAbstractAxis *createAxis(QAbstractAxis::AxisType type, Qt::Orientation orientation);
AbstractDomain::DomainType selectDomain(QList<QAbstractAxis* > axes);
AbstractDomain* createDomain(AbstractDomain::DomainType type);
void deleteAllAxes();
void deleteAllSeries();
void findMinMaxForSeries(QList<QAbstractSeries *> series,Qt::Orientations orientation, qreal &min, qreal &max);

View File

@ -52,19 +52,6 @@ void ChartItem::handleDomainUpdated()
qWarning() << __FUNCTION__<< "Slot not implemented";
}
void ChartItem::reversePainter(QPainter *painter, const QRectF &clipRect)
{
if (m_series->reverseXAxis()) {
painter->translate(clipRect.width(), 0);
painter->scale(-1, 1);
}
if (m_series->reverseYAxis()) {
painter->translate(0, clipRect.height());
painter->scale(1, -1);
}
}
#include "moc_chartitem_p.cpp"
QT_CHARTS_END_NAMESPACE

View File

@ -55,7 +55,6 @@ public:
public Q_SLOTS:
virtual void handleDomainUpdated();
void reversePainter(QPainter *painter, const QRectF &clipRect);
QAbstractSeriesPrivate* seriesPrivate() const {return m_series;}
protected:

View File

@ -147,6 +147,7 @@ void ChartPresenter::handleSeriesRemoved(QAbstractSeries *series)
ChartItem *chart = series->d_ptr->m_item.take();
chart->hide();
chart->disconnect();
series->disconnect(chart);
chart->deleteLater();
if (chart->animation())
chart->animation()->stopAndDestroyLater();

View File

@ -45,7 +45,9 @@ AbstractDomain::AbstractDomain(QObject *parent)
m_zoomResetMinX(0),
m_zoomResetMaxX(0),
m_zoomResetMinY(0),
m_zoomResetMaxY(0)
m_zoomResetMaxY(0),
m_reverseX(false),
m_reverseY(false)
{
}
@ -114,15 +116,6 @@ bool AbstractDomain::isEmpty() const
return qFuzzyCompare(spanX(), 0) || qFuzzyCompare(spanY(), 0) || m_size.isEmpty();
}
QPointF AbstractDomain::calculateDomainPoint(const QPointF &point) const
{
const qreal deltaX = m_size.width() / (m_maxX - m_minX);
const qreal deltaY = m_size.height() / (m_maxY - m_minY);
qreal x = point.x() / deltaX + m_minX;
qreal y = (point.y() - m_size.height()) / (-deltaY) + m_minY;
return QPointF(x, y);
}
// handlers
void AbstractDomain::handleVerticalAxisRangeChanged(qreal min, qreal max)
@ -135,6 +128,18 @@ void AbstractDomain::handleHorizontalAxisRangeChanged(qreal min, qreal max)
setRangeX(min, max);
}
void AbstractDomain::handleReverseXChanged(bool reverse)
{
m_reverseX = reverse;
emit updated();
}
void AbstractDomain::handleReverseYChanged(bool reverse)
{
m_reverseY = reverse;
emit updated();
}
void AbstractDomain::blockRangeSignals(bool block)
{
if (m_signalsBlocked!=block) {
@ -207,11 +212,17 @@ bool AbstractDomain::attachAxis(QAbstractAxis *axis)
if (axis->orientation() == Qt::Vertical) {
QObject::connect(axis->d_ptr.data(), SIGNAL(rangeChanged(qreal,qreal)), this, SLOT(handleVerticalAxisRangeChanged(qreal,qreal)));
QObject::connect(this, SIGNAL(rangeVerticalChanged(qreal,qreal)), axis->d_ptr.data(), SLOT(handleRangeChanged(qreal,qreal)));
QObject::connect(axis, &QAbstractAxis::reverseChanged,
this, &AbstractDomain::handleReverseYChanged);
m_reverseY = axis->isReverse();
}
if (axis->orientation() == Qt::Horizontal) {
QObject::connect(axis->d_ptr.data(), SIGNAL(rangeChanged(qreal,qreal)), this, SLOT(handleHorizontalAxisRangeChanged(qreal,qreal)));
QObject::connect(this, SIGNAL(rangeHorizontalChanged(qreal,qreal)), axis->d_ptr.data(), SLOT(handleRangeChanged(qreal,qreal)));
QObject::connect(axis, &QAbstractAxis::reverseChanged,
this, &AbstractDomain::handleReverseXChanged);
m_reverseX = axis->isReverse();
}
return true;
@ -222,12 +233,16 @@ bool AbstractDomain::detachAxis(QAbstractAxis *axis)
if (axis->orientation() == Qt::Vertical) {
QObject::disconnect(axis->d_ptr.data(), SIGNAL(rangeChanged(qreal,qreal)), this, SLOT(handleVerticalAxisRangeChanged(qreal,qreal)));
QObject::disconnect(this, SIGNAL(rangeVerticalChanged(qreal,qreal)), axis->d_ptr.data(), SLOT(handleRangeChanged(qreal,qreal)));
}
QObject::disconnect(axis, &QAbstractAxis::reverseChanged,
this, &AbstractDomain::handleReverseYChanged);
}
if (axis->orientation() == Qt::Horizontal) {
QObject::disconnect(axis->d_ptr.data(), SIGNAL(rangeChanged(qreal,qreal)), this, SLOT(handleHorizontalAxisRangeChanged(qreal,qreal)));
QObject::disconnect(this, SIGNAL(rangeHorizontalChanged(qreal,qreal)), axis->d_ptr.data(), SLOT(handleRangeChanged(qreal,qreal)));
}
QObject::disconnect(axis, &QAbstractAxis::reverseChanged,
this, &AbstractDomain::handleReverseXChanged);
}
return true;
}
@ -269,6 +284,22 @@ void AbstractDomain::adjustLogDomainRanges(qreal &min, qreal &max)
}
}
// This function fixes the zoom rect based on axis reversals
QRectF AbstractDomain::fixZoomRect(const QRectF &rect)
{
QRectF fixRect = rect;
if (m_reverseX || m_reverseY) {
QPointF center = rect.center();
if (m_reverseX)
center.setX(m_size.width() - center.x());
if (m_reverseY)
center.setY(m_size.height() - center.y());
fixRect.moveCenter(QPointF(center.x(), center.y()));
}
return fixRect;
}
#include "moc_abstractdomain_p.cpp"

View File

@ -111,6 +111,12 @@ public:
static void looseNiceNumbers(qreal &min, qreal &max, int &ticksCount);
static qreal niceNumber(qreal x, bool ceiling);
void setReverseX(bool reverse) { m_reverseX = reverse; }
void setReverseY(bool reverse) { m_reverseY = reverse; }
bool isReverseX() const { return m_reverseX; }
bool isReverseY() const { return m_reverseY; }
Q_SIGNALS:
void updated();
void rangeHorizontalChanged(qreal min, qreal max);
@ -119,9 +125,12 @@ Q_SIGNALS:
public Q_SLOTS:
void handleVerticalAxisRangeChanged(qreal min,qreal max);
void handleHorizontalAxisRangeChanged(qreal min,qreal max);
void handleReverseXChanged(bool reverse);
void handleReverseYChanged(bool reverse);
protected:
void adjustLogDomainRanges(qreal &min, qreal &max);
QRectF fixZoomRect(const QRectF &rect);
qreal m_minX;
qreal m_maxX;
@ -134,6 +143,8 @@ protected:
qreal m_zoomResetMaxX;
qreal m_zoomResetMinY;
qreal m_zoomResetMaxY;
bool m_reverseX;
bool m_reverseY;
};
QT_CHARTS_END_NAMESPACE

View File

@ -89,15 +89,16 @@ void LogXLogYDomain::setRange(qreal minX, qreal maxX, qreal minY, qreal maxY)
void LogXLogYDomain::zoomIn(const QRectF &rect)
{
storeZoomReset();
qreal logLeftX = rect.left() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal logRightX = rect.right() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
QRectF fixedRect = fixZoomRect(rect);
qreal logLeftX = fixedRect.left() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal logRightX = fixedRect.right() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal leftX = qPow(m_logBaseX, logLeftX);
qreal rightX = qPow(m_logBaseX, logRightX);
qreal minX = leftX < rightX ? leftX : rightX;
qreal maxX = leftX > rightX ? leftX : rightX;
qreal logLeftY = m_logRightY - rect.bottom() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logRightY = m_logRightY - rect.top() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logLeftY = m_logRightY - fixedRect.bottom() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logRightY = m_logRightY - fixedRect.top() * (m_logRightY - m_logLeftY) / m_size.height();
qreal leftY = qPow(m_logBaseY, logLeftY);
qreal rightY = qPow(m_logBaseY, logRightY);
qreal minY = leftY < rightY ? leftY : rightY;
@ -109,8 +110,9 @@ void LogXLogYDomain::zoomIn(const QRectF &rect)
void LogXLogYDomain::zoomOut(const QRectF &rect)
{
storeZoomReset();
const qreal factorX = m_size.width() / rect.width();
const qreal factorY = m_size.height() / rect.height();
QRectF fixedRect = fixZoomRect(rect);
const qreal factorX = m_size.width() / fixedRect.width();
const qreal factorY = m_size.height() / fixedRect.height();
qreal logLeftX = m_logLeftX + (m_logRightX - m_logLeftX) / 2 * (1 - factorX);
qreal logRIghtX = m_logLeftX + (m_logRightX - m_logLeftX) / 2 * (1 + factorX);
@ -131,6 +133,11 @@ void LogXLogYDomain::zoomOut(const QRectF &rect)
void LogXLogYDomain::move(qreal dx, qreal dy)
{
if (m_reverseX)
dx = -dx;
if (m_reverseY)
dy = -dy;
qreal stepX = dx * qAbs(m_logRightX - m_logLeftX) / m_size.width();
qreal leftX = qPow(m_logBaseX, m_logLeftX + stepX);
qreal rightX = qPow(m_logBaseX, m_logRightX + stepX);
@ -153,23 +160,25 @@ QPointF LogXLogYDomain::calculateGeometryPoint(const QPointF &point, bool &ok) c
qreal x(0);
qreal y(0);
if (point.x() > 0 && point.y() > 0) {
x = (std::log10(point.x()) / std::log10(m_logBaseX)) * deltaX - m_logLeftX * deltaX;
y = (std::log10(point.y()) / std::log10(m_logBaseY)) * -deltaY - m_logLeftY * -deltaY + m_size.height();
x = ((std::log10(point.x()) / std::log10(m_logBaseX)) - m_logLeftX) * deltaX;
y = ((std::log10(point.y()) / std::log10(m_logBaseY)) - m_logLeftY) * deltaY;
ok = true;
} else {
qWarning() << "Logarithms of zero and negative values are undefined.";
ok = false;
if (point.x() > 0)
x = (std::log10(point.x()) / std::log10(m_logBaseX)) * deltaX - m_logLeftX * deltaX;
x = ((std::log10(point.x()) / std::log10(m_logBaseX)) - m_logLeftX) * deltaX;
else
x = 0;
if (point.y() > 0) {
y = (std::log10(point.y()) / std::log10(m_logBaseY)) * -deltaY - m_logLeftY * -deltaY
+ m_size.height();
} else {
y = m_size.height();
}
if (point.y() > 0)
y = ((std::log10(point.y()) / std::log10(m_logBaseY)) - m_logLeftY) * deltaY;
else
y = 0;
}
if (m_reverseX)
x = m_size.width() - x;
if (!m_reverseY)
y = m_size.height() - y;
return QPointF(x, y);
}
@ -183,8 +192,12 @@ QVector<QPointF> LogXLogYDomain::calculateGeometryPoints(const QVector<QPointF>
for (int i = 0; i < vector.count(); ++i) {
if (vector[i].x() > 0 && vector[i].y() > 0) {
qreal x = (std::log10(vector[i].x()) / std::log10(m_logBaseX)) * deltaX - m_logLeftX * deltaX;
qreal y = (std::log10(vector[i].y()) / std::log10(m_logBaseY)) * -deltaY - m_logLeftY * -deltaY + m_size.height();
qreal x = ((std::log10(vector[i].x()) / std::log10(m_logBaseX)) - m_logLeftX) * deltaX;
if (m_reverseX)
x = m_size.width() - x;
qreal y = ((std::log10(vector[i].y()) / std::log10(m_logBaseY)) - m_logLeftY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
result[i].setX(x);
result[i].setY(y);
} else {
@ -199,8 +212,10 @@ QPointF LogXLogYDomain::calculateDomainPoint(const QPointF &point) const
{
const qreal deltaX = m_size.width() / qAbs(m_logRightX - m_logLeftX);
const qreal deltaY = m_size.height() / qAbs(m_logRightY - m_logLeftY);
qreal x = qPow(m_logBaseX, m_logLeftX + point.x() / deltaX);
qreal y = qPow(m_logBaseY, m_logLeftY + (m_size.height() - point.y()) / deltaY);
qreal x = m_reverseX ? (m_size.width() - point.x()) : point.x();
x = qPow(m_logBaseX, m_logLeftX + x / deltaX);
qreal y = m_reverseY ? point.y() : (m_size.height() - point.y());
y = qPow(m_logBaseY, m_logLeftY + y / deltaY);
return QPointF(x, y);
}

View File

@ -81,8 +81,9 @@ void LogXYDomain::setRange(qreal minX, qreal maxX, qreal minY, qreal maxY)
void LogXYDomain::zoomIn(const QRectF &rect)
{
storeZoomReset();
qreal logLeftX = rect.left() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal logRightX = rect.right() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
QRectF fixedRect = fixZoomRect(rect);
qreal logLeftX = fixedRect.left() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal logRightX = fixedRect.right() * (m_logRightX - m_logLeftX) / m_size.width() + m_logLeftX;
qreal leftX = qPow(m_logBaseX, logLeftX);
qreal rightX = qPow(m_logBaseX, logRightX);
qreal minX = leftX < rightX ? leftX : rightX;
@ -92,8 +93,8 @@ void LogXYDomain::zoomIn(const QRectF &rect)
qreal minY = m_minY;
qreal maxY = m_maxY;
minY = maxY - dy * rect.bottom();
maxY = maxY - dy * rect.top();
minY = maxY - dy * fixedRect.bottom();
maxY = maxY - dy * fixedRect.top();
setRange(minX, maxX, minY, maxY);
}
@ -101,7 +102,8 @@ void LogXYDomain::zoomIn(const QRectF &rect)
void LogXYDomain::zoomOut(const QRectF &rect)
{
storeZoomReset();
const qreal factorX = m_size.width() / rect.width();
QRectF fixedRect = fixZoomRect(rect);
const qreal factorX = m_size.width() / fixedRect.width();
qreal logLeftX = m_logLeftX + (m_logRightX - m_logLeftX) / 2 * (1 - factorX);
qreal logRIghtX = m_logLeftX + (m_logRightX - m_logLeftX) / 2 * (1 + factorX);
@ -110,11 +112,11 @@ void LogXYDomain::zoomOut(const QRectF &rect)
qreal minX = leftX < rightX ? leftX : rightX;
qreal maxX = leftX > rightX ? leftX : rightX;
qreal dy = spanY() / rect.height();
qreal dy = spanY() / fixedRect.height();
qreal minY = m_minY;
qreal maxY = m_maxY;
maxY = minY + dy * rect.bottom();
maxY = minY + dy * fixedRect.bottom();
minY = maxY - dy * m_size.height();
setRange(minX, maxX, minY, maxY);
@ -122,6 +124,11 @@ void LogXYDomain::zoomOut(const QRectF &rect)
void LogXYDomain::move(qreal dx, qreal dy)
{
if (m_reverseX)
dx = -dx;
if (m_reverseY)
dy = -dy;
qreal stepX = dx * (m_logRightX - m_logLeftX) / m_size.width();
qreal leftX = qPow(m_logBaseX, m_logLeftX + stepX);
qreal rightX = qPow(m_logBaseX, m_logRightX + stepX);
@ -145,9 +152,13 @@ QPointF LogXYDomain::calculateGeometryPoint(const QPointF &point, bool &ok) cons
const qreal deltaY = m_size.height() / (m_maxY - m_minY);
qreal x(0);
qreal y = (point.y() - m_minY) * -deltaY + m_size.height();
qreal y = (point.y() - m_minY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
if (point.x() > 0) {
x = (std::log10(point.x()) / std::log10(m_logBaseX)) * deltaX - m_logLeftX * deltaX;
x = ((std::log10(point.x()) / std::log10(m_logBaseX)) - m_logLeftX) * deltaX;
if (m_reverseX)
x = m_size.width() - x;
ok = true;
} else {
x = 0;
@ -167,8 +178,12 @@ QVector<QPointF> LogXYDomain::calculateGeometryPoints(const QVector<QPointF> &ve
for (int i = 0; i < vector.count(); ++i) {
if (vector[i].x() > 0) {
qreal x = (std::log10(vector[i].x()) / std::log10(m_logBaseX)) * deltaX - m_logLeftX * deltaX;
qreal y = (vector[i].y() - m_minY) * -deltaY + m_size.height();
qreal x = ((std::log10(vector[i].x()) / std::log10(m_logBaseX)) - m_logLeftX) * deltaX;
if (m_reverseX)
x = m_size.width() - x;
qreal y = (vector[i].y() - m_minY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
result[i].setX(x);
result[i].setY(y);
} else {
@ -184,8 +199,11 @@ QPointF LogXYDomain::calculateDomainPoint(const QPointF &point) const
{
const qreal deltaX = m_size.width() / (m_logRightX - m_logLeftX);
const qreal deltaY = m_size.height() / (m_maxY - m_minY);
qreal x = qPow(m_logBaseX, m_logLeftX + point.x() / deltaX);
qreal y = (point.y() - m_size.height()) / (-deltaY) + m_minY;
qreal x = m_reverseX ? (m_size.width() - point.x()) : point.x();
x = qPow(m_logBaseX, m_logLeftX + x / deltaX);
qreal y = m_reverseY ? point.y() : (m_size.height() - point.y());
y /= deltaY;
y += m_minY;
return QPointF(x, y);
}

View File

@ -81,15 +81,16 @@ void XLogYDomain::setRange(qreal minX, qreal maxX, qreal minY, qreal maxY)
void XLogYDomain::zoomIn(const QRectF &rect)
{
storeZoomReset();
QRectF fixedRect = fixZoomRect(rect);
qreal dx = spanX() / m_size.width();
qreal maxX = m_maxX;
qreal minX = m_minX;
maxX = minX + dx * rect.right();
minX = minX + dx * rect.left();
maxX = minX + dx * fixedRect.right();
minX = minX + dx * fixedRect.left();
qreal logLeftY = m_logRightY - rect.bottom() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logRightY = m_logRightY - rect.top() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logLeftY = m_logRightY - fixedRect.bottom() * (m_logRightY - m_logLeftY) / m_size.height();
qreal logRightY = m_logRightY - fixedRect.top() * (m_logRightY - m_logLeftY) / m_size.height();
qreal leftY = qPow(m_logBaseY, logLeftY);
qreal rightY = qPow(m_logBaseY, logRightY);
qreal minY = leftY < rightY ? leftY : rightY;
@ -101,14 +102,15 @@ void XLogYDomain::zoomIn(const QRectF &rect)
void XLogYDomain::zoomOut(const QRectF &rect)
{
storeZoomReset();
qreal dx = spanX() / rect.width();
QRectF fixedRect = fixZoomRect(rect);
qreal dx = spanX() / fixedRect.width();
qreal maxX = m_maxX;
qreal minX = m_minX;
minX = maxX - dx * rect.right();
minX = maxX - dx * fixedRect.right();
maxX = minX + dx * m_size.width();
const qreal factorY = m_size.height() / rect.height();
const qreal factorY = m_size.height() / fixedRect.height();
qreal newLogMinY = m_logLeftY + (m_logRightY - m_logLeftY) / 2 * (1 - factorY);
qreal newLogMaxY = m_logLeftY + (m_logRightY - m_logLeftY) / 2 * (1 + factorY);
qreal leftY = qPow(m_logBaseY, newLogMinY);
@ -121,6 +123,11 @@ void XLogYDomain::zoomOut(const QRectF &rect)
void XLogYDomain::move(qreal dx, qreal dy)
{
if (m_reverseX)
dx = -dx;
if (m_reverseY)
dy = -dy;
qreal x = spanX() / m_size.width();
qreal maxX = m_maxX;
qreal minX = m_minX;
@ -145,9 +152,13 @@ QPointF XLogYDomain::calculateGeometryPoint(const QPointF &point, bool &ok) cons
const qreal deltaY = m_size.height() / qAbs(m_logRightY - m_logLeftY);
qreal x = (point.x() - m_minX) * deltaX;
if (m_reverseX)
x = m_size.width() - x;
qreal y(0);
if (point.y() > 0) {
y = (std::log10(point.y()) / std::log10(m_logBaseY)) * -deltaY - m_logLeftY * -deltaY + m_size.height();
y = ((std::log10(point.y()) / std::log10(m_logBaseY)) - m_logLeftY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
ok = true;
} else {
y = m_size.height();
@ -168,7 +179,11 @@ QVector<QPointF> XLogYDomain::calculateGeometryPoints(const QVector<QPointF> &ve
for (int i = 0; i < vector.count(); ++i) {
if (vector[i].y() > 0) {
qreal x = (vector[i].x() - m_minX) * deltaX;
qreal y = (std::log10(vector[i].y()) / std::log10(m_logBaseY)) * -deltaY - m_logLeftY * -deltaY + m_size.height();
if (m_reverseX)
x = m_size.width() - x;
qreal y = ((std::log10(vector[i].y()) / std::log10(m_logBaseY)) - m_logLeftY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
result[i].setX(x);
result[i].setY(y);
} else {
@ -183,8 +198,11 @@ QPointF XLogYDomain::calculateDomainPoint(const QPointF &point) const
{
const qreal deltaX = m_size.width() / (m_maxX - m_minX);
const qreal deltaY = m_size.height() / qAbs(m_logRightY - m_logLeftY);
qreal x = point.x() / deltaX + m_minX;
qreal y = qPow(m_logBaseY, m_logLeftY + (m_size.height() - point.y()) / deltaY);
qreal x = m_reverseX ? (m_size.width() - point.x()) : point.x();
x /= deltaX;
x += m_minX;
qreal y = m_reverseY ? point.y() : (m_size.height() - point.y());
y = qPow(m_logBaseY, m_logLeftY + y / deltaY);
return QPointF(x, y);
}

View File

@ -71,6 +71,7 @@ void XYDomain::setRange(qreal minX, qreal maxX, qreal minY, qreal maxY)
void XYDomain::zoomIn(const QRectF &rect)
{
storeZoomReset();
QRectF fixedRect = fixZoomRect(rect);
qreal dx = spanX() / m_size.width();
qreal dy = spanY() / m_size.height();
@ -79,10 +80,10 @@ void XYDomain::zoomIn(const QRectF &rect)
qreal minY = m_minY;
qreal maxY = m_maxY;
maxX = minX + dx * rect.right();
minX = minX + dx * rect.left();
minY = maxY - dy * rect.bottom();
maxY = maxY - dy * rect.top();
maxX = minX + dx * fixedRect.right();
minX = minX + dx * fixedRect.left();
minY = maxY - dy * fixedRect.bottom();
maxY = maxY - dy * fixedRect.top();
if ((maxX - minX) == spanX()) {
minX = m_minX;
@ -99,6 +100,7 @@ void XYDomain::zoomIn(const QRectF &rect)
void XYDomain::zoomOut(const QRectF &rect)
{
storeZoomReset();
QRectF fixedRect = fixZoomRect(rect);
qreal dx = spanX() / rect.width();
qreal dy = spanY() / rect.height();
@ -107,9 +109,9 @@ void XYDomain::zoomOut(const QRectF &rect)
qreal minY = m_minY;
qreal maxY = m_maxY;
minX = maxX - dx * rect.right();
minX = maxX - dx * fixedRect.right();
maxX = minX + dx * m_size.width();
maxY = minY + dy * rect.bottom();
maxY = minY + dy * fixedRect.bottom();
minY = maxY - dy * m_size.height();
if ((maxX - minX) == spanX()) {
@ -126,6 +128,11 @@ void XYDomain::zoomOut(const QRectF &rect)
void XYDomain::move(qreal dx, qreal dy)
{
if (m_reverseX)
dx = -dx;
if (m_reverseY)
dy = -dy;
qreal x = spanX() / m_size.width();
qreal y = spanY() / m_size.height();
@ -150,7 +157,11 @@ QPointF XYDomain::calculateGeometryPoint(const QPointF &point, bool &ok) const
const qreal deltaX = m_size.width() / (m_maxX - m_minX);
const qreal deltaY = m_size.height() / (m_maxY - m_minY);
qreal x = (point.x() - m_minX) * deltaX;
qreal y = (point.y() - m_minY) * -deltaY + m_size.height();
if (m_reverseX)
x = m_size.width() - x;
qreal y = (point.y() - m_minY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
ok = true;
return QPointF(x, y);
}
@ -165,7 +176,11 @@ QVector<QPointF> XYDomain::calculateGeometryPoints(const QVector<QPointF> &vecto
for (int i = 0; i < vector.count(); ++i) {
qreal x = (vector[i].x() - m_minX) * deltaX;
qreal y = (vector[i].y() - m_minY) * -deltaY + m_size.height();
if (m_reverseX)
x = m_size.width() - x;
qreal y = (vector[i].y() - m_minY) * deltaY;
if (!m_reverseY)
y = m_size.height() - y;
result[i].setX(x);
result[i].setY(y);
}
@ -176,8 +191,12 @@ QPointF XYDomain::calculateDomainPoint(const QPointF &point) const
{
const qreal deltaX = m_size.width() / (m_maxX - m_minX);
const qreal deltaY = m_size.height() / (m_maxY - m_minY);
qreal x = point.x() / deltaX + m_minX;
qreal y = (point.y() - m_size.height()) / (-deltaY) + m_minY;
qreal x = m_reverseX ? (m_size.width() - point.x()) : point.x();
x /= deltaX;
x += m_minX;
qreal y = m_reverseY ? point.y() : (m_size.height() - point.y());
y /= deltaY;
y += m_minY;
return QPointF(x, y);
}

View File

@ -395,8 +395,6 @@ void LineChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
painter->setClipRect(clipRect);
}
reversePainter(painter, clipRect);
if (m_pointsVisible) {
painter->setBrush(m_linePen.color());
painter->drawPath(m_linePath);
@ -412,8 +410,6 @@ void LineChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opt
}
}
reversePainter(painter, clipRect);
if (m_pointLabelsVisible) {
if (m_pointLabelsClipping)
painter->setClipping(true);

View File

@ -457,40 +457,6 @@ void QAbstractSeriesPrivate::initializeAnimations(QChart::AnimationOptions optio
Q_UNUSED(curve);
}
bool QAbstractSeriesPrivate::reverseXAxis()
{
bool reverseXAxis = false;
if (m_axes.size() != 0 && !(m_chart->chartType() == QChart::ChartTypePolar)) {
int i = 0;
while (i < m_axes.size()) {
if (m_axes.at(i)->orientation() == Qt::Horizontal && m_axes.at(i)->isReverse()) {
reverseXAxis = true;
break;
}
i++;
}
}
return reverseXAxis;
}
bool QAbstractSeriesPrivate::reverseYAxis()
{
bool reverseYAxis = false;
if (m_axes.size() != 0 && !(m_chart->chartType() == QChart::ChartTypePolar)) {
int i = 0;
while (i < m_axes.size()) {
if (m_axes.at(i)->orientation() == Qt::Vertical && m_axes.at(i)->isReverse()) {
reverseYAxis = true;
break;
}
i++;
}
}
return reverseYAxis;
}
// This function can be used to explicitly block OpenGL use from some otherwise supported series,
// such as the line series used as edge series of an area series.
void QAbstractSeriesPrivate::setBlockOpenGL(bool enable)

View File

@ -89,8 +89,6 @@ public:
ChartPresenter *presenter() const;
QChart* chart() { return m_chart; }
bool reverseXAxis();
bool reverseYAxis();
void setBlockOpenGL(bool enable);

View File

@ -194,17 +194,10 @@ void ScatterChartItem::updateGeometry()
// fake anyway. After remove animation stops, geometry is updated to correct one.
m_markerMap[item] = m_series->at(qMin(seriesLastIndex, i));
QPointF position;
if (seriesPrivate()->reverseXAxis())
position.setX(domain()->size().width() - point.x() - rect.width() / 2);
else
position.setX(point.x() - rect.width() / 2);
if (seriesPrivate()->reverseYAxis())
position.setY(domain()->size().height() - point.y() - rect.height() / 2);
else
position.setY(point.y() - rect.height() / 2);
position.setX(point.x() - rect.width() / 2);
position.setY(point.y() - rect.height() / 2);
item->setPos(position);
if (!m_visible || offGridStatus.at(i))
item->setVisible(false);
else

View File

@ -460,8 +460,6 @@ void SplineChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *o
painter->setClipRect(clipRect);
}
reversePainter(painter, clipRect);
painter->drawPath(m_path);
if (m_pointsVisible) {
@ -472,8 +470,6 @@ void SplineChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *o
painter->drawPoints(geometryPoints());
}
reversePainter(painter, clipRect);
if (m_pointLabelsVisible) {
if (m_pointLabelsClipping)
painter->setClipping(true);

View File

@ -559,11 +559,15 @@ void QXYModelMapperPrivate::initializeXYFromModel()
// determine when we should end looping.
}
} else {
// Invalid index right off the bat means series will be left empty, so output a warning
if (!xIndex.isValid())
qWarning() << __FUNCTION__ << QStringLiteral("Invalid X coordinate index in model mapper.");
else if (!yIndex.isValid())
qWarning() << __FUNCTION__ << QStringLiteral("Invalid Y coordinate index in model mapper.");
// Invalid index right off the bat means series will be left empty, so output a warning,
// unless model is also empty
int count = m_orientation == Qt::Vertical ? m_model->rowCount() : m_model->columnCount();
if (count > 0) {
if (!xIndex.isValid())
qWarning() << __FUNCTION__ << QStringLiteral("Invalid X coordinate index in model mapper.");
else if (!yIndex.isValid())
qWarning() << __FUNCTION__ << QStringLiteral("Invalid Y coordinate index in model mapper.");
}
}
blockSeriesSignals(false);

View File

@ -972,14 +972,8 @@ void QXYSeriesPrivate::drawSeriesPointLabels(QPainter *painter, const QVector<QP
// Position text in relation to the point
int pointLabelWidth = fm.width(pointLabel);
QPointF position(points.at(i));
if (!reverseXAxis())
position.setX(position.x() - pointLabelWidth / 2);
else
position.setX(domain()->size().width() - position.x() - pointLabelWidth / 2);
if (!reverseYAxis())
position.setY(position.y() - labelOffset);
else
position.setY(domain()->size().height() - position.y() - labelOffset);
position.setX(position.x() - pointLabelWidth / 2);
position.setY(position.y() - labelOffset);
painter->drawText(position, pointLabel);
}