From 80de54ed93f05f2030c14872a746c643db15356b 2012-09-26 15:12:15 From: Michal Klocek Date: 2012-09-26 15:12:15 Subject: [PATCH] Refactors axis updateGeometry handling * adds verticalaxis class * adds horizontalaxis class * adds updateGeometry logic to base clases * fixes small issues with axis hadnling for datetime,category,barcategory axis --- diff --git a/src/animations/axisanimation.cpp b/src/animations/axisanimation.cpp index cb9b917..6bc49e7 100644 --- a/src/animations/axisanimation.cpp +++ b/src/animations/axisanimation.cpp @@ -69,13 +69,13 @@ void AxisAnimation::setValues(QVector &oldLayout, QVector &newLayo oldLayout.resize(newLayout.count()); for(int i = 0, j = oldLayout.count() - 1; i < (oldLayout.count() + 1) / 2; ++i, --j) { - oldLayout[i] = m_axis->axisType() == ChartAxis::X_AXIS ? rect.left() : rect.bottom(); - oldLayout[j] = m_axis->axisType() == ChartAxis::X_AXIS ? rect.right() : rect.top(); + oldLayout[i] = m_axis->orientation() == Qt::Horizontal ? rect.left() : rect.bottom(); + oldLayout[j] = m_axis->orientation() == Qt::Horizontal ? rect.right() : rect.top(); } } break; case ZoomInAnimation: { - int index = qMin(oldLayout.count() * (m_axis->axisType() == ChartAxis::X_AXIS ? m_point.x() : (1 - m_point.y())), newLayout.count() - (qreal)1.0); + int index = qMin(oldLayout.count() * (m_axis->orientation() == Qt::Horizontal ? m_point.x() : (1 - m_point.y())), newLayout.count() - (qreal)1.0); oldLayout.resize(newLayout.count()); for(int i = 0; i < oldLayout.count(); i++) @@ -100,7 +100,7 @@ void AxisAnimation::setValues(QVector &oldLayout, QVector &newLayo oldLayout.resize(newLayout.count()); QRectF rect = m_axis->gridGeometry(); for(int i = 0, j = oldLayout.count() - 1; i < oldLayout.count(); ++i, --j) - oldLayout[i] = m_axis->axisType() == ChartAxis::X_AXIS ? rect.left() : rect.top(); + oldLayout[i] = m_axis->orientation() == Qt::Horizontal ? rect.left() : rect.top(); } break; } diff --git a/src/axis/axis.pri b/src/axis/axis.pri index 350f8b4..e8e8625 100644 --- a/src/axis/axis.pri +++ b/src/axis/axis.pri @@ -13,6 +13,8 @@ DEPENDPATH += $$PWD \ SOURCES += \ $$PWD/chartaxis.cpp \ $$PWD/qabstractaxis.cpp \ + $$PWD/verticalaxis.cpp \ + $$PWD/horizontalaxis.cpp \ $$PWD/valueaxis/chartvalueaxisx.cpp \ $$PWD/valueaxis/chartvalueaxisy.cpp \ $$PWD/valueaxis/qvalueaxis.cpp \ @@ -21,11 +23,13 @@ SOURCES += \ $$PWD/barcategoryaxis/qbarcategoryaxis.cpp \ $$PWD/categoryaxis/chartcategoryaxisx.cpp \ $$PWD/categoryaxis/chartcategoryaxisy.cpp \ - $$PWD/categoryaxis/qcategoryaxis.cpp + $$PWD/categoryaxis/qcategoryaxis.cpp PRIVATE_HEADERS += \ $$PWD/chartaxis_p.h \ $$PWD/qabstractaxis_p.h \ + $$PWD/verticalaxis_p.h \ + $$PWD/horizontalaxis_p.h \ $$PWD/valueaxis/chartvalueaxisx_p.h \ $$PWD/valueaxis/chartvalueaxisy_p.h \ $$PWD/valueaxis/qvalueaxis_p.h \ diff --git a/src/axis/barcategoryaxis/chartbarcategoryaxisx.cpp b/src/axis/barcategoryaxis/chartbarcategoryaxisx.cpp index bec4b4e..aaed0a4 100644 --- a/src/axis/barcategoryaxis/chartbarcategoryaxisx.cpp +++ b/src/axis/barcategoryaxis/chartbarcategoryaxisx.cpp @@ -25,14 +25,12 @@ #include #include -static int label_padding = 5; - QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartBarCategoryAxisX::ChartBarCategoryAxisX(QBarCategoryAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), +ChartBarCategoryAxisX::ChartBarCategoryAxisX(QBarCategoryAxis *axis,ChartPresenter *presenter) : HorizontalAxis(axis,presenter), m_categoriesAxis(axis) { - + setLabelBetweenTicks(true); } ChartBarCategoryAxisX::~ChartBarCategoryAxisX() @@ -48,23 +46,22 @@ QVector ChartBarCategoryAxisX::calculateLayout() const QVector points; points.resize(count+2); - const qreal delta = m_gridRect.width()/(count); - qreal offset =-m_min-0.5; + const QRectF& gridRect = gridGeometry(); + + const qreal delta = gridRect.width()/(count); + qreal offset =-min()-0.5; if(delta<1) return points; - if(offset<=0) { - offset = int(offset * m_gridRect.width()/(m_max - m_min))%int(delta) + delta; + if(offset<0) { + offset = int(offset * gridRect.width()/(max() - min()))%int(delta) + delta; } else { - offset = int(offset * m_gridRect.width()/(m_max - m_min))%int(delta); + offset = int(offset * gridRect.width()/(max() - min()))%int(delta); } - points[0] = m_gridRect.left(); - points[count+1] = m_gridRect.right(); - - for (int i = 0; i < count; ++i) { - qreal x = offset + i * delta + m_gridRect.left(); + for (int i = -1; i < count+1; ++i) { + qreal x = offset + i * delta + gridRect.left(); points[i+1] = x; } return points; @@ -72,11 +69,12 @@ QVector ChartBarCategoryAxisX::calculateLayout() const QStringList ChartBarCategoryAxisX::createCategoryLabels(const QVector& layout) const { - QStringList result; + QStringList result ; + const QRectF& gridRect = gridGeometry(); - qreal d = (m_max - m_min)/m_gridRect.width(); + qreal d = (max() - min())/gridRect.width(); for (int i = 0;i < layout.count()-1; ++i) { - qreal x = qFloor((((layout[i+1] + layout[i])/2-m_gridRect.left())*d + m_min+0.5)); + qreal x = qFloor((((layout[i] + layout[i+1])/2-gridRect.left())*d + min()+0.5)); if ((x < m_categoriesAxis->categories().count()) && (x >= 0)) { result << m_categoriesAxis->categories().at(x); } @@ -93,55 +91,9 @@ QStringList ChartBarCategoryAxisX::createCategoryLabels(const QVector& la void ChartBarCategoryAxisX::updateGeometry() { const QVector& layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList = createCategoryLabels(layout); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - const qreal delta = m_gridRect.width()/(m_categoriesAxis->d_ptr->count()); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine( m_gridRect.left(), m_gridRect.bottom(), m_gridRect.right(), m_gridRect.bottom()); - - qreal width = m_gridRect.left(); - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine(layout[i], m_gridRect.top(), layout[i], m_gridRect.bottom()); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - labelItem->setText(ticksList.at(i)); - const QRectF& rect = labelItem->boundingRect(); - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - - if(i==0){ - labelItem->setPos(layout[i+1] - (delta)/2 - center.x(), m_gridRect.bottom() + label_padding); - }else{ - labelItem->setPos(layout[i] + (delta)/2 - center.x(), m_gridRect.bottom() + label_padding); - } - - if(labelItem->pos().x()<=width || labelItem->pos().x()+ rect.width()> m_gridRect.right()) { - labelItem->setVisible(false); - } - else { - labelItem->setVisible(true); - width=rect.width()+labelItem->pos().x(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(layout[i-1], m_gridRect.top(),layout[i]-layout[i-1], m_gridRect.height()); - } - lineItem = static_cast(axis.at(i+1)); - lineItem->setLine(layout[i], m_gridRect.bottom(),layout[i], m_gridRect.bottom()+5); - } + setLabels(createCategoryLabels(layout)); + HorizontalAxis::updateGeometry(); } void ChartBarCategoryAxisX::handleAxisUpdated() @@ -158,7 +110,7 @@ QSizeF ChartBarCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constra { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); QStringList ticksList = createCategoryLabels(ChartAxis::layout()); @@ -168,7 +120,7 @@ QSizeF ChartBarCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constra switch (which) { case Qt::MinimumSize: width = fn.boundingRect("...").width(); - height = fn.height()+label_padding; + height = fn.height()+labelPadding(); width=qMax(width,base.width()); height+=base.height(); sh = QSizeF(width,height); @@ -179,7 +131,7 @@ QSizeF ChartBarCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constra { QRectF rect = fn.boundingRect(ticksList.at(i)); width+=rect.width(); - height=qMax(rect.height()+label_padding,height); + height=qMax(rect.height()+labelPadding(),height); } width=qMax(width,base.width()); height+=base.height(); diff --git a/src/axis/barcategoryaxis/chartbarcategoryaxisx_p.h b/src/axis/barcategoryaxis/chartbarcategoryaxisx_p.h index 16da68c..c7df385 100644 --- a/src/axis/barcategoryaxis/chartbarcategoryaxisx_p.h +++ b/src/axis/barcategoryaxis/chartbarcategoryaxisx_p.h @@ -30,21 +30,19 @@ #ifndef CHARTBARCATEGORYAXISX_H #define CHARTBARCATEGORYAXISX_H -#include "chartaxis_p.h" +#include "horizontalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; class ChartPresenter; class QBarCategoryAxis; -class ChartBarCategoryAxisX : public ChartAxis +class ChartBarCategoryAxisX : public HorizontalAxis { public: ChartBarCategoryAxisX(QBarCategoryAxis *axis, ChartPresenter *presenter); ~ChartBarCategoryAxisX(); - AxisType axisType() const { return X_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: QVector calculateLayout() const; diff --git a/src/axis/barcategoryaxis/chartbarcategoryaxisy.cpp b/src/axis/barcategoryaxis/chartbarcategoryaxisy.cpp index 831cd04..843d73c 100644 --- a/src/axis/barcategoryaxis/chartbarcategoryaxisy.cpp +++ b/src/axis/barcategoryaxis/chartbarcategoryaxisy.cpp @@ -23,15 +23,13 @@ #include "qbarcategoryaxis_p.h" #include #include -#include - -static int label_padding = 5; QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartBarCategoryAxisY::ChartBarCategoryAxisY(QBarCategoryAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), +ChartBarCategoryAxisY::ChartBarCategoryAxisY(QBarCategoryAxis *axis,ChartPresenter *presenter) : VerticalAxis(axis,presenter), m_categoriesAxis(axis) { + setLabelBetweenTicks(true); } ChartBarCategoryAxisY::~ChartBarCategoryAxisY() @@ -47,23 +45,22 @@ QVector ChartBarCategoryAxisY::calculateLayout() const QVector points; points.resize(count+2); - const qreal delta = m_gridRect.height()/(count); - qreal offset = - m_min - 0.5; + const QRectF& gridRect = gridGeometry(); + + const qreal delta = gridRect.height()/(count); + qreal offset = - min() - 0.5; if(delta<1) return points; - if(offset<=0) { - offset = int(offset * m_gridRect.height()/(m_max - m_min))%int(delta) + delta; + if(offset<0) { + offset = int(offset * gridRect.height()/(max() - min()))%int(delta) + delta; } else { - offset = int(offset * m_gridRect.height()/(m_max - m_min))%int(delta); + offset = int(offset * gridRect.height()/(max() - min()))%int(delta); } - points[0] = m_gridRect.bottom(); - points[count+1] = m_gridRect.top(); - - for (int i = 0; i < count; ++i) { - int y = m_gridRect.bottom() - i * delta - offset; + for (int i = -1; i < count +1; ++i) { + int y = gridRect.bottom() - i * delta - offset; points[i+1] = y; } return points; @@ -72,10 +69,10 @@ QVector ChartBarCategoryAxisY::calculateLayout() const QStringList ChartBarCategoryAxisY::createCategoryLabels(const QVector& layout) const { QStringList result; - - qreal d = (m_max - m_min)/m_gridRect.height(); + const QRectF& gridRect = gridGeometry(); + qreal d = (max() - min())/gridRect.height(); for (int i = 0;i < layout.count()-1; ++i) { - qreal x = qFloor(((m_gridRect.height()- (layout[i+1] + layout[i])/2 + m_gridRect.top())*d + m_min+0.5)); + qreal x = qFloor(((gridRect.height()- (layout[i+1] + layout[i])/2 + gridRect.top())*d + min()+0.5)); if ((x < m_categoriesAxis->categories().count()) && (x >= 0)) { result << m_categoriesAxis->categories().at(x); } @@ -91,56 +88,9 @@ QStringList ChartBarCategoryAxisY::createCategoryLabels(const QVector& la void ChartBarCategoryAxisY::updateGeometry() { const QVector& layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList = createCategoryLabels(layout); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - const qreal delta = m_gridRect.height()/(m_categoriesAxis->d_ptr->count()); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine(m_gridRect.left() , m_gridRect.top(), m_gridRect.left(), m_gridRect.bottom()); - - qreal height = m_gridRect.bottom(); - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine(m_gridRect.left() , layout[i], m_gridRect.right(), layout[i]); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - labelItem->setText(ticksList.at(i)); - const QRectF& rect = labelItem->boundingRect(); - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - - if(i==0) { - labelItem->setPos(m_gridRect.left() - rect.width() - label_padding ,layout[i+1] + (delta)/2 - center.y()); - } - else { - labelItem->setPos(m_gridRect.left() - rect.width() - label_padding ,layout[i] - (delta)/2 - center.y()); - } - - if(labelItem->pos().y()+rect.height()>= height || labelItem->pos().y() < m_gridRect.top()) { - labelItem->setVisible(false); - } - else { - labelItem->setVisible(true); - height=labelItem->pos().y(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(m_gridRect.left(),layout[i],m_gridRect.width(),layout[i-1]-layout[i]); - } - lineItem = static_cast(axis.at(i+1)); - lineItem->setLine(m_gridRect.left()-5,layout[i],m_gridRect.left(),layout[i]); - } + setLabels(createCategoryLabels(layout)); + VerticalAxis::updateGeometry(); } void ChartBarCategoryAxisY::handleAxisUpdated() @@ -160,7 +110,7 @@ QSizeF ChartBarCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constra { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); QStringList ticksList = createCategoryLabels(ChartAxis::layout()); @@ -169,7 +119,7 @@ QSizeF ChartBarCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constra switch (which) { case Qt::MinimumSize: - width = fn.boundingRect("...").width() + label_padding; + width = fn.boundingRect("...").width() + labelPadding(); height = fn.height(); width+=base.width(); height=qMax(height,base.height()); @@ -181,7 +131,7 @@ QSizeF ChartBarCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constra { QRectF rect = fn.boundingRect(ticksList.at(i)); height+=rect.height(); - width=qMax(rect.width()+label_padding,width); + width=qMax(rect.width()+labelPadding(),width); } height=qMax(height,base.height()); width+=base.width(); diff --git a/src/axis/barcategoryaxis/chartbarcategoryaxisy_p.h b/src/axis/barcategoryaxis/chartbarcategoryaxisy_p.h index feb9afa..d0ffb15 100644 --- a/src/axis/barcategoryaxis/chartbarcategoryaxisy_p.h +++ b/src/axis/barcategoryaxis/chartbarcategoryaxisy_p.h @@ -30,21 +30,19 @@ #ifndef CHARTBARCATEGORYAXISY_H #define CHARTBARCATEGORYAXISY_H -#include "chartaxis_p.h" +#include "verticalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; class QBarCategoryAxis; class ChartPresenter; -class ChartBarCategoryAxisY : public ChartAxis +class ChartBarCategoryAxisY : public VerticalAxis { public: ChartBarCategoryAxisY(QBarCategoryAxis *axis, ChartPresenter *presenter); ~ChartBarCategoryAxisY(); - AxisType axisType() const { return Y_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: QVector calculateLayout() const; diff --git a/src/axis/categoryaxis/chartcategoryaxisx.cpp b/src/axis/categoryaxis/chartcategoryaxisx.cpp index cf07892..aaf1aab 100644 --- a/src/axis/categoryaxis/chartcategoryaxisx.cpp +++ b/src/axis/categoryaxis/chartcategoryaxisx.cpp @@ -26,12 +26,12 @@ #include #include -static int label_padding = 5; - QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartCategoryAxisX::ChartCategoryAxisX(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter) +ChartCategoryAxisX::ChartCategoryAxisX(QCategoryAxis *axis,ChartPresenter *presenter) : HorizontalAxis(axis,presenter), + m_axis(axis) { + setLabelBetweenTicks(true); } ChartCategoryAxisX::~ChartCategoryAxisX() @@ -40,99 +40,34 @@ ChartCategoryAxisX::~ChartCategoryAxisX() QVector ChartCategoryAxisX::calculateLayout() const { - QCategoryAxis *axis = qobject_cast(m_chartAxis); - int tickCount = axis->categoriesLabels().count() + 1; + int tickCount = m_axis->categoriesLabels().count() + 1; QVector points; if (tickCount < 2) return points; - qreal range = axis->max() - axis->min(); + const QRectF& gridRect = gridGeometry(); + qreal range = m_axis->max() - m_axis->min(); if (range > 0) { points.resize(tickCount); - qreal scale = m_gridRect.width() / range; + qreal scale = gridRect.width() / range; for (int i = 0; i < tickCount; ++i) if (i < tickCount - 1) { - int x = (axis->startValue(axis->categoriesLabels().at(i)) - axis->min()) * scale + m_gridRect.left(); + int x = (m_axis->startValue(m_axis->categoriesLabels().at(i)) - m_axis->min()) * scale + gridRect.left(); points[i] = x; } else { - int x = (axis->endValue(axis->categoriesLabels().at(i - 1)) - axis->min()) * scale + m_gridRect.left(); + int x = (m_axis->endValue(m_axis->categoriesLabels().at(i - 1)) - m_axis->min()) * scale + gridRect.left(); points[i] = x; } } + return points; } void ChartCategoryAxisX::updateGeometry() { - const QVector& layout = ChartAxis::layout(); - - if(layout.isEmpty()) return; - - QCategoryAxis *categoryAxis = qobject_cast(m_chartAxis); - QStringList ticksList = categoryAxis->categoriesLabels(); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - - for (int i = 0; i < labels.count(); i++) { - labels.at(i)->setVisible(false); - } - // axis base line - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine(m_gridRect.left(), m_gridRect.bottom(), m_gridRect.right(), m_gridRect.bottom()); - - for (int i = 0; i < layout.size(); ++i) { - - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - if (i < ticksList.count()) { - labelItem->setText(ticksList.at(i)); - } - const QRectF& rect = labelItem->boundingRect(); - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - - if (i < layout.size() - 1) { - labelItem->setPos(layout[i] + (layout[i + 1] - layout[i]) / 2 - center.x(), m_gridRect.bottom() + label_padding); - } else { - labelItem->setPos(layout[i] - center.x(), m_gridRect.bottom() + label_padding); - } - - // check if the label should be shown - if (labelItem->pos().x() + center.x() < m_gridRect.left() || labelItem->pos().x() + center.x() > m_gridRect.right()) - labelItem->setVisible(false); - else - labelItem->setVisible(true); - - if ((i + 1) % 2 && i > 1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i / 2 - 1)); - rectItem->setRect(layout[i - 1],m_gridRect.top(),layout[i]-layout[i - 1],m_gridRect.height()); - } - - // grid lines and axis line ticks - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setPos(layout[i], m_gridRect.top()); - lineItem->setLine(0, 0, 0, m_gridRect.height()); - - QGraphicsLineItem *tickLineItem = static_cast(axis.at(i+1)); - tickLineItem->setPos(layout[i], m_gridRect.bottom()); - tickLineItem->setLine(0, 0, 0, 5); - - // check if the grid line and the axis tick should be shown - if (lineItem->pos().x() < m_gridRect.left() || lineItem->pos().x() > m_gridRect.right()) { - lineItem->setVisible(false); - tickLineItem->setVisible(false); - } else { - lineItem->setVisible(true); - tickLineItem->setVisible(true); - } - - } - + setLabels(m_axis->categoriesLabels()<<""); + HorizontalAxis::updateGeometry(); } void ChartCategoryAxisX::handleAxisUpdated() @@ -145,7 +80,7 @@ QSizeF ChartCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constraint { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); QStringList ticksList ; //TODO: @@ -155,7 +90,7 @@ QSizeF ChartCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constraint switch (which) { case Qt::MinimumSize: width = fn.boundingRect("...").width(); - height = fn.height() + label_padding; + height = fn.height() + labelPadding(); width=qMax(width,base.width()); height+=base.height(); sh = QSizeF(width,height); @@ -166,7 +101,7 @@ QSizeF ChartCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constraint { QRectF rect = fn.boundingRect(ticksList.at(i)); width+=rect.width(); - height=qMax(rect.height()+label_padding,height); + height=qMax(rect.height()+labelPadding(),height); } width=qMax(width,base.width()); height+=base.height(); diff --git a/src/axis/categoryaxis/chartcategoryaxisx_p.h b/src/axis/categoryaxis/chartcategoryaxisx_p.h index 5a3009b..5a49916 100644 --- a/src/axis/categoryaxis/chartcategoryaxisx_p.h +++ b/src/axis/categoryaxis/chartcategoryaxisx_p.h @@ -30,27 +30,27 @@ #ifndef CHARTCATEGORYAXISX_H #define CHARTCATEGORYAXISX_H -#include "chartaxis_p.h" +#include "horizontalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; +class QCategoryAxis; class ChartPresenter; -class ChartCategoryAxisX : public ChartAxis +class ChartCategoryAxisX : public HorizontalAxis { public: - ChartCategoryAxisX(QAbstractAxis *axis, ChartPresenter *presenter); + ChartCategoryAxisX(QCategoryAxis *axis, ChartPresenter *presenter); ~ChartCategoryAxisX(); - AxisType axisType() const { return X_AXIS; } QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: QVector calculateLayout() const; void updateGeometry(); - - Q_SLOTS +Q_SLOTS void handleAxisUpdated(); +private: + QCategoryAxis *m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/categoryaxis/chartcategoryaxisy.cpp b/src/axis/categoryaxis/chartcategoryaxisy.cpp index 03b1091..8294d73 100644 --- a/src/axis/categoryaxis/chartcategoryaxisy.cpp +++ b/src/axis/categoryaxis/chartcategoryaxisy.cpp @@ -26,12 +26,12 @@ #include #include -static int label_padding = 5; - QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartCategoryAxisY::ChartCategoryAxisY(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter) +ChartCategoryAxisY::ChartCategoryAxisY(QCategoryAxis *axis,ChartPresenter *presenter) : VerticalAxis(axis,presenter), + m_axis(axis) { + setLabelBetweenTicks(true); } ChartCategoryAxisY::~ChartCategoryAxisY() @@ -40,23 +40,23 @@ ChartCategoryAxisY::~ChartCategoryAxisY() QVector ChartCategoryAxisY::calculateLayout() const { - QCategoryAxis *axis = qobject_cast(m_chartAxis); - int tickCount = axis->categoriesLabels().count() + 1; + int tickCount = m_axis->categoriesLabels().count() + 1; QVector points; if (tickCount < 2) return points; - qreal range = axis->max() - axis->min(); + const QRectF& gridRect = gridGeometry(); + qreal range = m_axis->max() - m_axis->min(); if (range > 0) { points.resize(tickCount); - qreal scale = m_gridRect.height() / range; + qreal scale = gridRect.height() / range; for (int i = 0; i < tickCount; ++i) if (i < tickCount - 1) { - int y = -(axis->startValue(axis->categoriesLabels().at(i)) - axis->min()) * scale + m_gridRect.bottom(); + int y = -(m_axis->startValue(m_axis->categoriesLabels().at(i)) - m_axis->min()) * scale + gridRect.bottom(); points[i] = y; } else { - int y = -(axis->endValue(axis->categoriesLabels().at(i - 1)) - axis->min()) * scale + m_gridRect.bottom(); + int y = -(m_axis->endValue(m_axis->categoriesLabels().at(i - 1)) - m_axis->min()) * scale + gridRect.bottom(); points[i] = y; } } @@ -66,77 +66,8 @@ QVector ChartCategoryAxisY::calculateLayout() const void ChartCategoryAxisY::updateGeometry() { - const QVector &layout = ChartAxis::layout(); - - if(layout.isEmpty()) { - return; - } - - QCategoryAxis *categoryAxis = qobject_cast(m_chartAxis); - QStringList ticksList = categoryAxis->categoriesLabels(); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - for (int i = 0; i < labels.count(); i++) { - labels.at(i)->setVisible(false); - } - - // axis base line - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine(m_gridRect.left() , m_gridRect.top(), m_gridRect.left(), m_gridRect.bottom()); - - for (int i = 0; i < layout.size(); ++i) { - - // label items - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - if (i < ticksList.count()) { - labelItem->setText(ticksList.at(i)); - } - const QRectF& rect = labelItem->boundingRect(); - - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - - - if (i < layout.size() - 1) - labelItem->setPos(m_gridRect.left() - rect.width() - label_padding , layout[i] + (layout[i + 1] - layout[i]) / 2 - center.y()); - else - labelItem->setPos(m_gridRect.left() - rect.width() - label_padding , layout[i]-center.y()); - - // check if the label should be shown - if (labelItem->pos().y() + center.y() < m_gridRect.top() || labelItem->pos().y() + center.y() > m_gridRect.bottom()) - labelItem->setVisible(false); - else - labelItem->setVisible(true); - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(m_gridRect.left(),layout[i],m_gridRect.width(),layout[i-1]-layout[i]); - } - - // grid lines and axis line ticks - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setPos(m_gridRect.left(), layout[i]); - lineItem->setLine(0, 0, m_gridRect.width(), 0); - - QGraphicsLineItem *tickLineItem = static_cast(axis.at(i+1)); - tickLineItem->setPos(m_gridRect.left(), layout[i]); - tickLineItem->setLine(-5, 0, 0, 0); - - // check if the grid line and the axis tick should be shown - if (lineItem->pos().y() < m_gridRect.top() || lineItem->pos().y() > m_gridRect.bottom()) { - lineItem->setVisible(false); - tickLineItem->setVisible(false); - } else { - lineItem->setVisible(true); - tickLineItem->setVisible(true); - } - - } - + setLabels(m_axis->categoriesLabels()<<""); + VerticalAxis::updateGeometry(); } void ChartCategoryAxisY::handleAxisUpdated() @@ -149,7 +80,7 @@ QSizeF ChartCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constraint { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); QStringList ticksList; //TODO:: @@ -158,7 +89,7 @@ QSizeF ChartCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constraint switch (which) { case Qt::MinimumSize: - width = fn.boundingRect("...").width()+label_padding; + width = fn.boundingRect("...").width()+labelPadding(); height = fn.height(); width=qMax(width,base.width()); height+=base.height(); @@ -170,7 +101,7 @@ QSizeF ChartCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constraint { QRectF rect = fn.boundingRect(ticksList.at(i)); height+=rect.height(); - width=qMax(rect.width()+label_padding,width); + width=qMax(rect.width()+labelPadding(),width); } height=qMax(height,base.height()); width+=base.width(); diff --git a/src/axis/categoryaxis/chartcategoryaxisy_p.h b/src/axis/categoryaxis/chartcategoryaxisy_p.h index ebc358e..6b99548 100644 --- a/src/axis/categoryaxis/chartcategoryaxisy_p.h +++ b/src/axis/categoryaxis/chartcategoryaxisy_p.h @@ -30,27 +30,27 @@ #ifndef CHARTCATEGORYAXISY_H #define CHARTCATEGORYAXISY_H -#include "chartaxis_p.h" +#include "verticalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; +class QCategoryAxis; class ChartPresenter; -class ChartCategoryAxisY : public ChartAxis +class ChartCategoryAxisY : public VerticalAxis { public: - ChartCategoryAxisY(QAbstractAxis *axis, ChartPresenter *presenter); + ChartCategoryAxisY(QCategoryAxis *axis, ChartPresenter *presenter); ~ChartCategoryAxisY(); - AxisType axisType() const { return Y_AXIS; } QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: QVector calculateLayout() const; void updateGeometry(); - -public Q_SLOTS: +Q_SLOTS void handleAxisUpdated(); +private: + QCategoryAxis *m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/chartaxis.cpp b/src/axis/chartaxis.cpp index ade1ee1..da7acac 100644 --- a/src/axis/chartaxis.cpp +++ b/src/axis/chartaxis.cpp @@ -43,7 +43,8 @@ ChartAxis::ChartAxis(QAbstractAxis *axis,ChartPresenter *presenter) : ChartEleme m_min(0), m_max(0), m_animation(0), - m_labelPadding(5) + m_labelPadding(5), + m_labelBetween(false) { //initial initialization m_arrow->setZValue(ChartPresenter::AxisZValue); @@ -76,12 +77,17 @@ void ChartAxis::setLayout(QVector &layout) void ChartAxis::createItems(int count) { if (m_arrow->children().size() == 0) - m_arrow->addToGroup(new AxisItem(this,presenter()->rootItem())); + m_arrow->addToGroup(new AxisItem(this,presenter()->rootItem())); + if (m_grid->children().size() == 0){ + for(int i = 0 ; i < 2 ;i ++) + m_grid->addToGroup(new QGraphicsLineItem(presenter()->rootItem())); + } for (int i = 0; i < count; ++i) { m_grid->addToGroup(new QGraphicsLineItem(presenter()->rootItem())); m_labels->addToGroup(new QGraphicsSimpleTextItem(presenter()->rootItem())); m_arrow->addToGroup(new QGraphicsLineItem(presenter()->rootItem())); - if ((m_grid->childItems().size())%2 && m_grid->childItems().size()>2) m_shades->addToGroup(new QGraphicsRectItem(presenter()->rootItem())); + if ((m_grid->childItems().size())%2 && m_grid->childItems().size()>2) + m_shades->addToGroup(new QGraphicsRectItem(presenter()->rootItem())); } } @@ -409,36 +415,9 @@ void ChartAxis::axisSelected() //TODO: axis clicked; } - -QStringList ChartAxis::createNumberLabels(qreal min, qreal max, int ticks) const +void ChartAxis::setLabelBetweenTicks(bool enabled) { - Q_ASSERT(max>min); - Q_ASSERT(ticks>1); - - QStringList labels; - - int n = qMax(int(-qFloor(log10((max-min)/(ticks-1)))),0); - n++; - - QValueAxis *axis = qobject_cast(m_chartAxis); - - QString format = axis->labelFormat(); - - if(format.isNull()) { - for (int i=0; i< ticks; i++) { - qreal value = min + (i * (max - min)/ (ticks-1)); - labels << QString::number(value,'f',n); - } - } - else { - QByteArray array = format.toAscii(); - for (int i=0; i< ticks; i++) { - qreal value = min + (i * (max - min)/ (ticks-1)); - labels << QString().sprintf(array, value); - } - } - - return labels; + m_labelBetween=enabled; } Qt::Orientation ChartAxis::orientation() const @@ -456,6 +435,11 @@ bool ChartAxis::isVisible() return m_chartAxis->isVisible(); } +void ChartAxis::setLabels(const QStringList& labels) +{ + m_labelsList=labels; +} + QSizeF ChartAxis::sizeHint(Qt::SizeHint which, const QSizeF& constraint) const { @@ -492,6 +476,52 @@ QSizeF ChartAxis::sizeHint(Qt::SizeHint which, const QSizeF& constraint) const return sh; } +QStringList ChartAxis::createValueLabels(int ticks) const +{ + Q_ASSERT(m_max>m_min); + Q_ASSERT(ticks>1); + + QStringList labels; + + int n = qMax(int(-qFloor(log10((m_max-m_min)/(ticks-1)))),0); + n++; + + QValueAxis *axis = qobject_cast(m_chartAxis); + + QString format = axis->labelFormat(); + + if(format.isNull()) { + for (int i=0; i< ticks; i++) { + qreal value = m_min + (i * (m_max - m_min)/ (ticks-1)); + labels << QString::number(value,'f',n); + } + } + else { + QByteArray array = format.toAscii(); + for (int i=0; i< ticks; i++) { + qreal value = m_min + (i * (m_max - m_min)/ (ticks-1)); + labels << QString().sprintf(array, value); + } + } + + return labels; +} + +QStringList ChartAxis::createDateTimeLabels(const QString& format,int ticks) const +{ + Q_ASSERT(m_max>m_min); + Q_ASSERT(ticks>1); + QStringList labels; + int n = qMax(int(-floor(log10((m_max-m_min)/(ticks-1)))),0); + n++; + for (int i=0; i< ticks; i++) { + qreal value = m_min + (i * (m_max - m_min)/ (ticks-1)); + labels << QDateTime::fromMSecsSinceEpoch(value).toString(format); + } + + return labels; +} + #include "moc_chartaxis_p.cpp" QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/chartaxis_p.h b/src/axis/chartaxis_p.h index 8beb394..10b0dae 100644 --- a/src/axis/chartaxis_p.h +++ b/src/axis/chartaxis_p.h @@ -47,13 +47,10 @@ class ChartAxis : public ChartElement, public QGraphicsLayoutItem Q_OBJECT Q_INTERFACES(QGraphicsLayoutItem) public: - enum AxisType { X_AXIS, Y_AXIS }; ChartAxis(QAbstractAxis *axis, ChartPresenter *presenter); ~ChartAxis(); - virtual AxisType axisType() const = 0; - void setArrowOpacity(qreal opacity); qreal arrowOpacity() const; void setArrowVisibility(bool visible); @@ -106,20 +103,34 @@ public: QRectF axisGeometry() const { return m_axisRect; } QRectF gridGeometry() const { return m_gridRect; } + void setLabels(const QStringList& labels); + QStringList labels() const { return m_labelsList; } + + void setLabelBetweenTicks(bool enabled); + bool labelBetweenTicks() const { return m_labelBetween; } + virtual QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint = QSizeF()) const; protected: void setGeometry(const QRectF &size){ Q_UNUSED(size);}; virtual void updateGeometry() = 0; virtual QVector calculateLayout() const = 0; - QStringList createNumberLabels(qreal min, qreal max, int ticks) const; + QList lineItems() { return m_grid->childItems(); }; + QList labelItems() { return m_labels->childItems();}; + QList shadeItems() { return m_shades->childItems();}; + QList arrowItems() { return m_arrow->childItems();}; + + QFont font() const { return m_font; } + qreal min() const {return m_min; } + qreal max() const {return m_max; } + QStringList createValueLabels(int ticks) const; + QStringList createDateTimeLabels(const QString& format,int ticks) const; public Q_SLOTS: virtual void handleAxisUpdated(); virtual void handleDomainUpdated(); - private: inline bool isEmpty(); void createItems(int count); @@ -127,10 +138,9 @@ private: void updateLayout(QVector &layout); void axisSelected(); -protected: +private: QAbstractAxis *m_chartAxis; int m_labelsAngle; - //TODO: to be removed QRectF m_axisRect; QRectF m_gridRect; QScopedPointer m_grid; @@ -145,9 +155,11 @@ protected: QFont m_font; QString m_titleText; int m_labelPadding; + QStringList m_labelsList; + bool m_labelBetween; - friend class AxisAnimation; - friend class AxisItem; +friend class AxisAnimation; +friend class AxisItem; }; @@ -170,7 +182,7 @@ protected: QPainterPath shape() const { QPainterPath path = QGraphicsLineItem::shape(); QRectF rect = path.boundingRect(); - path.addRect(rect.adjusted(0, 0, m_axis->axisType() != ChartAxis::X_AXIS ? 8 : 0, m_axis->axisType() != ChartAxis::Y_AXIS ? 8 : 0)); + path.addRect(rect.adjusted(0, 0, m_axis->orientation() != Qt::Horizontal ? 8 : 0, m_axis->orientation() != Qt::Vertical ? 8 : 0)); return path; } diff --git a/src/axis/datetimeaxis/chartdatetimeaxisx.cpp b/src/axis/datetimeaxis/chartdatetimeaxisx.cpp index 97357f8..85fce51 100644 --- a/src/axis/datetimeaxis/chartdatetimeaxisx.cpp +++ b/src/axis/datetimeaxis/chartdatetimeaxisx.cpp @@ -31,8 +31,8 @@ static int label_padding = 5; QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartDateTimeAxisX::ChartDateTimeAxisX(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), -m_tickCount(0) +ChartDateTimeAxisX::ChartDateTimeAxisX(QDateTimeAxis *axis,ChartPresenter *presenter) : HorizontalAxis(axis,presenter), +m_tickCount(0),m_axis(axis) { } @@ -40,31 +40,16 @@ ChartDateTimeAxisX::~ChartDateTimeAxisX() { } -void ChartDateTimeAxisX::createLabels(QStringList &labels,qreal min, qreal max, int ticks) -{ - Q_ASSERT(max>min); - Q_ASSERT(ticks>1); - - QDateTimeAxis *axis = qobject_cast(m_chartAxis); - - int n = qMax(int(-floor(log10((max-min)/(ticks-1)))),0); - n++; - for (int i=0; i< ticks; i++) { - qreal value = min + (i * (max - min)/ (ticks-1)); - labels << QDateTime::fromMSecsSinceEpoch(value).toString(axis->format()); - } -} - QVector ChartDateTimeAxisX::calculateLayout() const { Q_ASSERT(m_tickCount>=2); QVector points; points.resize(m_tickCount); - - const qreal deltaX = m_gridRect.width()/(m_tickCount-1); + const QRectF& gridRect = gridGeometry(); + const qreal deltaX = gridRect.width()/(m_tickCount-1); for (int i = 0; i < m_tickCount; ++i) { - int x = i * deltaX + m_gridRect.left(); + int x = i * deltaX + gridRect.left(); points[i] = x; } return points; @@ -73,58 +58,14 @@ QVector ChartDateTimeAxisX::calculateLayout() const void ChartDateTimeAxisX::updateGeometry() { const QVector& layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList; - - createLabels(ticksList,m_min,m_max,layout.size()); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine(m_gridRect.left(), m_gridRect.bottom(), m_gridRect.right(), m_gridRect.bottom()); - - qreal width = 0; - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine(layout[i], m_gridRect.top(), layout[i], m_gridRect.bottom()); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - labelItem->setText(ticksList.at(i)); - const QRectF& rect = labelItem->boundingRect(); - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - labelItem->setPos(layout[i] - center.x(), m_gridRect.bottom() + label_padding); - - if(labelItem->pos().x()<=width){ - labelItem->setVisible(false); - lineItem->setVisible(false); - }else{ - labelItem->setVisible(true); - lineItem->setVisible(true); - width=rect.width()+labelItem->pos().x(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(layout[i-1],m_gridRect.top(),layout[i]-layout[i-1],m_gridRect.height()); - } - lineItem = static_cast(axis.at(i+1)); - lineItem->setLine(layout[i],m_gridRect.bottom(),layout[i],m_gridRect.bottom()+5); - } + setLabels(createDateTimeLabels(m_axis->format(),layout.size())); + HorizontalAxis::updateGeometry(); } void ChartDateTimeAxisX::handleAxisUpdated() { - //TODO:: fix this - QDateTimeAxis* axis = qobject_cast(m_chartAxis); - m_tickCount = axis->tickCount(); + m_tickCount = m_axis->tickCount(); ChartAxis::handleAxisUpdated(); } @@ -132,7 +73,7 @@ QSizeF ChartDateTimeAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constraint { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; switch (which) { diff --git a/src/axis/datetimeaxis/chartdatetimeaxisx_p.h b/src/axis/datetimeaxis/chartdatetimeaxisx_p.h index c56e309..90481af 100644 --- a/src/axis/datetimeaxis/chartdatetimeaxisx_p.h +++ b/src/axis/datetimeaxis/chartdatetimeaxisx_p.h @@ -30,29 +30,28 @@ #ifndef CHARTDATETIMEAXISX_H #define CHARTDATETIMEAXISX_H -#include "chartaxis_p.h" +#include "horizontalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; +class QDateTimeAxis; class ChartPresenter; -class ChartDateTimeAxisX : public ChartAxis +class ChartDateTimeAxisX : public HorizontalAxis { public: - ChartDateTimeAxisX(QAbstractAxis *axis, ChartPresenter *presenter); + ChartDateTimeAxisX(QDateTimeAxis *axis, ChartPresenter *presenter); ~ChartDateTimeAxisX(); - AxisType axisType() const { return X_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: - void createLabels(QStringList &labels, qreal min, qreal max, int ticks); void handleAxisUpdated(); QVector calculateLayout() const; void updateGeometry(); private: int m_tickCount; + QDateTimeAxis *m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/datetimeaxis/chartdatetimeaxisy.cpp b/src/axis/datetimeaxis/chartdatetimeaxisy.cpp index 21ee91b..8e531a5 100644 --- a/src/axis/datetimeaxis/chartdatetimeaxisy.cpp +++ b/src/axis/datetimeaxis/chartdatetimeaxisy.cpp @@ -31,8 +31,8 @@ static int label_padding = 5; QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartDateTimeAxisY::ChartDateTimeAxisY(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), -m_tickCount(0) +ChartDateTimeAxisY::ChartDateTimeAxisY(QDateTimeAxis *axis,ChartPresenter *presenter) : VerticalAxis(axis,presenter), +m_tickCount(0),m_axis(axis) { } @@ -40,31 +40,16 @@ ChartDateTimeAxisY::~ChartDateTimeAxisY() { } -void ChartDateTimeAxisY::createLabels(QStringList &labels,qreal min, qreal max, int ticks) -{ - Q_ASSERT(max>min); - Q_ASSERT(ticks>1); - - QDateTimeAxis *axis = qobject_cast(m_chartAxis); - - int n = qMax(int(-floor(log10((max-min)/(ticks-1)))),0); - n++; - for (int i=0; i< ticks; i++) { - qreal value = min + (i * (max - min)/ (ticks-1)); - labels << QDateTime::fromMSecsSinceEpoch(value).toString(axis->format()); - } -} - QVector ChartDateTimeAxisY::calculateLayout() const { Q_ASSERT(m_tickCount>=2); QVector points; points.resize(m_tickCount); - - const qreal deltaY = m_gridRect.height()/(m_tickCount-1); + const QRectF& gridRect = gridGeometry(); + const qreal deltaY = gridRect.height()/(m_tickCount-1); for (int i = 0; i < m_tickCount; ++i) { - int y = i * -deltaY + m_gridRect.bottom(); + int y = i * -deltaY + gridRect.bottom(); points[i] = y; } @@ -74,62 +59,14 @@ QVector ChartDateTimeAxisY::calculateLayout() const void ChartDateTimeAxisY::updateGeometry() { const QVector &layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList; - - createLabels(ticksList,m_min,m_max,layout.size()); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - qreal height = m_gridRect.bottom(); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - lineItem->setLine(m_gridRect.left() , m_gridRect.top(), m_gridRect.left(), m_gridRect.bottom()); - - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine(m_gridRect.left() , layout[i], m_gridRect.right(), layout[i]); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - - labelItem->setText(ticksList.at(i)); - const QRectF& rect = labelItem->boundingRect(); - - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - labelItem->setPos(m_gridRect.left() - rect.width() - label_padding , layout[i]-center.y()); - - if(labelItem->pos().y()+rect.height()>height) { - labelItem->setVisible(false); - lineItem->setVisible(false); - } - else { - labelItem->setVisible(true); - lineItem->setVisible(true); - height=labelItem->pos().y(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(m_gridRect.left(),layout[i],m_gridRect.width(),layout[i-1]-layout[i]); - } - lineItem = static_cast(axis.at(i+1)); - lineItem->setLine(m_gridRect.left()-5,layout[i],m_gridRect.left(),layout[i]); - } + setLabels(createDateTimeLabels(m_axis->format(),layout.size())); + VerticalAxis::updateGeometry(); } void ChartDateTimeAxisY::handleAxisUpdated() { - //TODO:: fix this - QDateTimeAxis* axis = qobject_cast(m_chartAxis); - m_tickCount = axis->tickCount(); + m_tickCount = m_axis->tickCount(); ChartAxis::handleAxisUpdated(); } @@ -137,7 +74,7 @@ QSizeF ChartDateTimeAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constraint { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; switch (which) { diff --git a/src/axis/datetimeaxis/chartdatetimeaxisy_p.h b/src/axis/datetimeaxis/chartdatetimeaxisy_p.h index e33fb5a..b565311 100644 --- a/src/axis/datetimeaxis/chartdatetimeaxisy_p.h +++ b/src/axis/datetimeaxis/chartdatetimeaxisy_p.h @@ -30,28 +30,27 @@ #ifndef CHARTDATETIMEAXISY_H #define CHARTDATETIMEAXISY_H -#include "chartaxis_p.h" +#include "verticalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; +class QDateTimeAxis; class ChartPresenter; -class ChartDateTimeAxisY : public ChartAxis +class ChartDateTimeAxisY : public VerticalAxis { public: - ChartDateTimeAxisY(QAbstractAxis *axis, ChartPresenter *presenter); + ChartDateTimeAxisY(QDateTimeAxis *axis, ChartPresenter *presenter); ~ChartDateTimeAxisY(); - AxisType axisType() const { return Y_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: - void createLabels(QStringList &labels, qreal min, qreal max, int ticks); QVector calculateLayout() const; void updateGeometry(); void handleAxisUpdated(); private: int m_tickCount; + QDateTimeAxis *m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/horizontalaxis.cpp b/src/axis/horizontalaxis.cpp new file mode 100644 index 0000000..032d9ba --- /dev/null +++ b/src/axis/horizontalaxis.cpp @@ -0,0 +1,136 @@ +/**************************************************************************** +** +** 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 "horizontalaxis_p.h" +#include "qabstractaxis.h" +#include +#include + +QTCOMMERCIALCHART_BEGIN_NAMESPACE + +HorizontalAxis::HorizontalAxis(QAbstractAxis *axis, ChartPresenter *presenter):ChartAxis(axis,presenter) +{ +} + +HorizontalAxis::~HorizontalAxis() +{ +} + +void HorizontalAxis::updateGeometry() +{ + const QVector& layout = ChartAxis::layout(); + + if(layout.isEmpty()) return; + + QStringList ticksList = labels(); + + QList lines = lineItems(); + QList labels = labelItems(); + QList shades = shadeItems(); + QList axis = arrowItems(); + + Q_ASSERT(labels.size() == ticksList.size()); + Q_ASSERT(layout.size() == ticksList.size()); + + const QRectF& axisRect = axisGeometry(); + const QRectF& gridRect = gridGeometry(); + + //arrow + QGraphicsLineItem *arrowItem = static_cast(axis.at(0)); + + if (alignment()==Qt::AlignTop) + arrowItem->setLine(gridRect.left(), axisRect.bottom(), gridRect.right(), axisRect.bottom()); + else if(alignment()==Qt::AlignBottom) + arrowItem->setLine(gridRect.left(), axisRect.top(), gridRect.right(), axisRect.top()); + + qreal width = 0; + + for (int i = 0; i < layout.size(); ++i) { + + QGraphicsLineItem *gridItem = static_cast(lines.at(i)); + QGraphicsLineItem *tickItem = static_cast(axis.at(i+1)); + QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); + + //grid line + gridItem->setLine(layout[i], gridRect.top(), layout[i], gridRect.bottom()); + + //label text + labelItem->setText(ticksList.at(i)); + const QRectF& rect = labelItem->boundingRect(); + QPointF center = rect.center(); + labelItem->setTransformOriginPoint(center.x(), center.y()); + + //ticks and label position + if (alignment()==Qt::AlignTop){ + labelItem->setPos(layout[i] - center.x(), axisRect.bottom() - rect.height() - labelPadding()); + tickItem->setLine(layout[i],axisRect.bottom(),layout[i],axisRect.bottom() - labelPadding()); + }else if(alignment()==Qt::AlignBottom){ + labelItem->setPos(layout[i] - center.x(), axisRect.top() + labelPadding()); + tickItem->setLine(layout[i],axisRect.top(),layout[i],axisRect.top() + labelPadding()); + } + + if(labelBetweenTicks()&& i+1!=layout.size()) { + const qreal delta = (layout[i+1] - layout[i])/2; + labelItem->setPos(layout[i] + delta - center.x(), labelItem->pos().y()); + } + + //overlap detection + if(labelItem->pos().x() <= width || + labelItem->pos().x() < axisRect.left() || + labelItem->pos().x() + rect.width() > axisRect.right()) { + labelItem->setVisible(false); + gridItem->setVisible(false); + tickItem->setVisible(false); + } + else { + labelItem->setVisible(true); + gridItem->setVisible(true); + tickItem->setVisible(true); + width=rect.width()+labelItem->pos().x(); + } + + //shades + if ((i+1)%2 && i>1) { + QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); + rectItem->setRect(layout[i-1],gridRect.top(),layout[i]-layout[i-1],gridRect.height()); + } + + // check if the grid line and the axis tick should be shown + qreal x = gridItem->line().p1().x(); + if (x < gridRect.left() || x > gridRect.right()) { + gridItem->setVisible(false); + tickItem->setVisible(false); + if( labelBetweenTicks() && ( labelItem->pos().x() < gridRect.left() || labelItem->pos().x() + rect.width() > gridRect.right())) + labelItem->setVisible(false); + } + + } + + //begin/end grid line in case labels between + if(labelBetweenTicks()) { + QGraphicsLineItem *gridLine; + gridLine = static_cast(lines.at(layout.size())); + gridLine->setLine(gridRect.right(), gridRect.top(), gridRect.right(), gridRect.bottom()); + gridLine = static_cast(lines.at(layout.size()+1)); + gridLine->setLine(gridRect.left(), gridRect.top(), gridRect.left(), gridRect.bottom()); + } +} + +QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/horizontalaxis_p.h b/src/axis/horizontalaxis_p.h new file mode 100644 index 0000000..488ba5c --- /dev/null +++ b/src/axis/horizontalaxis_p.h @@ -0,0 +1,49 @@ +/**************************************************************************** +** +** 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$ +** +****************************************************************************/ + +// W A R N I N G +// ------------- +// +// This file is not part of the QtCommercial Chart API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. + +#ifndef HORIZONTALAXIS_P_H_ +#define HORIZONTALAXIS_P_H_ + +#include "chartaxis_p.h" + +QTCOMMERCIALCHART_BEGIN_NAMESPACE + +class HorizontalAxis : public ChartAxis +{ +public: + HorizontalAxis(QAbstractAxis *axis, ChartPresenter *presenter); + ~HorizontalAxis(); +protected: + void updateGeometry(); + +}; + +QTCOMMERCIALCHART_END_NAMESPACE + +#endif diff --git a/src/axis/valueaxis/chartvalueaxisx.cpp b/src/axis/valueaxis/chartvalueaxisx.cpp index 67a2875..f3a7272 100644 --- a/src/axis/valueaxis/chartvalueaxisx.cpp +++ b/src/axis/valueaxis/chartvalueaxisx.cpp @@ -30,8 +30,8 @@ QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartValueAxisX::ChartValueAxisX(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), - m_tickCount(0) +ChartValueAxisX::ChartValueAxisX(QValueAxis *axis,ChartPresenter *presenter) : HorizontalAxis(axis,presenter), + m_tickCount(0),m_axis(axis) { } @@ -46,9 +46,10 @@ QVector ChartValueAxisX::calculateLayout() const QVector points; points.resize(m_tickCount); - const qreal deltaX = m_gridRect.width()/(m_tickCount-1); + const QRectF& gridRect = gridGeometry(); + const qreal deltaX = gridRect.width()/(m_tickCount-1); for (int i = 0; i < m_tickCount; ++i) { - int x = i * deltaX + m_gridRect.left(); + int x = i * deltaX + gridRect.left(); points[i] = x; } return points; @@ -57,74 +58,15 @@ QVector ChartValueAxisX::calculateLayout() const void ChartValueAxisX::updateGeometry() { const QVector& layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList = createNumberLabels(m_min,m_max,layout.size()); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - //lineItem->setLine(m_gridRect.left(), m_gridRect.bottom(), m_gridRect.right(), m_gridRect.bottom()); - - if (m_chartAxis->alignment()==Qt::AlignTop) - lineItem->setLine(m_gridRect.left(), m_axisRect.bottom(), m_gridRect.right(), m_axisRect.bottom()); - else if(m_chartAxis->alignment()==Qt::AlignBottom) - lineItem->setLine(m_gridRect.left(), m_axisRect.top(), m_gridRect.right(), m_axisRect.top()); - - qreal width = 0; - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine(layout[i], m_gridRect.top(), layout[i], m_gridRect.bottom()); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - labelItem->setText(ticksList.at(i)); - const QRectF& rect = labelItem->boundingRect(); - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - //labelItem->setPos(layout[i] - center.x(), m_gridRect.bottom() + label_padding); - - if (m_chartAxis->alignment()==Qt::AlignTop) - labelItem->setPos(layout[i] - center.x(), m_axisRect.bottom() - rect.height() - labelPadding()); - else if(m_chartAxis->alignment()==Qt::AlignBottom) - labelItem->setPos(layout[i] - center.x(), m_axisRect.top() + labelPadding()); - - if(labelItem->pos().x() <= width || - labelItem->pos().x() < m_axisRect.left() || - labelItem->pos().x() + rect.width() > m_axisRect.right()){ - labelItem->setVisible(false); - lineItem->setVisible(false); - }else{ - labelItem->setVisible(true); - lineItem->setVisible(true); - width=rect.width()+labelItem->pos().x(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect(layout[i-1],m_gridRect.top(),layout[i]-layout[i-1],m_gridRect.height()); - } - lineItem = static_cast(axis.at(i+1)); - //lineItem->setLine(layout[i],m_gridRect.bottom(),layout[i],m_gridRect.bottom()+5); - - if (m_chartAxis->alignment()==Qt::AlignTop) - lineItem->setLine(layout[i],m_axisRect.bottom(),layout[i],m_axisRect.bottom() - labelPadding()); - else if(m_chartAxis->alignment()==Qt::AlignBottom) - lineItem->setLine(layout[i],m_axisRect.top(),layout[i],m_axisRect.top() + labelPadding()); - - } + setLabels(createValueLabels(layout.size())); + HorizontalAxis::updateGeometry(); } void ChartValueAxisX::handleAxisUpdated() { - QValueAxis* axis = qobject_cast(m_chartAxis); - if (m_tickCount != axis->tickCount()) { - m_tickCount = axis->tickCount(); + if (m_tickCount != m_axis->tickCount()) { + m_tickCount = m_axis->tickCount(); presenter()->layout()->invalidate(); } @@ -135,11 +77,11 @@ QSizeF ChartValueAxisX::sizeHint(Qt::SizeHint which, const QSizeF& constraint) c { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); - QStringList ticksList = createNumberLabels(m_min,m_max,m_tickCount); + QStringList ticksList = createValueLabels(m_tickCount); qreal width=0; qreal height=0; diff --git a/src/axis/valueaxis/chartvalueaxisx_p.h b/src/axis/valueaxis/chartvalueaxisx_p.h index 4bd70de..45120c0 100644 --- a/src/axis/valueaxis/chartvalueaxisx_p.h +++ b/src/axis/valueaxis/chartvalueaxisx_p.h @@ -30,20 +30,19 @@ #ifndef CHARTVALUEAXISX_H #define CHARTVALUEAXISX_H -#include "chartaxis_p.h" +#include "horizontalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; class ChartPresenter; +class QValueAxis; -class ChartValueAxisX : public ChartAxis +class ChartValueAxisX : public HorizontalAxis { public: - ChartValueAxisX(QAbstractAxis *axis, ChartPresenter *presenter); + ChartValueAxisX(QValueAxis *axis, ChartPresenter *presenter); ~ChartValueAxisX(); - AxisType axisType() const { return X_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: @@ -53,7 +52,7 @@ protected: private: int m_tickCount; - + QValueAxis *m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/valueaxis/chartvalueaxisy.cpp b/src/axis/valueaxis/chartvalueaxisy.cpp index 65d7eb2..61580d1 100644 --- a/src/axis/valueaxis/chartvalueaxisy.cpp +++ b/src/axis/valueaxis/chartvalueaxisy.cpp @@ -29,8 +29,8 @@ QTCOMMERCIALCHART_BEGIN_NAMESPACE -ChartValueAxisY::ChartValueAxisY(QAbstractAxis *axis,ChartPresenter *presenter) : ChartAxis(axis,presenter), - m_tickCount(0) +ChartValueAxisY::ChartValueAxisY(QValueAxis *axis,ChartPresenter *presenter) : VerticalAxis(axis,presenter), + m_tickCount(0),m_axis(axis) { } @@ -45,9 +45,11 @@ QVector ChartValueAxisY::calculateLayout() const QVector points; points.resize(m_tickCount); - const qreal deltaY = m_gridRect.height()/(m_tickCount-1); + const QRectF& gridRect = gridGeometry(); + + const qreal deltaY = gridRect.height()/(m_tickCount-1); for (int i = 0; i < m_tickCount; ++i) { - int y = i * -deltaY + m_gridRect.bottom(); + int y = i * -deltaY + gridRect.bottom(); points[i] = y; } @@ -57,89 +59,15 @@ QVector ChartValueAxisY::calculateLayout() const void ChartValueAxisY::updateGeometry() { const QVector &layout = ChartAxis::layout(); - if(layout.isEmpty()) return; - - QStringList ticksList = createNumberLabels(m_min,m_max,layout.size()); - - QList lines = m_grid->childItems(); - QList labels = m_labels->childItems(); - QList shades = m_shades->childItems(); - QList axis = m_arrow->childItems(); - - Q_ASSERT(labels.size() == ticksList.size()); - Q_ASSERT(layout.size() == ticksList.size()); - - qreal height = m_axisRect.bottom(); - - QGraphicsLineItem *lineItem = static_cast(axis.at(0)); - //lineItem->setLine( m_gridRect.left() , m_gridRect.top(), m_gridRect.left(), m_gridRect.bottom()); - - if (m_chartAxis->alignment()==Qt::AlignLeft) - lineItem->setLine( m_axisRect.right() , m_gridRect.top(), m_axisRect.right(), m_gridRect.bottom()); - else if(m_chartAxis->alignment()==Qt::AlignRight) - lineItem->setLine( m_axisRect.left() , m_gridRect.top(), m_axisRect.left(), m_gridRect.bottom()); - - QFontMetrics fn(m_font); - - for (int i = 0; i < layout.size(); ++i) { - QGraphicsLineItem *lineItem = static_cast(lines.at(i)); - lineItem->setLine( m_gridRect.left() , layout[i], m_gridRect.right(), layout[i]); - QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); - - QString text = ticksList.at(i); - - if (fn.boundingRect(text).width() > m_axisRect.right() - m_axisRect.left() - labelPadding() ) - { - QString label = text + "..."; - while (fn.boundingRect(label).width() > m_axisRect.right() - m_axisRect.left() - labelPadding() && label.length() > 3) - label.remove(label.length() - 4, 1); - labelItem->setText(label); - }else{ - labelItem->setText(text); - } - - const QRectF& rect = labelItem->boundingRect(); - - QPointF center = rect.center(); - labelItem->setTransformOriginPoint(center.x(), center.y()); - //labelItem->setPos( m_gridRect.left() - rect.width() - labelPadding() , layout[i]-center.y()); - - if (m_chartAxis->alignment()==Qt::AlignLeft) - labelItem->setPos( m_axisRect.right() - rect.width() - labelPadding() , layout[i]-center.y()); - else if(m_chartAxis->alignment()==Qt::AlignRight) - labelItem->setPos( m_axisRect.left() + labelPadding() , layout[i]-center.y()); - - if(labelItem->pos().y() + rect.height() > height || - labelItem->pos().y() < m_axisRect.top()) { - labelItem->setVisible(false); - lineItem->setVisible(false); - }else{ - labelItem->setVisible(true); - lineItem->setVisible(true); - height=labelItem->pos().y(); - } - - if ((i+1)%2 && i>1) { - QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); - rectItem->setRect( m_gridRect.left(),layout[i], m_gridRect.width(),layout[i-1]-layout[i]); - } - lineItem = static_cast(axis.at(i+1)); - // lineItem->setLine( m_gridRect.left()-5,layout[i], m_gridRect.left(),layout[i]); - - if (m_chartAxis->alignment()==Qt::AlignLeft) - lineItem->setLine( m_axisRect.right()- labelPadding(),layout[i], m_axisRect.right(),layout[i]); - else if(m_chartAxis->alignment()==Qt::AlignRight) - lineItem->setLine( m_axisRect.left(),layout[i], m_axisRect.left()+ labelPadding(),layout[i]); - - } + setLabels(createValueLabels(layout.size())); + VerticalAxis::updateGeometry(); } void ChartValueAxisY::handleAxisUpdated() { - QValueAxis* axis = qobject_cast(m_chartAxis); - if (m_tickCount != axis->tickCount()) { - m_tickCount = axis->tickCount(); + if (m_tickCount != m_axis->tickCount()) { + m_tickCount = m_axis->tickCount(); presenter()->layout()->invalidate(); } @@ -150,10 +78,10 @@ QSizeF ChartValueAxisY::sizeHint(Qt::SizeHint which, const QSizeF& constraint) c { Q_UNUSED(constraint) - QFontMetrics fn(m_font); + QFontMetrics fn(font()); QSizeF sh; QSizeF base = ChartAxis::sizeHint(which, constraint); - QStringList ticksList = createNumberLabels(m_min,m_max,m_tickCount); + QStringList ticksList = createValueLabels(m_tickCount); qreal width=0; qreal height=0; diff --git a/src/axis/valueaxis/chartvalueaxisy_p.h b/src/axis/valueaxis/chartvalueaxisy_p.h index 84aea8f..c8373e3 100644 --- a/src/axis/valueaxis/chartvalueaxisy_p.h +++ b/src/axis/valueaxis/chartvalueaxisy_p.h @@ -30,20 +30,19 @@ #ifndef CHARTVALUEAXISY_H #define CHARTVALUEAXISY_H -#include "chartaxis_p.h" +#include "verticalaxis_p.h" QTCOMMERCIALCHART_BEGIN_NAMESPACE -class QAbstractAxis; +class QValueAxis; class ChartPresenter; -class ChartValueAxisY : public ChartAxis +class ChartValueAxisY : public VerticalAxis { public: - ChartValueAxisY(QAbstractAxis *axis, ChartPresenter *presenter); + ChartValueAxisY(QValueAxis *axis, ChartPresenter *presenter); ~ChartValueAxisY(); - AxisType axisType() const { return Y_AXIS;} QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const; protected: QVector calculateLayout() const; @@ -51,6 +50,7 @@ protected: void handleAxisUpdated(); private: int m_tickCount; + QValueAxis* m_axis; }; QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/verticalaxis.cpp b/src/axis/verticalaxis.cpp new file mode 100644 index 0000000..f15bd7e --- /dev/null +++ b/src/axis/verticalaxis.cpp @@ -0,0 +1,146 @@ +/**************************************************************************** +** +** 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 "verticalaxis_p.h" +#include "qabstractaxis.h" +#include + +QTCOMMERCIALCHART_BEGIN_NAMESPACE + +VerticalAxis::VerticalAxis(QAbstractAxis *axis, ChartPresenter *presenter):ChartAxis(axis,presenter) +{ + +} + +VerticalAxis::~VerticalAxis() +{ + +} + +void VerticalAxis::updateGeometry() +{ + const QVector &layout = ChartAxis::layout(); + + if(layout.isEmpty()) return; + + QStringList labelList = labels(); + + QList lines = lineItems(); + QList labels = labelItems(); + QList shades = shadeItems(); + QList axis = arrowItems(); + + Q_ASSERT(labels.size() == labelList.size()); + Q_ASSERT(layout.size() == labelList.size()); + + const QRectF& axisRect = axisGeometry(); + const QRectF& gridRect = gridGeometry(); + + qreal height = axisRect.bottom(); + + QGraphicsLineItem *lineItem = static_cast(axis.at(0)); + + if (alignment()==Qt::AlignLeft) + lineItem->setLine( axisRect.right() , gridRect.top(), axisRect.right(), gridRect.bottom()); + else if(alignment()==Qt::AlignRight) + lineItem->setLine( axisRect.left() , gridRect.top(), axisRect.left(), gridRect.bottom()); + + QFontMetrics fn(font()); + + for (int i = 0; i < layout.size(); ++i) { + + QGraphicsLineItem *gridItem = static_cast(lines.at(i)); + QGraphicsLineItem *tickItem = static_cast(axis.at(i+1)); + QGraphicsSimpleTextItem *labelItem = static_cast(labels.at(i)); + + //grid line + gridItem->setLine( gridRect.left() , layout[i], gridRect.right(), layout[i]); + + //label text + QString text = labelList.at(i); + if (fn.boundingRect(text).width() > axisRect.right() - axisRect.left() - labelPadding() ) + { + QString label = text + "..."; + while (fn.boundingRect(label).width() > axisRect.right() - axisRect.left() - labelPadding() && label.length() > 3) + label.remove(label.length() - 4, 1); + labelItem->setText(label); + } + else { + labelItem->setText(text); + } + const QRectF& rect = labelItem->boundingRect(); + QPointF center = rect.center(); + labelItem->setTransformOriginPoint(center.x(), center.y()); + + //ticks and label position + if (alignment()==Qt::AlignLeft) { + labelItem->setPos( axisRect.right() - rect.width() - labelPadding() , layout[i]-center.y()); + tickItem->setLine( axisRect.right()- labelPadding(),layout[i], axisRect.right(),layout[i]); + } + else if(alignment()==Qt::AlignRight) { + labelItem->setPos( axisRect.left() + labelPadding() , layout[i]-center.y()); + tickItem->setLine( axisRect.left(),layout[i], axisRect.left()+ labelPadding(),layout[i]); + } + if(labelBetweenTicks()&& i+1!=layout.size()) { + const qreal delta = (layout[i+1] - layout[i])/2; + labelItem->setPos(labelItem->pos().x() , layout[i] + delta - center.y()); + } + + //overlap detection + if(labelItem->pos().y() + rect.height() > height || + labelItem->pos().y() + rect.height() > axisRect.bottom() || + labelItem->pos().y() < axisRect.top()) { + labelItem->setVisible(false); + gridItem->setVisible(false); + tickItem->setVisible(false); + } + else { + labelItem->setVisible(true); + gridItem->setVisible(true); + height=labelItem->pos().y(); + } + + //shades + if ((i+1)%2 && i>1) { + QGraphicsRectItem *rectItem = static_cast(shades.at(i/2-1)); + rectItem->setRect( gridRect.left(),layout[i], gridRect.width(),layout[i-1]-layout[i]); + } + + // check if the grid line and the axis tick should be shown + qreal y = gridItem->line().p1().y(); + if (y < gridRect.top() || y > gridRect.bottom()) { + gridItem->setVisible(false); + tickItem->setVisible(false); + if( labelBetweenTicks() && ( labelItem->pos().y() < gridRect.top() || labelItem->pos().y() + rect.height() > gridRect.bottom())) + labelItem->setVisible(false); + } + + } + //begin/end grid line in case labels between + if(labelBetweenTicks()) { + QGraphicsLineItem *gridLine; + gridLine = static_cast(lines.at(layout.size())); + gridLine->setLine(gridRect.left(), gridRect.top(), gridRect.right(), gridRect.top()); + gridLine = static_cast(lines.at(layout.size()+1)); + gridLine->setLine(gridRect.left(), gridRect.bottom(), gridRect.right(), gridRect.bottom()); + } +} + +QTCOMMERCIALCHART_END_NAMESPACE diff --git a/src/axis/verticalaxis_p.h b/src/axis/verticalaxis_p.h new file mode 100644 index 0000000..e095e44 --- /dev/null +++ b/src/axis/verticalaxis_p.h @@ -0,0 +1,49 @@ +/**************************************************************************** +** +** 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$ +** +****************************************************************************/ + +// W A R N I N G +// ------------- +// +// This file is not part of the QtCommercial Chart API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. + +#ifndef VERTICALAXIS_P_H_ +#define VERTICALAXIS_P_H_ + +#include "chartaxis_p.h" + +QTCOMMERCIALCHART_BEGIN_NAMESPACE + +class VerticalAxis : public ChartAxis +{ +public: + VerticalAxis(QAbstractAxis *axis, ChartPresenter *presenter); + ~VerticalAxis(); +protected: + void updateGeometry(); + +}; + +QTCOMMERCIALCHART_END_NAMESPACE + +#endif /* VERTICALAXIS_P_H_ */