1// Copyright (C) 2023 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#ifndef QQUICKSHAPECURVENODE_P_H
5#define QQUICKSHAPECURVENODE_P_H
6
7#include <QtQuick/qsgnode.h>
8
9#include "qquickshapegenericrenderer_p.h"
10
11//
12// W A R N I N G
13// -------------
14//
15// This file is not part of the Qt API. It exists for the convenience
16// of a number of Qt sources files. This header file may change from
17// version to version without notice, or even be removed.
18//
19// We mean it.
20//
21
22QT_BEGIN_NAMESPACE
23
24class QQuickShapeCurveNode : public QSGGeometryNode
25{
26public:
27 QQuickShapeCurveNode();
28
29 void setColor(QColor col)
30 {
31 if (m_color == col)
32 return;
33 m_color = col;
34 updateMaterial();
35 }
36
37 QColor color() const
38 {
39 return m_color;
40 }
41
42 void setStrokeColor(QColor col)
43 {
44 const bool hadStroke = hasStroke();
45 m_strokeColor = col;
46 if (hadStroke != hasStroke())
47 updateMaterial();
48 }
49
50 QColor strokeColor() const
51 {
52 return m_strokeColor;
53 }
54
55 void setStrokeWidth(float width)
56 {
57 const bool hadStroke = hasStroke();
58 m_strokeWidth = width;
59 if (hadStroke != hasStroke())
60 updateMaterial();
61 }
62
63 float strokeWidth() const
64 {
65 return m_strokeWidth;
66 }
67
68 void setFillGradient(const QQuickAbstractPathRenderer::GradientDesc &fillGradient)
69 {
70 m_fillGradient = fillGradient;
71 }
72
73 QQuickAbstractPathRenderer::GradientDesc fillGradient() const
74 {
75 return m_fillGradient;
76 }
77
78 void setGradientType(QQuickAbstractPathRenderer::FillGradientType type)
79 {
80 if (m_gradientType != type) {
81 m_gradientType = type;
82 updateMaterial();
83 }
84 }
85
86 float debug() const
87 {
88 return m_debug;
89 }
90
91 void setDebug(float newDebug)
92 {
93 m_debug = newDebug;
94 }
95
96 QQuickAbstractPathRenderer::FillGradientType gradientType() const
97 {
98 return m_gradientType;
99 }
100
101 bool hasStroke() const
102 {
103 return m_strokeWidth > 0.0f && m_strokeColor.alpha() > 0;
104 }
105
106 void appendTriangle(const std::array<QVector2D, 3> &v, // triangle vertices
107 const std::array<QVector2D, 3> &n, // vertex normals
108 std::function<QVector3D(QVector2D)> uvForPoint
109 )
110 {
111 QVector3D uv1 = uvForPoint(v[0]);
112 QVector3D uv2 = uvForPoint(v[1]);
113 QVector3D uv3 = uvForPoint(v[2]);
114
115 QVector2D duvdx = QVector2D(uvForPoint(v[0] + QVector2D(1, 0))) - QVector2D(uv1);
116 QVector2D duvdy = QVector2D(uvForPoint(v[0] + QVector2D(0, 1))) - QVector2D(uv1);
117
118 m_uncookedIndexes.append(t: m_uncookedVertexes.size());
119 m_uncookedVertexes.append( t: { .x: v[0].x(), .y: v[0].y(),
120 .u: uv1.x(), .v: uv1.y(), .w: uv1.z(),
121 .dudx: duvdx.x(), .dvdx: duvdx.y(),
122 .dudy: duvdy.x(), .dvdy: duvdy.y(),
123 .nx: n[0].x(), .ny: n[0].y()
124 });
125
126 m_uncookedIndexes.append(t: m_uncookedVertexes.size());
127 m_uncookedVertexes.append( t: { .x: v[1].x(), .y: v[1].y(),
128 .u: uv2.x(), .v: uv2.y(), .w: uv2.z(),
129 .dudx: duvdx.x(), .dvdx: duvdx.y(),
130 .dudy: duvdy.x(), .dvdy: duvdy.y(),
131 .nx: n[1].x(), .ny: n[1].y()
132 });
133
134 m_uncookedIndexes.append(t: m_uncookedVertexes.size());
135 m_uncookedVertexes.append( t: { .x: v[2].x(), .y: v[2].y(),
136 .u: uv3.x(), .v: uv3.y(), .w: uv3.z(),
137 .dudx: duvdx.x(), .dvdx: duvdx.y(),
138 .dudy: duvdy.x(), .dvdy: duvdy.y(),
139 .nx: n[2].x(), .ny: n[2].y()
140 });
141
142 }
143
144 void appendTriangle(const QVector2D &v1,
145 const QVector2D &v2,
146 const QVector2D &v3,
147 std::function<QVector3D(QVector2D)> uvForPoint)
148 {
149 appendTriangle(v: {v1, v2, v3}, n: {}, uvForPoint);
150 }
151
152 void appendIndex(quint32 index)
153 {
154 m_uncookedIndexes.append(t: index);
155 }
156
157 void appendIndexes(QVector<quint32> indexes)
158 {
159 m_uncookedIndexes.append(l: indexes);
160 }
161
162 QVector<quint32> uncookedIndexes() const
163 {
164 return m_uncookedIndexes;
165 }
166
167 void cookGeometry();
168
169private:
170 struct CurveNodeVertex
171 {
172 float x, y, u, v, w;
173 float dudx, dvdx, dudy, dvdy; // Size of pixel in curve space (must be same for all vertices in triangle)
174 float nx, ny; // normal vector describing the direction to shift the vertex for AA
175 };
176
177 void updateMaterial();
178 static const QSGGeometry::AttributeSet &attributes();
179
180 QColor m_color = Qt::white;
181 QColor m_strokeColor = Qt::transparent;
182 float m_strokeWidth = 0.0f;
183 float m_debug = 0.0f;
184 QQuickAbstractPathRenderer::GradientDesc m_fillGradient;
185 QQuickAbstractPathRenderer::FillGradientType m_gradientType = QQuickAbstractPathRenderer::NoGradient;
186
187 QScopedPointer<QSGMaterial> m_material;
188
189 QVector<CurveNodeVertex> m_uncookedVertexes;
190 QVector<quint32> m_uncookedIndexes;
191};
192
193QT_END_NAMESPACE
194
195#endif // QQUICKSHAPECURVENODE_P_H
196

source code of qtdeclarative/src/quickshapes/qquickshapecurvenode_p.h