1// Copyright (C) 2023 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
3
4#ifndef QGRAPHSVIEW_H
5#define QGRAPHSVIEW_H
6
7//
8// W A R N I N G
9// -------------
10//
11// This file is not part of the QtGraphs API. It exists purely as an
12// implementation detail. This header file may change from version to
13// version without notice, or even be removed.
14//
15// We mean it.
16
17#include <QtQuick/QQuickItem>
18#include <QtCore/QList>
19#include <QtQml/QQmlListProperty>
20#include <QtGraphs/qabstractseries.h>
21#include <QtGraphs/qgraphstheme.h>
22#include <QtCore/qloggingcategory.h>
23
24QT_BEGIN_NAMESPACE
25
26Q_DECLARE_LOGGING_CATEGORY(lcGraphs2D)
27Q_DECLARE_LOGGING_CATEGORY(lcViewProperties2D)
28Q_DECLARE_LOGGING_CATEGORY(lcEvents2D)
29Q_DECLARE_LOGGING_CATEGORY(lcCritical2D)
30
31class QQuickRectangle;
32class QAbstractAxis;
33class AxisRenderer;
34class BarsRenderer;
35class PointRenderer;
36class PieRenderer;
37class AreaRenderer;
38class QQuickPinchHandler;
39
40class Q_GRAPHS_EXPORT QGraphsView : public QQuickItem
41{
42 Q_OBJECT
43 Q_PROPERTY(QGraphsTheme *theme READ theme WRITE setTheme NOTIFY themeChanged FINAL)
44 Q_PROPERTY(QQmlListProperty<QObject> seriesList READ seriesList CONSTANT)
45 Q_PROPERTY(qreal marginTop READ marginTop WRITE setMarginTop NOTIFY marginTopChanged FINAL)
46 Q_PROPERTY(qreal marginBottom READ marginBottom WRITE setMarginBottom NOTIFY marginBottomChanged FINAL)
47 Q_PROPERTY(qreal marginLeft READ marginLeft WRITE setMarginLeft NOTIFY marginLeftChanged FINAL)
48 Q_PROPERTY(qreal marginRight READ marginRight WRITE setMarginRight NOTIFY marginRightChanged FINAL)
49 Q_PROPERTY(bool clipPlotArea READ clipPlotArea WRITE setClipPlotArea NOTIFY clipPlotAreaChanged REVISION(6, 10))
50 Q_PROPERTY(QRectF plotArea READ plotArea NOTIFY plotAreaChanged REVISION(6, 9))
51
52 Q_PROPERTY(qreal axisXSmoothing READ axisXSmoothing WRITE setAxisXSmoothing NOTIFY axisXSmoothingChanged FINAL)
53 Q_PROPERTY(qreal axisYSmoothing READ axisYSmoothing WRITE setAxisYSmoothing NOTIFY axisYSmoothingChanged FINAL)
54 Q_PROPERTY(qreal gridSmoothing READ gridSmoothing WRITE setGridSmoothing NOTIFY gridSmoothingChanged FINAL)
55
56 Q_PROPERTY(bool shadowVisible READ isShadowVisible WRITE setShadowVisible NOTIFY
57 shadowVisibleChanged FINAL)
58 Q_PROPERTY(QColor shadowColor READ shadowColor WRITE setShadowColor NOTIFY shadowColorChanged FINAL)
59 Q_PROPERTY(qreal shadowBarWidth READ shadowBarWidth WRITE setShadowBarWidth NOTIFY shadowBarWidthChanged FINAL)
60 Q_PROPERTY(qreal shadowXOffset READ shadowXOffset WRITE setShadowXOffset NOTIFY shadowXOffsetChanged FINAL)
61 Q_PROPERTY(qreal shadowYOffset READ shadowYOffset WRITE setShadowYOffset NOTIFY shadowYOffsetChanged FINAL)
62 Q_PROPERTY(qreal shadowSmoothing READ shadowSmoothing WRITE setShadowSmoothing NOTIFY shadowSmoothingChanged FINAL)
63
64 Q_PROPERTY(QAbstractAxis *axisX READ axisX WRITE setAxisX NOTIFY axisXChanged FINAL)
65 Q_PROPERTY(QAbstractAxis *axisY READ axisY WRITE setAxisY NOTIFY axisYChanged FINAL)
66 Q_PROPERTY(
67 Qt::Orientation orientation READ orientation WRITE setOrientation NOTIFY orientationChanged FINAL)
68
69 Q_PROPERTY(ZoomStyle zoomStyle READ zoomStyle WRITE setZoomStyle NOTIFY zoomStyleChanged REVISION(6, 9))
70 Q_PROPERTY(PanStyle panStyle READ panStyle WRITE setPanStyle NOTIFY panStyleChanged REVISION(6, 9))
71 Q_PROPERTY(qreal zoomSensitivity READ zoomSensitivity WRITE setZoomSensitivity NOTIFY
72 zoomSensitivityChanged REVISION(6, 9))
73
74 Q_PROPERTY(bool zoomAreaEnabled READ zoomAreaEnabled WRITE setZoomAreaEnabled NOTIFY
75 zoomAreaEnabledChanged REVISION(6, 9))
76 Q_PROPERTY(QQmlComponent *zoomAreaDelegate READ zoomAreaDelegate WRITE setZoomAreaDelegate
77 NOTIFY zoomAreaDelegateChanged REVISION(6, 9))
78
79 Q_CLASSINFO("DefaultProperty", "seriesList")
80 QML_NAMED_ELEMENT(GraphsView)
81
82public:
83 explicit QGraphsView(QQuickItem *parent = nullptr);
84 ~QGraphsView() override;
85
86 Q_INVOKABLE void addSeries(QObject *series);
87 Q_INVOKABLE void insertSeries(qsizetype index, QObject *series);
88 Q_INVOKABLE void removeSeries(QObject *series);
89 Q_INVOKABLE void removeSeries(qsizetype index);
90 Q_INVOKABLE bool hasSeries(QObject *series);
91
92 QList<QObject *> getSeriesList() const {
93 return m_seriesList;
94 }
95
96 QPointF getDataPointCoordinates(QAbstractSeries *series, qreal x, qreal y);
97
98 QQmlListProperty<QObject> seriesList();
99 static void appendSeriesFunc(QQmlListProperty<QObject> *list, QObject *series);
100 static qsizetype countSeriesFunc(QQmlListProperty<QObject> *list);
101 static QObject *atSeriesFunc(QQmlListProperty<QObject> *list, qsizetype index);
102 static void clearSeriesFunc(QQmlListProperty<QObject> *list);
103
104 QGraphsTheme *theme() const;
105 void setTheme(QGraphsTheme *newTheme);
106
107 qreal marginTop() const;
108 void setMarginTop(qreal newMarginTop);
109
110 qreal marginBottom() const;
111 void setMarginBottom(qreal newMarginBottom);
112
113 qreal marginLeft() const;
114 void setMarginLeft(qreal newMarginLeft);
115
116 qreal marginRight() const;
117 void setMarginRight(qreal newMarginRight);
118
119 bool clipPlotArea() const;
120 void setClipPlotArea(bool enabled);
121
122 QRectF plotArea() const;
123 void updatePlotArea();
124 void updateAxisAreas();
125
126 void addAxis(QAbstractAxis *axis);
127 void removeAxis(QAbstractAxis *axis);
128
129 qsizetype graphSeriesCount() const;
130 void setGraphSeriesCount(qsizetype count);
131
132#ifdef USE_BARGRAPH
133 void createBarsRenderer();
134#endif
135 void createAxisRenderer();
136#ifdef USE_POINTS
137 void createPointRenderer();
138#endif
139#ifdef USE_PIEGRAPH
140 void createPieRenderer();
141#endif
142#ifdef USE_AREAGRAPH
143 void createAreaRenderer();
144#endif
145
146 qreal axisXSmoothing() const;
147 void setAxisXSmoothing(qreal smoothing);
148 qreal axisYSmoothing() const;
149 void setAxisYSmoothing(qreal smoothing);
150 qreal gridSmoothing() const;
151 void setGridSmoothing(qreal smoothing);
152
153 bool isShadowVisible() const;
154 void setShadowVisible(bool newShadowVisibility);
155 QColor shadowColor() const;
156 void setShadowColor(QColor newShadowColor);
157 qreal shadowBarWidth() const;
158 void setShadowBarWidth(qreal newShadowBarWidth);
159 qreal shadowXOffset() const;
160 void setShadowXOffset(qreal newShadowXOffset);
161 qreal shadowYOffset() const;
162 void setShadowYOffset(qreal newShadowYOffset);
163 qreal shadowSmoothing() const;
164 void setShadowSmoothing(qreal smoothing);
165
166 QAbstractAxis *axisX() const;
167 void setAxisX(QAbstractAxis *axis);
168
169 QAbstractAxis *axisY() const;
170 void setAxisY(QAbstractAxis *axis);
171
172 Qt::Orientation orientation() const;
173 void setOrientation(Qt::Orientation newOrientation);
174
175 enum class ZoomStyle { None, Center };
176 Q_ENUM(ZoomStyle)
177
178 enum class PanStyle { None, Drag };
179 Q_ENUM(PanStyle)
180
181 ZoomStyle zoomStyle() const;
182 void setZoomStyle(ZoomStyle newZoomStyle);
183
184 PanStyle panStyle() const;
185 void setPanStyle(PanStyle newPanStyle);
186
187 bool zoomAreaEnabled() const;
188 void setZoomAreaEnabled(bool newZoomAreaEnabled);
189
190 QQmlComponent *zoomAreaDelegate() const;
191 void setZoomAreaDelegate(QQmlComponent *newZoomAreaDelegate);
192
193 qreal zoomSensitivity() const;
194 void setZoomSensitivity(qreal newZoomSensitivity);
195
196 void calculateAxisCounts(int *xCount, int *yCount, int *leftCount, int *topCount);
197
198protected:
199 void handleHoverEnter(const QString &seriesName, QPointF position, QPointF value);
200 void handleHoverExit(const QString &seriesName, QPointF position);
201 void handleHover(const QString &seriesName, QPointF position, QPointF value);
202 void updateComponentSizes();
203 void componentComplete() override;
204 void geometryChange(const QRectF &newGeometry, const QRectF &oldGeometry) override;
205 void hoverMoveEvent(QHoverEvent *event) override;
206 void wheelEvent(QWheelEvent *event) override;
207 QSGNode *updatePaintNode(QSGNode *oldNode, QQuickItem::UpdatePaintNodeData *updatePaintNodeData) override;
208 void updatePolish() override;
209
210Q_SIGNALS:
211 void themeChanged();
212 void marginTopChanged();
213 void marginBottomChanged();
214 void marginLeftChanged();
215 void marginRightChanged();
216 Q_REVISION(6, 10) void clipPlotAreaChanged();
217 Q_REVISION(6, 9) void plotAreaChanged();
218 void hoverEnter(const QString &seriesName, QPointF position, QPointF value);
219 void hoverExit(const QString &seriesName, QPointF position);
220 void hover(const QString &seriesName, QPointF position, QPointF value);
221
222 void axisXSmoothingChanged();
223 void axisYSmoothingChanged();
224 void gridSmoothingChanged();
225
226 void shadowVisibleChanged();
227 void shadowColorChanged();
228 void shadowBarWidthChanged();
229 void shadowXOffsetChanged();
230 void shadowYOffsetChanged();
231 void shadowSmoothingChanged();
232
233 void axisXChanged();
234 void axisYChanged();
235
236 void orientationChanged();
237
238 Q_REVISION(6, 9) void zoomStyleChanged();
239 Q_REVISION(6, 9) void panStyleChanged();
240
241 Q_REVISION(6, 9) void zoomAreaEnabledChanged();
242 Q_REVISION(6, 9) void zoomAreaDelegateChanged();
243
244 Q_REVISION(6, 9) void zoomSensitivityChanged();
245
246private:
247 friend class AxisRenderer;
248 friend class BarsRenderer;
249 friend class PointRenderer;
250 friend class AreaRenderer;
251 friend class QAbstractAxis;
252
253 void polishAndUpdate();
254 int getSeriesRendererIndex(QAbstractSeries *series);
255 void onPinchScaleChanged(qreal delta);
256 void onPinchGrabChanged(QPointingDevice::GrabTransition transition, QEventPoint point);
257
258 static constexpr qreal m_defaultAxisTickersWidth = 15;
259 static constexpr qreal m_defaultAxisTickersHeight = 15;
260 static constexpr qreal m_defaultAxisLabelsWidth = 40;
261 static constexpr qreal m_defaultAxisLabelsHeight = 25;
262 static constexpr qreal m_defaultAxisXLabelsMargin = 0;
263 static constexpr qreal m_defaultAxisYLabelsMargin = 5;
264
265 AxisRenderer *m_axisRenderer = nullptr;
266 BarsRenderer *m_barsRenderer = nullptr;
267 PointRenderer *m_pointRenderer = nullptr;
268 PieRenderer *m_pieRenderer = nullptr;
269 AreaRenderer *m_areaRenderer = nullptr;
270 QList<QObject *> m_seriesList;
271 QHash<int, QList<QAbstractSeries *>> m_cleanupSeriesList;
272 QQuickRectangle *m_backgroundRectangle = nullptr;
273
274 QAbstractAxis *m_axisX = nullptr;
275 QAbstractAxis *m_axisY = nullptr;
276 Qt::Orientation m_orientation = Qt::Orientation::Vertical;
277
278 QGraphsTheme *m_theme = nullptr;
279 QGraphsTheme *m_defaultTheme = nullptr;
280
281 qsizetype m_graphSeriesCount = 0;
282
283 bool m_clipPlotArea = true;
284 qreal m_marginTop = 20;
285 qreal m_marginBottom = 20;
286 qreal m_marginLeft = 20;
287 qreal m_marginRight = 20;
288 QRectF m_plotArea;
289 // Areas of axis
290 QRectF m_x1AxisArea;
291 QRectF m_x2AxisArea;
292 QRectF m_y1AxisArea;
293 QRectF m_y2AxisArea;
294 // Areas of axis tickers
295 QRectF m_x1AxisTickersArea;
296 QRectF m_x2AxisTickersArea;
297 QRectF m_y1AxisTickersArea;
298 QRectF m_y2AxisTickersArea;
299 // Areas of axis labels
300 QRectF m_x1AxisLabelsArea;
301 QRectF m_x2AxisLabelsArea;
302 QRectF m_y1AxisLabelsArea;
303 QRectF m_y2AxisLabelsArea;
304 // Note: Add properties for these
305 qreal m_axisTickersWidth = m_defaultAxisTickersWidth;
306 qreal m_axisTickersHeight = m_defaultAxisTickersHeight;
307 qreal m_axisLabelsWidth = m_defaultAxisLabelsWidth;
308 qreal m_axisLabelsHeight = m_defaultAxisLabelsHeight;
309 qreal m_axisXLabelsMargin = m_defaultAxisXLabelsMargin;
310 qreal m_axisYLabelsMargin = m_defaultAxisYLabelsMargin;
311 // Calculated based the the above
312 qreal m_axisWidth = 0;
313 qreal m_axisHeight = 0;
314
315 int m_hoverCount = 0;
316
317 qreal m_axisXSmoothing = 1.0;
318 qreal m_axisYSmoothing = 1.0;
319 qreal m_gridSmoothing = 1.0;
320
321 bool m_isShadowVisible = false;
322 QColor m_shadowColor = QColorConstants::Black;
323 qreal m_shadowBarWidth = 2.0;
324 qreal m_shadowXOffset = 0.0;
325 qreal m_shadowYOffset = 0.0;
326 qreal m_shadowSmoothing = 4.0;
327
328 ZoomStyle m_zoomStyle = ZoomStyle::None;
329 PanStyle m_panStyle = PanStyle::None;
330 qreal m_zoomSensitivity = 0.05f;
331
332 bool m_zoomAreaEnabled = false;
333 QQmlComponent *m_zoomAreaDelegate = nullptr;
334 QQuickItem *m_zoomAreaItem = nullptr;
335 QQuickPinchHandler *m_pinchHandler = nullptr;
336};
337
338QT_END_NAMESPACE
339
340#endif
341

source code of qtgraphs/src/graphs2d/qgraphsview_p.h