v2.0.0
Loading...
Searching...
No Matches
lineplot.cpp
Go to the documentation of this file.
1//=============================================================================================================
15
16//=============================================================================================================
17// INCLUDES
18//=============================================================================================================
19
20#include "lineplot.h"
21
22//=============================================================================================================
23// QT INCLUDES
24//=============================================================================================================
25
26#include <QPainter>
27#include <QPainterPath>
28#include <QPaintEvent>
29
30//=============================================================================================================
31// EIGEN INCLUDES
32//=============================================================================================================
33
34//=============================================================================================================
35// USED NAMESPACES
36//=============================================================================================================
37
38using namespace DISPLIB;
39using namespace Eigen;
40
41//=============================================================================================================
42// DEFINE MEMBER METHODS
43//=============================================================================================================
44
45LinePlot::LinePlot(QWidget *parent)
46: QWidget(parent)
47, m_dMinX(0)
48, m_dMaxX(0)
49, m_dMinY(0)
50, m_dMaxY(0)
51{
52 setMinimumSize(200, 150);
53 setBackgroundRole(QPalette::Base);
54 setAutoFillBackground(true);
55}
56
57//=============================================================================================================
58
59LinePlot::LinePlot(const QVector<double> &y,
60 const QString& title,
61 QWidget *parent)
62: QWidget(parent)
63, m_sTitle(title)
64, m_dMinX(0)
65, m_dMaxX(0)
66, m_dMinY(0)
67, m_dMaxY(0)
68{
69 setMinimumSize(200, 150);
70 setBackgroundRole(QPalette::Base);
71 setAutoFillBackground(true);
72 updateData(y);
73}
74
75//=============================================================================================================
76
77LinePlot::LinePlot(const QVector<double> &x,
78 const QVector<double> &y,
79 const QString& title,
80 QWidget *parent)
81: QWidget(parent)
82, m_sTitle(title)
83, m_dMinX(0)
84, m_dMaxX(0)
85, m_dMinY(0)
86, m_dMaxY(0)
87{
88 setMinimumSize(200, 150);
89 setBackgroundRole(QPalette::Base);
90 setAutoFillBackground(true);
91 updateData(x, y);
92}
93
94//=============================================================================================================
95
99
100//=============================================================================================================
101
102void LinePlot::setTitle(const QString &p_sTitle)
103{
104 m_sTitle = p_sTitle;
105 QWidget::update();
106}
107
108//=============================================================================================================
109
110void LinePlot::setXLabel(const QString &p_sXLabel)
111{
112 m_sXLabel = p_sXLabel;
113 QWidget::update();
114}
115
116//=============================================================================================================
117
118void LinePlot::setYLabel(const QString &p_sYLabel)
119{
120 m_sYLabel = p_sYLabel;
121 QWidget::update();
122}
123
124//=============================================================================================================
125
126void LinePlot::updateData(const QVector<double> &y)
127{
128 QVector<double> x(y.size());
129 for(int i = 0; i < x.size(); ++i) {
130 x[i] = static_cast<double>(i);
131 }
132 updateData(x, y);
133}
134
135//=============================================================================================================
136
137void LinePlot::updateData(const QVector<double> &x,
138 const QVector<double> &y)
139{
140 m_vecXData = x;
141 m_vecYData = y;
142
143 if (!x.isEmpty()) {
144 m_dMinX = x[0];
145 m_dMaxX = x[0];
146 for (int i = 1; i < x.size(); ++i) {
147 if (x[i] < m_dMinX) m_dMinX = x[i];
148 if (x[i] > m_dMaxX) m_dMaxX = x[i];
149 }
150 }
151
152 if (!y.isEmpty()) {
153 m_dMinY = y[0];
154 m_dMaxY = y[0];
155 for (int i = 1; i < y.size(); ++i) {
156 if (y[i] < m_dMinY) m_dMinY = y[i];
157 if (y[i] > m_dMaxY) m_dMaxY = y[i];
158 }
159 }
160
161 setWindowTitle(m_sTitle);
162 QWidget::update();
163}
164
165//=============================================================================================================
166
167void LinePlot::paintEvent(QPaintEvent * /*event*/)
168{
169 QPainter painter(this);
170 painter.setRenderHint(QPainter::Antialiasing);
171
172 const int w = width();
173 const int h = height();
174 const int mLeft = 60;
175 const int mRight = 20;
176 const int mTop = 35;
177 const int mBottom = 40;
178 const int plotW = w - mLeft - mRight;
179 const int plotH = h - mTop - mBottom;
180
181 if (plotW <= 0 || plotH <= 0)
182 return;
183
184 // Title
185 if (!m_sTitle.isEmpty()) {
186 QFont titleFont = painter.font();
187 titleFont.setBold(true);
188 titleFont.setPointSize(titleFont.pointSize() + 2);
189 painter.setFont(titleFont);
190 painter.setPen(Qt::black);
191 painter.drawText(QRect(0, 0, w, mTop), Qt::AlignCenter, m_sTitle);
192 painter.setFont(QFont());
193 }
194
195 // Draw axes
196 painter.setPen(QPen(Qt::black, 1));
197 painter.drawLine(mLeft, mTop, mLeft, mTop + plotH);
198 painter.drawLine(mLeft, mTop + plotH, mLeft + plotW, mTop + plotH);
199
200 // Y-axis label
201 if (!m_sYLabel.isEmpty()) {
202 painter.save();
203 painter.translate(12, mTop + plotH / 2);
204 painter.rotate(-90);
205 painter.drawText(QRect(-plotH / 2, 0, plotH, 15), Qt::AlignCenter, m_sYLabel);
206 painter.restore();
207 }
208
209 // X-axis label
210 if (!m_sXLabel.isEmpty()) {
211 painter.drawText(QRect(mLeft, h - 15, plotW, 15), Qt::AlignCenter, m_sXLabel);
212 }
213
214 double rangeX = m_dMaxX - m_dMinX;
215 double rangeY = m_dMaxY - m_dMinY;
216 if (rangeX == 0) rangeX = 1.0;
217 if (rangeY == 0) rangeY = 1.0;
218
219 // Y-axis ticks
220 const int nYTicks = 5;
221 for (int i = 0; i <= nYTicks; ++i) {
222 double yVal = m_dMinY + rangeY * i / nYTicks;
223 int y = mTop + plotH - static_cast<int>(plotH * static_cast<double>(i) / nYTicks);
224 painter.drawLine(mLeft - 5, y, mLeft, y);
225 painter.drawText(QRect(0, y - 10, mLeft - 8, 20), Qt::AlignRight | Qt::AlignVCenter,
226 QString::number(yVal, 'g', 4));
227 }
228
229 // X-axis ticks
230 const int nXTicks = 5;
231 for (int i = 0; i <= nXTicks; ++i) {
232 double xVal = m_dMinX + rangeX * i / nXTicks;
233 int x = mLeft + static_cast<int>(plotW * static_cast<double>(i) / nXTicks);
234 painter.drawLine(x, mTop + plotH, x, mTop + plotH + 5);
235 painter.drawText(QRect(x - 30, mTop + plotH + 6, 60, 20), Qt::AlignCenter,
236 QString::number(xVal, 'g', 4));
237 }
238
239 if (m_vecXData.isEmpty() || m_vecYData.isEmpty())
240 return;
241
242 // Draw line series
243 QPainterPath path;
244 auto toPixelX = [&](double dx) -> double {
245 return mLeft + ((dx - m_dMinX) / rangeX) * plotW;
246 };
247 auto toPixelY = [&](double dy) -> double {
248 return mTop + plotH - ((dy - m_dMinY) / rangeY) * plotH;
249 };
250
251 int n = qMin(m_vecXData.size(), m_vecYData.size());
252 path.moveTo(toPixelX(m_vecXData[0]), toPixelY(m_vecYData[0]));
253 for (int i = 1; i < n; ++i) {
254 path.lineTo(toPixelX(m_vecXData[i]), toPixelY(m_vecYData[i]));
255 }
256
257 painter.setPen(QPen(QColor(70, 130, 180), 2));
258 painter.setBrush(Qt::NoBrush);
259 painter.drawPath(path);
260}
Simple x/y line-series widget drawn with QPainter.
2-D display widgets and visualisation helpers (charts, topography, colour maps).
void updateData(const QVector< double > &y)
Definition lineplot.cpp:126
void paintEvent(QPaintEvent *event) override
Definition lineplot.cpp:167
LinePlot(QWidget *parent=nullptr)
Definition lineplot.cpp:45
void setTitle(const QString &p_sTitle)
Definition lineplot.cpp:102
void setXLabel(const QString &p_sXLabel)
Definition lineplot.cpp:110
void setYLabel(const QString &p_sYLabel)
Definition lineplot.cpp:118
virtual ~LinePlot()
Definition lineplot.cpp:96