aboutsummaryrefslogtreecommitdiffstats
path: root/src/quick/scenegraph/qsgdefaultspritenode.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/quick/scenegraph/qsgdefaultspritenode.cpp')
-rw-r--r--src/quick/scenegraph/qsgdefaultspritenode.cpp77
1 files changed, 74 insertions, 3 deletions
diff --git a/src/quick/scenegraph/qsgdefaultspritenode.cpp b/src/quick/scenegraph/qsgdefaultspritenode.cpp
index 8761d99c1f..4d4d9f6971 100644
--- a/src/quick/scenegraph/qsgdefaultspritenode.cpp
+++ b/src/quick/scenegraph/qsgdefaultspritenode.cpp
@@ -84,6 +84,7 @@ public:
QQuickSpriteMaterial::QQuickSpriteMaterial()
{
setFlag(Blending, true);
+ setFlag(SupportsRhiShader, true);
}
QQuickSpriteMaterial::~QQuickSpriteMaterial()
@@ -91,10 +92,10 @@ QQuickSpriteMaterial::~QQuickSpriteMaterial()
delete texture;
}
-class SpriteMaterialData : public QSGMaterialShader
+class SpriteMaterialShader : public QSGMaterialShader
{
public:
- SpriteMaterialData()
+ SpriteMaterialShader()
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/sprite.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/sprite.frag"));
@@ -135,9 +136,79 @@ public:
int m_animPos_id;
};
+class SpriteMaterialRhiShader : public QSGMaterialRhiShader
+{
+public:
+ SpriteMaterialRhiShader();
+
+ bool updateUniformData(const RenderState &state,
+ QSGMaterial *newMaterial, QSGMaterial *oldMaterial) override;
+ void updateSampledImage(const RenderState &state, int binding, QSGTexture **texture,
+ QSGMaterial *newMaterial, QSGMaterial *oldMaterial) override;
+};
+
+SpriteMaterialRhiShader::SpriteMaterialRhiShader()
+{
+ setShaderFileName(VertexStage, QStringLiteral(":/qt-project.org/scenegraph/shaders_ng/sprite.vert.qsb"));
+ setShaderFileName(FragmentStage, QStringLiteral(":/qt-project.org/scenegraph/shaders_ng/sprite.frag.qsb"));
+}
+
+bool SpriteMaterialRhiShader::updateUniformData(const RenderState &state,
+ QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
+{
+#ifdef QT_NO_DEBUG
+ Q_UNUSED(oldMaterial);
+#endif
+ Q_ASSERT(oldMaterial == nullptr || newMaterial->type() == oldMaterial->type());
+ QQuickSpriteMaterial *mat = static_cast<QQuickSpriteMaterial *>(newMaterial);
+
+ bool changed = false;
+ QByteArray *buf = state.uniformData();
+ Q_ASSERT(buf->size() >= 96);
+
+ if (state.isMatrixDirty()) {
+ const QMatrix4x4 m = state.combinedMatrix();
+ memcpy(buf->data(), m.constData(), 64);
+ changed = true;
+ }
+
+ float animPosAndData[7] = { mat->animX1, mat->animY1, mat->animX2, mat->animY2,
+ mat->animW, mat->animH, mat->animT };
+ memcpy(buf->data() + 64, animPosAndData, 28);
+ changed = true;
+
+ if (state.isOpacityDirty()) {
+ const float opacity = state.opacity();
+ memcpy(buf->data() + 92, &opacity, 4);
+ changed = true;
+ }
+
+ return changed;
+}
+
+void SpriteMaterialRhiShader::updateSampledImage(const RenderState &state, int binding, QSGTexture **texture,
+ QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
+{
+ if (binding != 1)
+ return;
+
+#ifdef QT_NO_DEBUG
+ Q_UNUSED(oldMaterial);
+#endif
+ Q_ASSERT(oldMaterial == nullptr || newMaterial->type() == oldMaterial->type());
+ QQuickSpriteMaterial *mat = static_cast<QQuickSpriteMaterial *>(newMaterial);
+
+ QSGTexture *t = mat->texture;
+ t->updateRhiTexture(state.rhi(), state.resourceUpdateBatch());
+ *texture = t;
+}
+
QSGMaterialShader *QQuickSpriteMaterial::createShader() const
{
- return new SpriteMaterialData;
+ if (flags().testFlag(RhiShaderWanted))
+ return new SpriteMaterialRhiShader;
+ else
+ return new SpriteMaterialShader;
}
static QSGGeometry::Attribute Sprite_Attributes[] = {