Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qsgadaptationlayer_p.h
Go to the documentation of this file.
1// Copyright (C) 2016 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 QSGADAPTATIONLAYER_P_H
5#define QSGADAPTATIONLAYER_P_H
6
7//
8// W A R N I N G
9// -------------
10//
11// This file is not part of the Qt 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
18#include <QtQuick/qsgnode.h>
19#include <QtQuick/qsgtexture.h>
20#include <QtQuick/qquickpainteditem.h>
21#include <QtCore/qobject.h>
22#include <QtCore/qrect.h>
23#include <QtGui/qbrush.h>
24#include <QtGui/qcolor.h>
25#include <QtGui/qpainterpath.h>
26#include <QtCore/qsharedpointer.h>
27#include <QtGui/qglyphrun.h>
28#include <QtGui/qpainterpath.h>
29#include <QtCore/qurl.h>
30#include <private/qfontengine_p.h>
31#include <QtGui/private/qdatabuffer_p.h>
32#include <private/qdistancefield_p.h>
33#include <private/qintrusivelist_p.h>
34#include <rhi/qshader.h>
35
36// ### remove
37#include <QtQuick/private/qquicktext_p.h>
38
40
41class QSGNode;
42class QImage;
43class TextureReference;
45class QSGInternalImageNode;
46class QSGPainterNode;
47class QSGInternalRectangleNode;
48class QSGGlyphNode;
49class QSGRootNode;
50class QSGSpriteNode;
51class QSGRenderNode;
52class QSGRenderContext;
53class QRhiTexture;
54
55class Q_QUICK_EXPORT QSGNodeVisitorEx
56{
57public:
58 virtual ~QSGNodeVisitorEx();
59
60 // visit(...) returns true if the children are supposed to be
61 // visisted and false if they're supposed to be skipped by the visitor.
62
63 virtual bool visit(QSGTransformNode *) = 0;
64 virtual void endVisit(QSGTransformNode *) = 0;
65 virtual bool visit(QSGClipNode *) = 0;
66 virtual void endVisit(QSGClipNode *) = 0;
67 virtual bool visit(QSGGeometryNode *) = 0;
68 virtual void endVisit(QSGGeometryNode *) = 0;
69 virtual bool visit(QSGOpacityNode *) = 0;
70 virtual void endVisit(QSGOpacityNode *) = 0;
71 virtual bool visit(QSGInternalImageNode *) = 0;
72 virtual void endVisit(QSGInternalImageNode *) = 0;
73 virtual bool visit(QSGPainterNode *) = 0;
74 virtual void endVisit(QSGPainterNode *) = 0;
75 virtual bool visit(QSGInternalRectangleNode *) = 0;
76 virtual void endVisit(QSGInternalRectangleNode *) = 0;
77 virtual bool visit(QSGGlyphNode *) = 0;
78 virtual void endVisit(QSGGlyphNode *) = 0;
79 virtual bool visit(QSGRootNode *) = 0;
80 virtual void endVisit(QSGRootNode *) = 0;
81#if QT_CONFIG(quick_sprite)
82 virtual bool visit(QSGSpriteNode *) = 0;
83 virtual void endVisit(QSGSpriteNode *) = 0;
84#endif
85 virtual bool visit(QSGRenderNode *) = 0;
86 virtual void endVisit(QSGRenderNode *) = 0;
87
88 void visitChildren(QSGNode *node);
89};
90
91
92class Q_QUICK_EXPORT QSGVisitableNode : public QSGGeometryNode
93{
94public:
95 QSGVisitableNode() { setFlag(IsVisitableNode); }
96 ~QSGVisitableNode() override;
97
98 virtual void accept(QSGNodeVisitorEx *) = 0;
99};
100
101class Q_QUICK_EXPORT QSGInternalRectangleNode : public QSGVisitableNode
102{
103public:
104 ~QSGInternalRectangleNode() override;
105
106 virtual void setRect(const QRectF &rect) = 0;
107 virtual void setColor(const QColor &color) = 0;
108 virtual void setPenColor(const QColor &color) = 0;
109 virtual void setPenWidth(qreal width) = 0;
110 virtual void setGradientStops(const QGradientStops &stops) = 0;
111 virtual void setGradientVertical(bool vertical) = 0;
112 virtual void setRadius(qreal radius) = 0;
113 virtual void setTopLeftRadius(qreal radius) = 0;
114 virtual void setTopRightRadius(qreal radius) = 0;
115 virtual void setBottomLeftRadius(qreal radius) = 0;
116 virtual void setBottomRightRadius(qreal radius) = 0;
117 virtual void resetTopLeftRadius() = 0;
118 virtual void resetTopRightRadius() = 0;
119 virtual void resetBottomLeftRadius() = 0;
120 virtual void resetBottomRightRadius() = 0;
121 virtual void setAntialiasing(bool antialiasing) { Q_UNUSED(antialiasing); }
122 virtual void setAligned(bool aligned) = 0;
123
124 virtual void update() = 0;
125
126 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
127};
128
129
130class Q_QUICK_EXPORT QSGInternalImageNode : public QSGVisitableNode
131{
132public:
133 ~QSGInternalImageNode() override;
134
135 virtual void setTargetRect(const QRectF &rect) = 0;
136 virtual void setInnerTargetRect(const QRectF &rect) = 0;
137 virtual void setInnerSourceRect(const QRectF &rect) = 0;
138 // The sub-source rect's width and height specify the number of times the inner source rect
139 // is repeated inside the inner target rect. The x and y specify which (normalized) location
140 // in the inner source rect maps to the upper-left corner of the inner target rect.
141 virtual void setSubSourceRect(const QRectF &rect) = 0;
142 virtual void setTexture(QSGTexture *texture) = 0;
143 virtual void setAntialiasing(bool antialiasing) { Q_UNUSED(antialiasing); }
144 virtual void setMirror(bool horizontally, bool vertically) = 0;
145 virtual void setMipmapFiltering(QSGTexture::Filtering filtering) = 0;
146 virtual void setFiltering(QSGTexture::Filtering filtering) = 0;
147 virtual void setHorizontalWrapMode(QSGTexture::WrapMode wrapMode) = 0;
148 virtual void setVerticalWrapMode(QSGTexture::WrapMode wrapMode) = 0;
149
150 virtual void update() = 0;
151
152 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
153};
154
155class Q_QUICK_EXPORT QSGPainterNode : public QSGVisitableNode
156{
157public:
158 ~QSGPainterNode() override;
159
160 virtual void setPreferredRenderTarget(QQuickPaintedItem::RenderTarget target) = 0;
161 virtual void setSize(const QSize &size) = 0;
162 virtual void setDirty(const QRect &dirtyRect = QRect()) = 0;
163 virtual void setOpaquePainting(bool opaque) = 0;
164 virtual void setLinearFiltering(bool linearFiltering) = 0;
165 virtual void setMipmapping(bool mipmapping) = 0;
166 virtual void setSmoothPainting(bool s) = 0;
167 virtual void setFillColor(const QColor &c) = 0;
168 virtual void setContentsScale(qreal s) = 0;
169 virtual void setFastFBOResizing(bool dynamic) = 0;
170 virtual void setTextureSize(const QSize &size) = 0;
171
172 virtual QImage toImage() const = 0;
173 virtual void update() = 0;
174 virtual QSGTexture *texture() const = 0;
175
176 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
177};
178
179class Q_QUICK_EXPORT QSGLayer : public QSGDynamicTexture
180{
181 Q_OBJECT
182public:
183 ~QSGLayer() override;
184
185 enum Format {
186 RGBA8 = 1,
187 RGBA16F,
188 RGBA32F
189 };
190 virtual void setItem(QSGNode *item) = 0;
191 virtual void setRect(const QRectF &logicalRect) = 0;
192 virtual void setSize(const QSize &pixelSize) = 0;
193 virtual void scheduleUpdate() = 0;
194 virtual QImage toImage() const = 0;
195 virtual void setLive(bool live) = 0;
196 virtual void setRecursive(bool recursive) = 0;
197 virtual void setFormat(Format format) = 0;
198 virtual void setHasMipmaps(bool mipmap) = 0;
199 virtual void setDevicePixelRatio(qreal ratio) = 0;
200 virtual void setMirrorHorizontal(bool mirror) = 0;
201 virtual void setMirrorVertical(bool mirror) = 0;
202 virtual void setSamples(int samples) = 0;
203 Q_SLOT virtual void markDirtyTexture() = 0;
204 Q_SLOT virtual void invalidated() = 0;
205
206Q_SIGNALS:
207 void updateRequested();
208 void scheduledUpdateCompleted();
209
210protected:
211 QSGLayer(QSGTexturePrivate &dd);
212};
213
214#if QT_CONFIG(quick_sprite)
215
216class Q_QUICK_EXPORT QSGSpriteNode : public QSGVisitableNode
217{
218public:
219 ~QSGSpriteNode() override;
220
221 virtual void setTexture(QSGTexture *texture) = 0;
222 virtual void setTime(float time) = 0;
223 virtual void setSourceA(const QPoint &source) = 0;
224 virtual void setSourceB(const QPoint &source) = 0;
225 virtual void setSpriteSize(const QSize &size) = 0;
226 virtual void setSheetSize(const QSize &size) = 0;
227 virtual void setSize(const QSizeF &size) = 0;
228 virtual void setFiltering(QSGTexture::Filtering filtering) = 0;
229
230 virtual void update() = 0;
231
232 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
233};
234
235#endif
236
237class Q_QUICK_EXPORT QSGGuiThreadShaderEffectManager : public QObject
238{
239 Q_OBJECT
240
241public:
242 ~QSGGuiThreadShaderEffectManager() override;
243
244 enum Status {
245 Compiled,
246 Uncompiled,
247 Error
248 };
249
250 virtual bool hasSeparateSamplerAndTextureObjects() const = 0;
251
252 virtual QString log() const = 0;
253 virtual Status status() const = 0;
254
255 struct ShaderInfo {
256 enum Type {
257 TypeVertex,
258 TypeFragment,
259 TypeOther
260 };
261 enum VariableType {
262 Constant, // cbuffer members or uniforms
263 Sampler,
264 Texture // for APIs with separate texture and sampler objects
265 };
266 struct Variable {
267 VariableType type = Constant;
268 QByteArray name;
269 uint offset = 0; // for cbuffer members
270 uint size = 0; // for cbuffer members
271 int bindPoint = 0; // for textures/samplers, where applicable
272 };
273
274 QString name; // optional, f.ex. the filename, used for debugging purposes only
275 QShader rhiShader;
276 Type type;
277 QVector<Variable> variables;
278
279 // Vertex inputs are not tracked here as QSGGeometry::AttributeSet
280 // hardwires that anyways so it is up to the shader to provide
281 // compatible inputs (e.g. compatible with
282 // QSGGeometry::defaultAttributes_TexturedPoint2D()).
283 };
284
285 virtual void prepareShaderCode(ShaderInfo::Type typeHint, const QUrl &src, ShaderInfo *result) = 0;
286
287Q_SIGNALS:
288 void shaderCodePrepared(bool ok, ShaderInfo::Type typeHint, const QUrl &src, ShaderInfo *result);
289 void logAndStatusChanged();
290};
291
292#ifndef QT_NO_DEBUG_STREAM
293Q_QUICK_EXPORT QDebug operator<<(QDebug debug, const QSGGuiThreadShaderEffectManager::ShaderInfo::Variable &v);
294#endif
295
296class Q_QUICK_EXPORT QSGShaderEffectNode : public QObject, public QSGVisitableNode
297{
298 Q_OBJECT
299
300public:
301 ~QSGShaderEffectNode() override;
302
303 enum DirtyShaderFlag {
304 DirtyShaders = 0x01,
305 DirtyShaderConstant = 0x02,
306 DirtyShaderTexture = 0x04,
307 DirtyShaderGeometry = 0x08,
308 DirtyShaderMesh = 0x10,
309
310 DirtyShaderAll = 0xFF
311 };
312 Q_DECLARE_FLAGS(DirtyShaderFlags, DirtyShaderFlag)
313
314 enum CullMode { // must match ShaderEffect
315 NoCulling,
316 BackFaceCulling,
317 FrontFaceCulling
318 };
319
320 struct VariableData {
321 enum SpecialType { None, Unused, Source, SubRect, Opacity, Matrix };
322
323 QVariant value;
324 SpecialType specialType;
325 int propertyIndex = -1;
326 };
327
328 struct ShaderData {
329 ShaderData() {}
330 bool hasShaderCode = false;
331 QSGGuiThreadShaderEffectManager::ShaderInfo shaderInfo;
332 QVector<VariableData> varData;
333 };
334
335 struct SyncData {
336 DirtyShaderFlags dirty;
337 CullMode cullMode;
338 bool blending;
339 struct ShaderSyncData {
340 const ShaderData *shader;
341 const QSet<int> *dirtyConstants;
342 const QSet<int> *dirtyTextures;
343 };
344 ShaderSyncData vertex;
345 ShaderSyncData fragment;
346 void *materialTypeCacheKey;
347 qint8 viewCount;
348 };
349
350 // Each ShaderEffect item has one node (render thread) and one manager (gui thread).
351
352 virtual QRectF updateNormalizedTextureSubRect(bool supportsAtlasTextures) = 0;
353 virtual void syncMaterial(SyncData *syncData) = 0;
354
355 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
356
357Q_SIGNALS:
358 void textureChanged();
359};
360
361Q_DECLARE_OPERATORS_FOR_FLAGS(QSGShaderEffectNode::DirtyShaderFlags)
362
363#ifndef QT_NO_DEBUG_STREAM
364Q_QUICK_EXPORT QDebug operator<<(QDebug debug, const QSGShaderEffectNode::VariableData &vd);
365#endif
366
367class Q_QUICK_EXPORT QSGGlyphNode : public QSGVisitableNode
368{
369public:
370 enum AntialiasingMode
371 {
372 DefaultAntialiasing = -1,
373 GrayAntialiasing,
374 LowQualitySubPixelAntialiasing,
375 HighQualitySubPixelAntialiasing
376 };
377
378 QSGGlyphNode() {}
379 ~QSGGlyphNode() override;
380
381 virtual void setGlyphs(const QPointF &position, const QGlyphRun &glyphs) = 0;
382 virtual void setColor(const QColor &color) = 0;
383 virtual void setStyle(QQuickText::TextStyle style) = 0;
384 virtual void setStyleColor(const QColor &color) = 0;
385 virtual QPointF baseLine() const = 0;
386
387 virtual QRectF boundingRect() const { return m_bounding_rect; }
388 virtual void setBoundingRect(const QRectF &bounds) { m_bounding_rect = bounds; }
389
390 virtual void setPreferredAntialiasingMode(AntialiasingMode) = 0;
391 virtual void setRenderTypeQuality(int renderTypeQuality) { Q_UNUSED(renderTypeQuality) }
392
393 virtual void update() = 0;
394
395 void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
396protected:
397 QRectF m_bounding_rect;
398};
399
401{
402public:
403 virtual ~QSGDistanceFieldGlyphConsumer();
404
405 virtual void invalidateGlyphs(const QVector<quint32> &glyphs) = 0;
406 QIntrusiveListNode node;
407};
409
410class Q_QUICK_EXPORT QSGDistanceFieldGlyphCache
411{
412public:
413 QSGDistanceFieldGlyphCache(const QRawFont &font,
414 int renderTypeQuality);
415 virtual ~QSGDistanceFieldGlyphCache();
416
417 struct Metrics {
418 qreal width;
419 qreal height;
420 qreal baselineX;
421 qreal baselineY;
422
423 bool isNull() const { return width == 0 || height == 0; }
424 };
425
426 struct TexCoord {
427 qreal x = 0;
428 qreal y = 0;
429 qreal width = -1;
430 qreal height = -1;
431 qreal xMargin = 0;
432 qreal yMargin = 0;
433
434 TexCoord() {}
435
436 bool isNull() const { return width <= 0 || height <= 0; }
437 bool isValid() const { return width >= 0 && height >= 0; }
438 };
439
440 struct Texture {
441 QRhiTexture *texture = nullptr;
442 QSize size;
443
444 bool operator == (const Texture &other) const {
445 return texture == other.texture;
446 }
447 };
448
449 const QRawFont &referenceFont() const { return m_referenceFont; }
450
451 qreal fontScale(qreal pixelSize) const
452 {
453 return pixelSize / baseFontSize();
454 }
455 qreal distanceFieldRadius() const
456 {
457 return QT_DISTANCEFIELD_RADIUS(m_doubleGlyphResolution) / qreal(QT_DISTANCEFIELD_SCALE(m_doubleGlyphResolution));
458 }
459 int glyphCount() const { return m_glyphCount; }
460 bool doubleGlyphResolution() const { return m_doubleGlyphResolution; }
461 int renderTypeQuality() const { return m_renderTypeQuality; }
462
463 Metrics glyphMetrics(glyph_t glyph, qreal pixelSize);
464 inline TexCoord glyphTexCoord(glyph_t glyph);
465 inline const Texture *glyphTexture(glyph_t glyph);
466
467 void populate(const QVector<glyph_t> &glyphs);
468 void release(const QVector<glyph_t> &glyphs);
469
470 void update();
471
472 void registerGlyphNode(QSGDistanceFieldGlyphConsumer *node) { m_registeredNodes.insert(node); }
473 void unregisterGlyphNode(QSGDistanceFieldGlyphConsumer *node) { m_registeredNodes.remove(node); }
474
475 virtual void processPendingGlyphs();
476
477 virtual bool eightBitFormatIsAlphaSwizzled() const = 0;
478 virtual bool screenSpaceDerivativesSupported() const = 0;
479 virtual bool isActive() const;
480
481protected:
482 struct GlyphPosition {
483 glyph_t glyph;
484 QPointF position;
485 };
486
487 struct GlyphData {
488 Texture *texture = nullptr;
489 TexCoord texCoord;
490 QRectF boundingRect;
491 QPainterPath path;
492 quint32 ref = 0;
493
494 GlyphData() {}
495 };
496
497 virtual void requestGlyphs(const QSet<glyph_t> &glyphs) = 0;
498 virtual void storeGlyphs(const QList<QDistanceField> &glyphs) = 0;
499 virtual void referenceGlyphs(const QSet<glyph_t> &glyphs) = 0;
500 virtual void releaseGlyphs(const QSet<glyph_t> &glyphs) = 0;
501
502 void setGlyphsPosition(const QList<GlyphPosition> &glyphs);
503 void setGlyphsTexture(const QVector<glyph_t> &glyphs, const Texture &tex);
504 void markGlyphsToRender(const QVector<glyph_t> &glyphs);
505 inline void removeGlyph(glyph_t glyph);
506
507 void updateRhiTexture(QRhiTexture *oldTex, QRhiTexture *newTex, const QSize &newTexSize);
508
509 inline bool containsGlyph(glyph_t glyph);
510
511 GlyphData &glyphData(glyph_t glyph);
512 GlyphData &emptyData(glyph_t glyph);
513
514 int baseFontSize() const;
515
516#if defined(QSG_DISTANCEFIELD_CACHE_DEBUG)
517 virtual void saveTexture(QRhiTexture *texture, const QString &nameBase) const = 0;
518#endif
519
520 bool m_doubleGlyphResolution;
521 int m_renderTypeQuality;
522
523protected:
524 QRawFont m_referenceFont;
525
526private:
527 int m_glyphCount;
528 QList<Texture> m_textures;
529 QHash<glyph_t, GlyphData> m_glyphsData;
530 QDataBuffer<glyph_t> m_pendingGlyphs;
531 QSet<glyph_t> m_populatingGlyphs;
532 QSGDistanceFieldGlyphConsumerList m_registeredNodes;
533
534 static Texture s_emptyTexture;
535};
536
537inline QSGDistanceFieldGlyphCache::TexCoord QSGDistanceFieldGlyphCache::glyphTexCoord(glyph_t glyph)
538{
539 return glyphData(glyph).texCoord;
540}
541
542inline const QSGDistanceFieldGlyphCache::Texture *QSGDistanceFieldGlyphCache::glyphTexture(glyph_t glyph)
543{
544 return glyphData(glyph).texture;
545}
546
547inline void QSGDistanceFieldGlyphCache::removeGlyph(glyph_t glyph)
548{
549 GlyphData &gd = glyphData(glyph);
550 gd.texCoord = TexCoord();
551 gd.texture = &s_emptyTexture;
552}
553
554inline bool QSGDistanceFieldGlyphCache::containsGlyph(glyph_t glyph)
555{
556 return glyphData(glyph).texCoord.isValid();
557}
558
559QT_END_NAMESPACE
560
561Q_DECLARE_METATYPE(QSGGuiThreadShaderEffectManager::ShaderInfo::Type)
562
563#endif
Q_CORE_EXPORT QDebug operator<<(QDebug debug, QDir::Filters filters)
Definition qdir.cpp:2568
QDebug operator<<(QDebug dbg, const QFileInfo &fi)
QIntrusiveList< QSGDistanceFieldGlyphConsumer, &QSGDistanceFieldGlyphConsumer::node > QSGDistanceFieldGlyphConsumerList