##// END OF EJS Templates
Fixes layout rounding issue
Michal Klocek -
r2306:496027721d42
parent child
Show More
@@ -1,146 +1,142
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "chartbarcategoryaxisx_p.h"
22 22 #include "chartpresenter_p.h"
23 23 #include "qbarcategoryaxis_p.h"
24 #include "chartlayout_p.h"
24 25 #include <QFontMetrics>
25 26 #include <QDebug>
26 27 #include <qmath.h>
27 28
28 29 QTCOMMERCIALCHART_BEGIN_NAMESPACE
29 30
30 31 ChartBarCategoryAxisX::ChartBarCategoryAxisX(QBarCategoryAxis *axis, QGraphicsItem* item)
31 32 : HorizontalAxis(axis, item, true),
32 33 m_categoriesAxis(axis)
33 34 {
34
35 QObject::connect(m_categoriesAxis,SIGNAL(categoriesChanged()),this, SLOT(handleCategoriesChanged()));
36 handleCategoriesChanged();
35 37 }
36 38
37 39 ChartBarCategoryAxisX::~ChartBarCategoryAxisX()
38 40 {
39 41 }
40 42
41 43 QVector<qreal> ChartBarCategoryAxisX::calculateLayout() const
42 44 {
43 45 QVector<qreal> points;
44 46 const QRectF& gridRect = gridGeometry();
45 47 qreal range = max() - min();
46 48 const qreal delta = gridRect.width()/range;
47 49
48 50 if(delta<2) return points;
49 51
50 52 qreal offset =-min()-0.5;
51 53 offset = int(offset * delta)%int(delta);
52 54
53 55 int count = qFloor(range);
54 56 if(count < 1 ) return points;
55 57
56 58 points.resize(count+2);
57 59
58 60 for (int i = 0; i < count+2; ++i) {
59 61 points[i] = offset + i * delta + gridRect.left();
60 62 }
61 63
62 64 return points;
63 65 }
64 66
65 67 QStringList ChartBarCategoryAxisX::createCategoryLabels(const QVector<qreal>& layout) const
66 68 {
67 69 QStringList result ;
68 70 const QRectF &gridRect = gridGeometry();
69 71 qreal d = (max() - min()) / gridRect.width();
70 72
71 73 for (int i = 0; i < layout.count() - 1; ++i) {
72 74 qreal x = qFloor((((layout[i] + layout[i + 1]) / 2 - gridRect.left()) * d + min() + 0.5));
73 75 if ((x < m_categoriesAxis->categories().count()) && (x >= 0)) {
74 76 result << m_categoriesAxis->categories().at(x);
75 77 } else {
76 78 // No label for x coordinate
77 79 result << "";
78 80 }
79 81 }
80 82 result << "";
81 83 return result;
82 84 }
83 85
84 86
85 87 void ChartBarCategoryAxisX::updateGeometry()
86 88 {
87 89 const QVector<qreal>& layout = ChartAxis::layout();
88 90 if (layout.isEmpty())
89 91 return;
90 92 setLabels(createCategoryLabels(layout));
91 93 HorizontalAxis::updateGeometry();
92 94 }
93 95
94 void ChartBarCategoryAxisX::handleAxisUpdated()
96 void ChartBarCategoryAxisX::handleCategoriesChanged()
95 97 {
96 //TODO:
97 /*
98 if (m_categoriesAxis->categories() != m_categories) {
99 m_categories = m_categoriesAxis->categories();
100 if (ChartAxis::layout().count() == m_categoriesAxis->d_ptr->count() + 2)
101 updateGeometry();
102 }
103 */
104 //TODO: ChartAxis::handleAxisUpdated();
98 if(presenter()) presenter()->layout()->invalidate();
105 99 }
106 100
107 101 QSizeF ChartBarCategoryAxisX::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
108 102 {
109 103 Q_UNUSED(constraint)
110 104
111 105 QFontMetrics fn(font());
112 106 QSizeF sh;
113 107 QSizeF base = HorizontalAxis::sizeHint(which, constraint);
114 QStringList ticksList = createCategoryLabels(ChartAxis::layout());
108 QStringList ticksList = m_categoriesAxis->categories();
115 109
116 110 qreal width=0;
117 111 qreal height=0;
118 112
119 113 switch (which) {
120 114 case Qt::MinimumSize:
121 115 width = fn.boundingRect("...").width();
122 116 height = fn.height()+labelPadding();
123 117 width=qMax(width,base.width());
124 118 height += base.height();
125 119 sh = QSizeF(width,height);
126 120 break;
127 121 case Qt::PreferredSize:{
128 122
129 123 for (int i = 0; i < ticksList.size(); ++i)
130 124 {
131 125 QRectF rect = fn.boundingRect(ticksList.at(i));
132 126 width += rect.width();
133 127 }
134 128 height = fn.height()+labelPadding();
135 129 width = qMax(width,base.width());
136 130 height += base.height();
137 131 sh = QSizeF(width,height);
138 132 break;
139 133 }
140 134 default:
141 135 break;
142 136 }
143 137 return sh;
144 138 }
145 139
140 #include "moc_chartbarcategoryaxisx_p.cpp"
141
146 142 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,62 +1,62
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 // W A R N I N G
22 22 // -------------
23 23 //
24 24 // This file is not part of the QtCommercial Chart API. It exists purely as an
25 25 // implementation detail. This header file may change from version to
26 26 // version without notice, or even be removed.
27 27 //
28 28 // We mean it.
29 29
30 30 #ifndef CHARTBARCATEGORYAXISX_H
31 31 #define CHARTBARCATEGORYAXISX_H
32 32
33 33 #include "horizontalaxis_p.h"
34 34
35 35 QTCOMMERCIALCHART_BEGIN_NAMESPACE
36 36
37 37 class ChartPresenter;
38 38 class QBarCategoryAxis;
39 39
40 40 class ChartBarCategoryAxisX : public HorizontalAxis
41 41 {
42 Q_OBJECT
42 43 public:
43 44 ChartBarCategoryAxisX(QBarCategoryAxis *axis, QGraphicsItem* item = 0);
44 45 ~ChartBarCategoryAxisX();
45 46
46 47 QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const;
47 48 protected:
48 49 QVector<qreal> calculateLayout() const;
49 50 void updateGeometry();
50 51 private:
51 52 QStringList createCategoryLabels(const QVector<qreal>& layout) const;
52 53 public Q_SLOTS:
53 void handleAxisUpdated();
54 void handleCategoriesChanged();
54 55
55 56 private:
56 QStringList m_categories;
57 57 QBarCategoryAxis *m_categoriesAxis;
58 58 };
59 59
60 60 QTCOMMERCIALCHART_END_NAMESPACE
61 61
62 62 #endif /* CHARTBARCATEGORYAXISX_H */
@@ -1,145 +1,143
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "chartbarcategoryaxisy_p.h"
22 22 #include "chartpresenter_p.h"
23 23 #include "qbarcategoryaxis_p.h"
24 #include "chartlayout_p.h"
24 25 #include <qmath.h>
25 26 #include <QFontMetrics>
26 27 #include <QDebug>
27 28
28 29 QTCOMMERCIALCHART_BEGIN_NAMESPACE
29 30
30 31 ChartBarCategoryAxisY::ChartBarCategoryAxisY(QBarCategoryAxis *axis, QGraphicsItem* item)
31 32 : VerticalAxis(axis, item, true),
32 33 m_categoriesAxis(axis)
33 34 {
35 QObject::connect( m_categoriesAxis,SIGNAL(categoriesChanged()),this, SLOT(handleCategoriesChanged()));
36 handleCategoriesChanged();
34 37 }
35 38
36 39 ChartBarCategoryAxisY::~ChartBarCategoryAxisY()
37 40 {
38 41 }
39 42
40 43 QVector<qreal> ChartBarCategoryAxisY::calculateLayout() const
41 44 {
42 45 QVector<qreal> points;
43 46 const QRectF& gridRect = gridGeometry();
44 47 qreal range = max() - min();
45 48 const qreal delta = gridRect.height()/range;
46 49
47 50 if(delta<2) return points;
48 51
49 52 qreal offset = - min() - 0.5;
50 53 offset = int(offset * delta)%int(delta);
51 54
52 55 int count = qFloor(range);
53 56 if(count < 1 ) return points;
54 57
55 58 points.resize(count+2);
56 59
57 60 for (int i = 0; i < count+2; ++i) {
58 61 points[i] = gridRect.bottom() - i * delta -offset;
59 62 }
60 63
61 64 return points;
62 65 }
63 66
64 67 QStringList ChartBarCategoryAxisY::createCategoryLabels(const QVector<qreal>& layout) const
65 68 {
66 69 QStringList result;
67 70 const QRectF &gridRect = gridGeometry();
68 71 qreal d = (max() - min()) / gridRect.height();
69 72
70 73 for (int i = 0; i < layout.count() - 1; ++i) {
71 74 qreal x = qFloor(((gridRect.height() - (layout[i + 1] + layout[i]) / 2 + gridRect.top()) * d + min() + 0.5));
72 75 if ((x < m_categoriesAxis->categories().count()) && (x >= 0)) {
73 76 result << m_categoriesAxis->categories().at(x);
74 77 } else {
75 78 // No label for x coordinate
76 79 result << "";
77 80 }
78 81 }
79 82 result << "";
80 83 return result;
81 84 }
82 85
83 86 void ChartBarCategoryAxisY::updateGeometry()
84 87 {
85 88 const QVector<qreal>& layout = ChartAxis::layout();
86 89 if (layout.isEmpty())
87 90 return;
88 91 setLabels(createCategoryLabels(layout));
89 92 VerticalAxis::updateGeometry();
90 93 }
91 94
92 void ChartBarCategoryAxisY::handleAxisUpdated()
95 void ChartBarCategoryAxisY::handleCategoriesChanged()
93 96 {
94 //TODO:
95 /*
96 if (m_categoriesAxis->categories() != m_categories) {
97 m_categories = m_categoriesAxis->categories();
98 if (ChartAxis::layout().count() == m_categoriesAxis->d_ptr->count() + 2)
99 updateGeometry();
100 }*/
101 //TODO :: ChartAxis::handleAxisUpdated();
97 QGraphicsLayoutItem::updateGeometry();
98 if(presenter()) presenter()->layout()->invalidate();
102 99 }
103 100
104 101 QSizeF ChartBarCategoryAxisY::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
105 102 {
106 103 Q_UNUSED(constraint)
107 104
108 105 QFontMetrics fn(font());
109 106 QSizeF sh;
110 107 QSizeF base = VerticalAxis::sizeHint(which, constraint);
111 QStringList ticksList = createCategoryLabels(ChartAxis::layout());
112
108 QStringList ticksList = m_categoriesAxis->categories();
113 109 qreal width=0;
114 110 qreal height=0;
115 111
116 112 switch (which) {
117 113 case Qt::MinimumSize:
118 114 width = fn.boundingRect("...").width() + labelPadding();
119 115 height = fn.height();
120 116 width+=base.width();
121 117 if(base.width()>0) width+=labelPadding();
122 118 height=qMax(height,base.height());
123 119 sh = QSizeF(width,height);
124 120 break;
125 121 case Qt::PreferredSize:{
126 122
127 123 for (int i = 0; i < ticksList.size(); ++i)
128 124 {
129 125 QRectF rect = fn.boundingRect(ticksList.at(i));
130 126 height+=rect.height();
131 127 width=qMax(rect.width()+labelPadding(),width); //one pixel torelance
132 128 }
133 129 height=qMax(height,base.height());
134 130 width+=base.width();
135 131 if(base.width()>0) width+=labelPadding();
136 132 sh = QSizeF(width,height);
137 133 break;
138 134 }
139 135 default:
140 136 break;
141 137 }
142 138 return sh;
143 139 }
144 140
141 #include "moc_chartbarcategoryaxisy_p.cpp"
142
145 143 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,61 +1,61
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 // W A R N I N G
22 22 // -------------
23 23 //
24 24 // This file is not part of the QtCommercial Chart API. It exists purely as an
25 25 // implementation detail. This header file may change from version to
26 26 // version without notice, or even be removed.
27 27 //
28 28 // We mean it.
29 29
30 30 #ifndef CHARTBARCATEGORYAXISY_H
31 31 #define CHARTBARCATEGORYAXISY_H
32 32
33 33 #include "verticalaxis_p.h"
34 34
35 35 QTCOMMERCIALCHART_BEGIN_NAMESPACE
36 36
37 37 class QBarCategoryAxis;
38 38 class ChartPresenter;
39 39
40 40 class ChartBarCategoryAxisY : public VerticalAxis
41 41 {
42 Q_OBJECT
42 43 public:
43 44 ChartBarCategoryAxisY(QBarCategoryAxis *axis, QGraphicsItem* item = 0);
44 45 ~ChartBarCategoryAxisY();
45 46
46 47 QSizeF sizeHint(Qt::SizeHint which, const QSizeF &constraint) const;
47 48 protected:
48 49 QVector<qreal> calculateLayout() const;
49 50 void updateGeometry();
50 51 private:
51 52 QStringList createCategoryLabels(const QVector<qreal>& layout) const;
52 53 public Q_SLOTS:
53 void handleAxisUpdated();
54 void handleCategoriesChanged();
54 55 private:
55 QStringList m_categories;
56 56 QBarCategoryAxis *m_categoriesAxis;
57 57 };
58 58
59 59 QTCOMMERCIALCHART_END_NAMESPACE
60 60
61 61 #endif /* CHARTBARCATEGORYAXISY_H */
@@ -1,210 +1,210
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "horizontalaxis_p.h"
22 22 #include "qabstractaxis.h"
23 23 #include <QFontMetrics>
24 24 #include <qmath.h>
25 25 #include <QDebug>
26 26
27 27 QTCOMMERCIALCHART_BEGIN_NAMESPACE
28 28
29 29 HorizontalAxis::HorizontalAxis(QAbstractAxis *axis, QGraphicsItem* item , bool intervalAxis)
30 30 : ChartAxis(axis, item, intervalAxis)
31 31 {
32 32 }
33 33
34 34 HorizontalAxis::~HorizontalAxis()
35 35 {
36 36 }
37 37
38 38 void HorizontalAxis::updateGeometry()
39 39 {
40 40 const QVector<qreal>& layout = ChartAxis::layout();
41 41
42 42 if (layout.isEmpty())
43 43 return;
44 44
45 45 QStringList labelList = labels();
46 46
47 47 QList<QGraphicsItem *> lines = lineItems();
48 48 QList<QGraphicsItem *> labels = labelItems();
49 49 QList<QGraphicsItem *> shades = shadeItems();
50 50 QList<QGraphicsItem *> axis = arrowItems();
51 51 QGraphicsSimpleTextItem* title = titleItem();
52 52
53 53 Q_ASSERT(labels.size() == labelList.size());
54 54 Q_ASSERT(layout.size() == labelList.size());
55 55
56 56 const QRectF &axisRect = axisGeometry();
57 57 const QRectF &gridRect = gridGeometry();
58 58
59 59 //arrow
60 60 QGraphicsLineItem *arrowItem = static_cast<QGraphicsLineItem *>(axis.at(0));
61 61
62 62 if (alignment() == Qt::AlignTop)
63 63 arrowItem->setLine(gridRect.left(), axisRect.bottom(), gridRect.right(), axisRect.bottom());
64 64 else if (alignment() == Qt::AlignBottom)
65 65 arrowItem->setLine(gridRect.left(), axisRect.top(), gridRect.right(), axisRect.top());
66 66
67 67 qreal width = 0;
68 68 QFontMetrics fn(font());
69 69
70 70 //title
71 71
72 72 if (!titleText().isNull()) {
73 73 QFontMetrics fn(title->font());
74 74
75 75 int size(0);
76 76
77 77 size = gridRect.width();
78 78 QString titleText = this->titleText();
79 79
80 80 if (fn.boundingRect(titleText).width() > size) {
81 81 QString string = titleText + "...";
82 82 while (fn.boundingRect(string).width() > size && string.length() > 3)
83 83 string.remove(string.length() - 4, 1);
84 84 title->setText(string);
85 85 } else {
86 86 title->setText(titleText);
87 87 }
88 88
89 89 QPointF center = gridRect.center() - title->boundingRect().center();
90 90 if (alignment() == Qt::AlignTop) {
91 91 title->setPos(center.x(), axisRect.top());
92 92 } else if (alignment() == Qt::AlignBottom) {
93 93 title->setPos(center.x(), axisRect.bottom() - title->boundingRect().height());
94 94 }
95 95 }
96 96
97 97 for (int i = 0; i < layout.size(); ++i) {
98 98
99 99 //items
100 100 QGraphicsLineItem *gridItem = static_cast<QGraphicsLineItem*>(lines.at(i));
101 101 QGraphicsLineItem *tickItem = static_cast<QGraphicsLineItem*>(axis.at(i + 1));
102 102 QGraphicsSimpleTextItem *labelItem = static_cast<QGraphicsSimpleTextItem *>(labels.at(i));
103 103
104 104 //grid line
105 105 gridItem->setLine(layout[i], gridRect.top(), layout[i], gridRect.bottom());
106 106
107 107 //label text wrapping
108 108 if(intervalAxis()&& i+1!=layout.size()) {
109 109 //wrapping in case of interval axis
110 110 const qreal delta = layout[i+1] - layout[i];
111 111 QString text = labelList.at(i);
112 112 if (fn.boundingRect(text).width() + 1 > delta )
113 113 {
114 114 QString label = text + "...";
115 115 while (fn.boundingRect(label).width() >= delta && label.length() > 3)
116 116 label.remove(label.length() - 4, 1);
117 117 labelItem->setText(label);
118 118 }
119 119 else {
120 120 labelItem->setText(text);
121 121 }
122 122 }else{
123 123 labelItem->setText(labelList.at(i));
124 124 }
125 125
126 126 //label transformation origin point
127 127 const QRectF& rect = labelItem->boundingRect();
128 128 QPointF center = rect.center();
129 129 labelItem->setTransformOriginPoint(center.x(), center.y());
130 130
131 131 //ticks and label position
132 132 if (alignment() == Qt::AlignTop) {
133 133 labelItem->setPos(layout[i] - center.x(), axisRect.bottom() - rect.height() - labelPadding());
134 134 tickItem->setLine(layout[i], axisRect.bottom(), layout[i], axisRect.bottom() - labelPadding());
135 135 } else if (alignment() == Qt::AlignBottom) {
136 136 labelItem->setPos(layout[i] - center.x(), axisRect.top() + labelPadding());
137 137 tickItem->setLine(layout[i], axisRect.top(), layout[i], axisRect.top() + labelPadding());
138 138 }
139 139
140 140 //label in beetwen
141 141 if(intervalAxis()&& i+1!=layout.size()) {
142 142 const qreal delta = (layout[i+1] - layout[i])/2;
143 143 labelItem->setPos(layout[i] + delta - center.x(), labelItem->pos().y());
144 144 }
145 145
146 146 //label overlap detection
147 147 if(labelItem->pos().x() < width ||
148 148 labelItem->pos().x() < axisRect.left() ||
149 149 labelItem->pos().x() + rect.width() > axisRect.right()) {
150 150 labelItem->setVisible(false);
151 151 } else {
152 152 labelItem->setVisible(true);
153 153 width=rect.width()+labelItem->pos().x();
154 154 }
155 155
156 156 //shades
157 157 if ((i + 1) % 2 && i > 1) {
158 158 QGraphicsRectItem *rectItem = static_cast<QGraphicsRectItem *>(shades.at(i / 2 - 1));
159 159 rectItem->setRect(layout[i - 1], gridRect.top(), layout[i] - layout[i - 1], gridRect.height());
160 160 }
161 161
162 162 // check if the grid line and the axis tick should be shown
163 163 qreal x = gridItem->line().p1().x();
164 164 if (x < gridRect.left() || x > gridRect.right()) {
165 165 gridItem->setVisible(false);
166 166 tickItem->setVisible(false);
167 167 }else{
168 168 gridItem->setVisible(true);
169 169 tickItem->setVisible(true);
170 170 }
171 171
172 172 }
173 173
174 174 //begin/end grid line in case labels between
175 175 if (intervalAxis()) {
176 176 QGraphicsLineItem *gridLine;
177 177 gridLine = static_cast<QGraphicsLineItem *>(lines.at(layout.size()));
178 178 gridLine->setLine(gridRect.right(), gridRect.top(), gridRect.right(), gridRect.bottom());
179 179 gridLine->setVisible(true);
180 180 gridLine = static_cast<QGraphicsLineItem*>(lines.at(layout.size()+1));
181 181 gridLine->setLine(gridRect.left(), gridRect.top(), gridRect.left(), gridRect.bottom());
182 182 gridLine->setVisible(true);
183 183 }
184 184 }
185 185
186 186 QSizeF HorizontalAxis::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
187 187 {
188 188 Q_UNUSED(constraint);
189 189 QFontMetrics fn(titleFont());
190 QSizeF sh;
190 QSizeF sh(0,0);
191 191
192 192 if (titleText().isNull() || !titleItem()->isVisible())
193 193 return sh;
194 194
195 195 switch (which) {
196 196 case Qt::MinimumSize:
197 197 sh = QSizeF(fn.boundingRect("...").width(), fn.height());
198 198 break;
199 199 case Qt::MaximumSize:
200 200 case Qt::PreferredSize:
201 201 sh = QSizeF(fn.boundingRect(axis()->titleText()).width(), fn.height());
202 202 break;
203 203 default:
204 204 break;
205 205 }
206 206
207 207 return sh;
208 208 }
209 209
210 210 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,124 +1,122
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "chartvalueaxisx_p.h"
22 22 #include "qabstractaxis.h"
23 23 #include "chartpresenter_p.h"
24 24 #include "qvalueaxis.h"
25 25 #include "chartlayout_p.h"
26 26 #include <QGraphicsLayout>
27 27 #include <QFontMetrics>
28 28 #include <qmath.h>
29 29 #include <QDebug>
30 30
31 31
32 32 QTCOMMERCIALCHART_BEGIN_NAMESPACE
33 33
34 34 ChartValueAxisX::ChartValueAxisX(QValueAxis *axis, QGraphicsItem* item )
35 35 : HorizontalAxis(axis, item),
36 36 m_axis(axis)
37 37 {
38 38 QObject::connect(m_axis,SIGNAL(tickCountChanged(int)),this, SLOT(handleTickCountChanged(int)));
39 39 }
40 40
41 41 ChartValueAxisX::~ChartValueAxisX()
42 42 {
43 43 }
44 44
45 45 QVector<qreal> ChartValueAxisX::calculateLayout() const
46 46 {
47 47 int tickCount = m_axis->tickCount();
48 48
49 49 Q_ASSERT(tickCount >= 2);
50 50
51 51 QVector<qreal> points;
52 52 points.resize(tickCount);
53 53
54 54 const QRectF &gridRect = gridGeometry();
55 55 const qreal deltaX = gridRect.width() / (tickCount - 1);
56 56 for (int i = 0; i < tickCount; ++i) {
57 57 points[i] = i * deltaX + gridRect.left();
58 58 }
59 59 return points;
60 60 }
61 61
62 62 void ChartValueAxisX::updateGeometry()
63 63 {
64 64 const QVector<qreal>& layout = ChartAxis::layout();
65 65 if (layout.isEmpty())
66 66 return;
67 67 setLabels(createValueLabels(min(),max(),layout.size(),m_axis->labelFormat()));
68 68 HorizontalAxis::updateGeometry();
69 69 }
70 70
71 71 void ChartValueAxisX::handleTickCountChanged(int tick)
72 72 {
73 73 Q_UNUSED(tick);
74 74 if(presenter()) presenter()->layout()->invalidate();
75 //QVector<qreal> layout = calculateLayout();
76 //updateLayout(layout);
77 75 }
78 76
79 77 QSizeF ChartValueAxisX::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
80 78 {
81 79 Q_UNUSED(constraint)
82 80
83 81 QFontMetrics fn(font());
84 82 QSizeF sh;
85 83
86 84 QSizeF base = HorizontalAxis::sizeHint(which, constraint);
87 85 QStringList ticksList = createValueLabels(min(),max(),m_axis->tickCount(),m_axis->labelFormat());
88 86 qreal width = 0;
89 87 qreal height = 0;
90 88
91 89 int count = 1;
92 90
93 91 if(!ticksList.empty()) {
94 92 count = qMax(ticksList.last().count(),ticksList.first().count());
95 93 }
96 94
97 95 switch (which) {
98 96 case Qt::MinimumSize:{
99 97 count = qMin(count,5);
100 98 width = fn.averageCharWidth() * count;
101 99 height = fn.height() + labelPadding();
102 100 width = qMax(width,base.width());
103 101 height += base.height();
104 102 sh = QSizeF(width,height);
105 103 break;
106 104 }
107 105 case Qt::PreferredSize:{
108 106 width=fn.averageCharWidth() * count;
109 107 height=fn.height()+labelPadding();
110 108 width=qMax(width,base.width());
111 109 height+=base.height();
112 110 sh = QSizeF(width,height);
113 111 break;
114 112 }
115 113 default:
116 114 break;
117 115 }
118 116
119 117 return sh;
120 118 }
121 119
122 120 #include "moc_chartvalueaxisx_p.cpp"
123 121
124 122 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,123 +1,121
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "chartvalueaxisy_p.h"
22 22 #include "qabstractaxis.h"
23 23 #include "chartpresenter_p.h"
24 24 #include "qvalueaxis.h"
25 25 #include "chartlayout_p.h"
26 26 #include <QGraphicsLayout>
27 27 #include <QFontMetrics>
28 28 #include <qmath.h>
29 29 #include <QDebug>
30 30
31 31 QTCOMMERCIALCHART_BEGIN_NAMESPACE
32 32
33 33 ChartValueAxisY::ChartValueAxisY(QValueAxis *axis, QGraphicsItem* item)
34 34 : VerticalAxis(axis, item),
35 35 m_axis(axis)
36 36 {
37 37 QObject::connect(m_axis,SIGNAL(tickCountChanged(int)),this, SLOT(handleTickCountChanged(int)));
38 38 }
39 39
40 40 ChartValueAxisY::~ChartValueAxisY()
41 41 {
42 42 }
43 43
44 44 QVector<qreal> ChartValueAxisY::calculateLayout() const
45 45 {
46 46 int tickCount = m_axis->tickCount();
47 47
48 48 Q_ASSERT(tickCount >= 2);
49 49
50 50 QVector<qreal> points;
51 51 points.resize(tickCount);
52 52
53 53 const QRectF &gridRect = gridGeometry();
54 54
55 55 const qreal deltaY = gridRect.height() / (tickCount - 1);
56 56 for (int i = 0; i < tickCount; ++i) {
57 57 points[i] = i * -deltaY + gridRect.bottom();
58 58 }
59 59
60 60 return points;
61 61 }
62 62
63 63 void ChartValueAxisY::updateGeometry()
64 64 {
65 65 const QVector<qreal> &layout = ChartAxis::layout();
66 66 if (layout.isEmpty())
67 67 return;
68 68 setLabels(createValueLabels(min(),max(),layout.size(),m_axis->labelFormat()));
69 69 VerticalAxis::updateGeometry();
70 70 }
71 71
72 72 void ChartValueAxisY::handleTickCountChanged(int tick)
73 73 {
74 74 Q_UNUSED(tick);
75 75 if(presenter()) presenter()->layout()->invalidate();
76 //QVector<qreal> layout = calculateLayout();
77 //updateLayout(layout);
78 76 }
79 77
80 78 QSizeF ChartValueAxisY::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
81 79 {
82 80 Q_UNUSED(constraint)
83 81
84 82 QFontMetrics fn(font());
85 83 QSizeF sh;
86 84 QSizeF base = VerticalAxis::sizeHint(which, constraint);
87 85 QStringList ticksList = createValueLabels(min(),max(),m_axis->tickCount(),m_axis->labelFormat());
88 86 qreal width = 0;
89 87 qreal height = 0;
90 88
91 89 int count = 1;
92 90
93 91 if(!ticksList.empty()){
94 92 count = qMax(ticksList.last().count(),ticksList.first().count());
95 93 }
96 94
97 95 switch (which) {
98 96 case Qt::MinimumSize: {
99 97 width = fn.boundingRect("...").width() + labelPadding();
100 98 width += base.width();
101 99 height = fn.height();
102 100 height = qMax(height,base.height());
103 101 sh = QSizeF(width,height);
104 102 break;
105 103 }
106 104 case Qt::PreferredSize:
107 105 {
108 106 width = count*fn.averageCharWidth() + labelPadding() + 2; //two pixels of tolerance
109 107 width += base.width();
110 108 height = fn.height() * ticksList.count();
111 109 height = qMax(height,base.height());
112 110 sh = QSizeF(width,height);
113 111 break;
114 112 }
115 113 default:
116 114 break;
117 115 }
118 116 return sh;
119 117 }
120 118
121 119 #include "moc_chartvalueaxisy_p.cpp"
122 120
123 121 QTCOMMERCIALCHART_END_NAMESPACE
@@ -1,212 +1,212
1 1 /****************************************************************************
2 2 **
3 3 ** Copyright (C) 2012 Digia Plc
4 4 ** All rights reserved.
5 5 ** For any questions to Digia, please use contact form at http://qt.digia.com
6 6 **
7 7 ** This file is part of the Qt Commercial Charts Add-on.
8 8 **
9 9 ** $QT_BEGIN_LICENSE$
10 10 ** Licensees holding valid Qt Commercial licenses may use this file in
11 11 ** accordance with the Qt Commercial License Agreement provided with the
12 12 ** Software or, alternatively, in accordance with the terms contained in
13 13 ** a written agreement between you and Digia.
14 14 **
15 15 ** If you have questions regarding the use of this file, please use
16 16 ** contact form at http://qt.digia.com
17 17 ** $QT_END_LICENSE$
18 18 **
19 19 ****************************************************************************/
20 20
21 21 #include "verticalaxis_p.h"
22 22 #include "qabstractaxis.h"
23 23 #include <QFontMetrics>
24 24 #include <QDebug>
25 25
26 26 QTCOMMERCIALCHART_BEGIN_NAMESPACE
27 27
28 28 VerticalAxis::VerticalAxis(QAbstractAxis *axis, QGraphicsItem* item, bool intervalAxis)
29 29 : ChartAxis(axis, item, intervalAxis)
30 30 {
31 31
32 32 }
33 33
34 34 VerticalAxis::~VerticalAxis()
35 35 {
36 36
37 37 }
38 38
39 39 void VerticalAxis::updateGeometry()
40 40 {
41 41 const QVector<qreal> &layout = ChartAxis::layout();
42 42
43 43 if (layout.isEmpty())
44 44 return;
45 45
46 46 QStringList labelList = labels();
47 47
48 48 QList<QGraphicsItem *> lines = lineItems();
49 49 QList<QGraphicsItem *> labels = labelItems();
50 50 QList<QGraphicsItem *> shades = shadeItems();
51 51 QList<QGraphicsItem *> axis = arrowItems();
52 52 QGraphicsSimpleTextItem* title = titleItem();
53 53
54 54 Q_ASSERT(labels.size() == labelList.size());
55 55 Q_ASSERT(layout.size() == labelList.size());
56 56
57 57 const QRectF &axisRect = axisGeometry();
58 58 const QRectF &gridRect = gridGeometry();
59 59
60 60 qreal height = axisRect.bottom();
61 61
62 62
63 63 //arrow
64 64 QGraphicsLineItem *arrowItem = static_cast<QGraphicsLineItem*>(axis.at(0));
65 65
66 66 //arrow position
67 67 if (alignment()==Qt::AlignLeft)
68 68 arrowItem->setLine( axisRect.right() , gridRect.top(), axisRect.right(), gridRect.bottom());
69 69 else if(alignment()==Qt::AlignRight)
70 70 arrowItem->setLine( axisRect.left() , gridRect.top(), axisRect.left(), gridRect.bottom());
71 71
72 72 QFontMetrics fn(font());
73 73
74 74 //title
75 75
76 76 if (!titleText().isNull()) {
77 77 QFontMetrics fn(title->font());
78 78
79 79 int size(0);
80 80 size = gridRect.height();
81 81 QString titleText = this->titleText();
82 82
83 83 if (fn.boundingRect(titleText).width() > size) {
84 84 QString string = titleText + "...";
85 85 while (fn.boundingRect(string).width() > size && string.length() > 3)
86 86 string.remove(string.length() - 4, 1);
87 87 title->setText(string);
88 88 }
89 89 else {
90 90 title->setText(titleText);
91 91 }
92 92
93 93 QPointF center = gridRect.center() - title->boundingRect().center();
94 94 if (alignment() == Qt::AlignLeft) {
95 95 title->setPos(axisRect.left() - title->boundingRect().width()/2 + title->boundingRect().height()/2 , center.y());
96 96 }
97 97 else if (alignment() == Qt::AlignRight) {
98 98 title->setPos(axisRect.right()- title->boundingRect().width()/2 - title->boundingRect().height()/2, center.y());
99 99 }
100 100 title->setTransformOriginPoint(title->boundingRect().center());
101 101 title->setRotation(270);
102 102 }
103 103
104 104 for (int i = 0; i < layout.size(); ++i) {
105 105
106 106 //items
107 107 QGraphicsLineItem *gridItem = static_cast<QGraphicsLineItem *>(lines.at(i));
108 108 QGraphicsLineItem *tickItem = static_cast<QGraphicsLineItem *>(axis.at(i + 1));
109 109 QGraphicsSimpleTextItem *labelItem = static_cast<QGraphicsSimpleTextItem *>(labels.at(i));
110 110
111 111 //grid line
112 112 gridItem->setLine(gridRect.left() , layout[i], gridRect.right(), layout[i]);
113 113
114 114 //label text wrapping
115 115 QString text = labelList.at(i);
116 116 qreal size = axisRect.right() - axisRect.left() - labelPadding() - title->boundingRect().height();
117 117 if (fn.boundingRect(text).width() > size) {
118 118 QString label = text + "...";
119 119 while (fn.boundingRect(label).width() > size && label.length() > 3)
120 120 label.remove(label.length() - 4, 1);
121 121 labelItem->setText(label);
122 122 } else {
123 123 labelItem->setText(text);
124 124 }
125 125 //label transformation origin point
126 126 const QRectF &rect = labelItem->boundingRect();
127 127
128 128 QPointF center = rect.center();
129 129 labelItem->setTransformOriginPoint(center.x(), center.y());
130 130
131 131 //ticks and label position
132 132 if (alignment() == Qt::AlignLeft) {
133 133 labelItem->setPos(axisRect.right() - rect.width() - labelPadding() , layout[i] - center.y());
134 134 tickItem->setLine(axisRect.right() - labelPadding(), layout[i], axisRect.right(), layout[i]);
135 135 } else if (alignment() == Qt::AlignRight) {
136 136 labelItem->setPos(axisRect.left() + labelPadding() , layout[i] - center.y());
137 137 tickItem->setLine(axisRect.left(), layout[i], axisRect.left() + labelPadding(), layout[i]);
138 138 }
139 139
140 140 //label in beetwen
141 141 if(intervalAxis()&& i+1!=layout.size()) {
142 142 const qreal delta = (layout[i+1] - layout[i])/2;
143 143 labelItem->setPos(labelItem->pos().x() , layout[i] + delta - center.y());
144 144 }
145 145
146 146 //label overlap detection
147 147 if(labelItem->pos().y() + rect.height() > height ||
148 148 labelItem->pos().y() + rect.height()/2 > gridRect.bottom() ||
149 149 labelItem->pos().y() + rect.height()/2 < gridRect.top()) {
150 150 labelItem->setVisible(false);
151 151 }
152 152 else {
153 153 labelItem->setVisible(true);
154 154 height=labelItem->pos().y();
155 155 }
156 156
157 157 //shades
158 158 if ((i + 1) % 2 && i > 1) {
159 159 QGraphicsRectItem *rectItem = static_cast<QGraphicsRectItem *>(shades.at(i / 2 - 1));
160 160 rectItem->setRect(gridRect.left(), layout[i], gridRect.width(), layout[i - 1] - layout[i]);
161 161 }
162 162
163 163 // check if the grid line and the axis tick should be shown
164 164 qreal y = gridItem->line().p1().y();
165 165 if ((y < gridRect.top() || y > gridRect.bottom()))
166 166 {
167 167 gridItem->setVisible(false);
168 168 tickItem->setVisible(false);
169 169 }else{
170 170 gridItem->setVisible(true);
171 171 tickItem->setVisible(true);
172 172 }
173 173
174 174 }
175 175 //begin/end grid line in case labels between
176 176 if (intervalAxis()) {
177 177 QGraphicsLineItem *gridLine;
178 178 gridLine = static_cast<QGraphicsLineItem *>(lines.at(layout.size()));
179 179 gridLine->setLine(gridRect.left(), gridRect.top(), gridRect.right(), gridRect.top());
180 180 gridLine->setVisible(true);
181 181 gridLine = static_cast<QGraphicsLineItem*>(lines.at(layout.size()+1));
182 182 gridLine->setLine(gridRect.left(), gridRect.bottom(), gridRect.right(), gridRect.bottom());
183 183 gridLine->setVisible(true);
184 184 }
185 185 }
186 186
187 187 QSizeF VerticalAxis::sizeHint(Qt::SizeHint which, const QSizeF &constraint) const
188 188 {
189 189
190 190 Q_UNUSED(constraint);
191 191 QFontMetrics fn(titleFont());
192 QSizeF sh;
192 QSizeF sh(0,0);
193 193
194 194 if (titleText().isNull() || !titleItem()->isVisible())
195 195 return sh;
196 196
197 197 switch (which) {
198 198 case Qt::MinimumSize:
199 199 sh = QSizeF(fn.height(), fn.boundingRect("...").width());
200 200 break;
201 201 case Qt::MaximumSize:
202 202 case Qt::PreferredSize:
203 203 sh = QSizeF(fn.height(), fn.boundingRect(axis()->titleText()).width());
204 204 break;
205 205 default:
206 206 break;
207 207 }
208 208
209 209 return sh;
210 210 }
211 211
212 212 QTCOMMERCIALCHART_END_NAMESPACE
General Comments 0
You need to be logged in to leave comments. Login now