QSGMaterialShader Class

QSGMaterialShaderクラスは、グラフィックスAPIに依存しないシェーダープログラムを表します。詳細...

Header: #include <QSGMaterialShader>
CMake: find_package(Qt6 REQUIRED COMPONENTS Quick)
target_link_libraries(mytarget PRIVATE Qt6::Quick)
qmake: QT += quick

パブリックタイプ

struct GraphicsPipelineState
class RenderState
enum Flag { UpdatesGraphicsPipelineState }
flags Flags

パブリック関数

QSGMaterialShader()
(since 6.4) int combinedImageSamplerCount(int binding) const
QSGMaterialShader::Flags flags() const
void setFlag(QSGMaterialShader::Flags flags, bool on = true)
void setFlags(QSGMaterialShader::Flags flags)
virtual bool updateGraphicsPipelineState(QSGMaterialShader::RenderState &state, QSGMaterialShader::GraphicsPipelineState *ps, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
virtual void updateSampledImage(QSGMaterialShader::RenderState &state, int binding, QSGTexture **texture, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
virtual bool updateUniformData(QSGMaterialShader::RenderState &state, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)

保護された関数

void setShader(QSGMaterialShader::Stage stage, const QShader &shader)
void setShaderFileName(QSGMaterialShader::Stage stage, const QString &filename)
(since 6.8) void setShaderFileName(QSGMaterialShader::Stage stage, const QString &filename, int viewCount)

詳細説明

QSGMaterialShader は、頂点シェーダとフラグメントシェーダ、グラフィックスパイプラインの状態変化を定義するデータ、ユニフォームバッファやテクスチャなどのグラフィックスリソースを更新するロジックの組み合わせを表します。

注意: QSG 接頭辞を持つすべてのクラスは、シーングラフのレンダリングスレッドでのみ使用する必要があります。詳細はシーングラフとレンダリングを参照してください。

QSGMaterial と QSGMaterialShader は、緊密な関係を形成しています。1つのシーングラフ(ネストされたグラフを含む)に対して、シーングラフがそのマテリアルでオブジェクトをレンダリングするために使用するシェーダと他のデータをカプセル化する、1つのユニークなQSGMaterialShaderインスタンスがあります。各QSGGeometryNode は、ノードの描画中にグラフィック パイプラインがどのように設定されなければならないかを定義する一意のQSGMaterial を持つことができます。QSGMaterialShaderのインスタンスは、ユーザーによって明示的に作成されることはなく、QSGMaterial::createShader ()を通してシーングラフによってオンデマンドで作成されます。シーングラフは、QSGMaterial::createShader ()メソッドを呼び出すことで QSGMaterialShader のインスタンスを作成し、各シェーダー実装のインスタンスが 1 つだけ存在するようにします。

Qt 5 では、QSGMaterialShader は OpenGL に関連付けられていました。Qt 5では、QSGMaterialShaderはOpenGLと結びついており、QOpenGLShaderProgram で直接ビルドされ、updateState() のように任意のOpenGLコマンドを発行できる関数を持っていました。Qt 6 ではこのようなことはなくなりました。QSGMaterialShaderは厳密にはデータ指向ではありません。つまり、データ(シェーダーと希望するパイプライン状態の変更)を、統一されたバッファ内のデータを更新するロジックとともに提供します。グラフィックスAPIへのアクセスは提供されません。これは、QSGMaterialShaderがそれ自身でOpenGL、Vulkan、Metal、またはDirect 3Dの呼び出しを行えないことを意味します。統一されたシェーダ管理と合わせて、これによってQSGMaterialShaderを一度書くだけで、サポートされているグラフィックスAPIのどれでも実行時に機能させることができます。

保護されたsetShaderFileName() 関数を呼び出すことによって設定されたシェーダは、ジオメトリからの頂点データでマテリアルが何を行うか、そしてフラグメントがどのようにシェーディングされるかを制御します。QSGMaterialShader は通常、構築時に頂点シェーダとフラグメントシェーダを設定します。後からシェーダを変更すると、期待した効果が得られないことがあるので、避ける必要があります。

Qt 6 では、デフォルトのアプローチとして、.qsb ファイルをアプリケーションと一緒に出荷します。通常、リソースシステムを介して埋め込まれ、setShaderFileName() を呼び出すときに参照されます。.qsb ファイルは、Qt Shader Tools モジュールのqsb ツールを使用して、Vulkan スタイルの GLSL ソースコードからオフラインで、または遅くともアプリケーションのビルド時に生成されます。

オーバーライドできるバーチャルは3つあります。これらは、均一なバッファ、テクスチャ、パイプラインの状態変更のためのデータ、またはデータを生成するロジックを提供します。

updateUniformData() は、サブクラスで最も一般的に再実装される関数です。この関数は、QByteArray の内容を更新し、ユニフォームバッファとしてシェーダに公開します。頂点シェーダまたはフラグメントシェーダにユニフォームブロックを持つ QSGMaterialShader は、updateUniformData() を再実装する必要があります。

updateSampledImage() は、シェーダコードがテクスチャをサンプリングするときに関連します。この関数は、各サンプラー(または関連する API では、組み合わ せたイメージサンプラー)に対して呼び出され、どのQSGTexture をシェー ダに公開するかを指定するオプションを与えます。

シェーダパイプラインの状態変更は、あまり使用されません。使用例としては、特定のブレンドモ ードを使用したいマテリアルがあります。関連する関数はupdateGraphicsPipelineState() です。この関数は、QSGMaterialShader がフラグUpdatesGraphicsPipelineState を設定してオプトインしていない限り呼び出されません。この関数のタスクは、渡されたGraphicsPipelineState 構造体インスタンスを希望する変更で更新することです。現在のところ、ブレンディングとカリング関連の機能のみが利用可能で、その他の状態はマテリアルによって制御できません。

テクスチャのサポートも含む最小限の例としては、次のようなものがあります。ここでは、Material がcreateShader() で Shader のインスタンスを作成するQSGMaterial であり、フラグメントシェーダでサンプリングしたいQSGTexture を保持していると仮定します。頂点シェーダはモデルビュー投影行列にのみ依存します。

class Shader : public QSGMaterialShader
{
public:
    Shader()
    {
        setShaderFileName(VertexStage, QLatin1String(":/materialshader.vert.qsb"));
        setShaderFileName(FragmentStage, QLatin1String(":/materialshader.frag.qsb"));
    }

    bool updateUniformData(RenderState &state, QSGMaterial *, QSGMaterial *)
    {
        bool changed = false;
        QByteArray *buf = state.uniformData();
        if (state.isMatrixDirty()) {
            const QMatrix4x4 m = state.combinedMatrix();
            memcpy(buf->data(), m.constData(), 64);
            changed = true;
        }
        return changed;
    }

    void updateSampledImage(RenderState &, int binding, QSGTexture **texture, QSGMaterial *newMaterial, QSGMaterial *)
    {
        Material *mat = static_cast<Material *>(newMaterial);
        if (binding == 1)
            *texture = mat->texture();
    }
};

シェーダ用の Vulkan スタイルの GLSL ソースコードは以下のようになります。これらは、Shader() コンストラクタで参照される.qsb ファイルを生成するqsb ツールを使用してオフラインで前処理されることが期待されます。

#version 440
layout(location = 0) in vec4 aVertex;
layout(location = 1) in vec2 aTexCoord;
layout(location = 0) out vec2 vTexCoord;
layout(std140, binding = 0) uniform buf {
    mat4 qt_Matrix;
} ubuf;
out gl_PerVertex { vec4 gl_Position; };
void main() {
    gl_Position = ubuf.qt_Matrix * aVertex;
    vTexCoord = aTexCoord;
}
#version 440
layout(location = 0) in vec2 vTexCoord;
layout(location = 0) out vec4 fragColor;
layout(binding = 1) uniform sampler2D srcTex;
void main() {
    vec4 c = texture(srcTex, vTexCoord);
    fragColor = vec4(c.rgb * 0.5, 1.0);
}

注意: QSG接頭辞を持つすべてのクラスは、シーングラフのレンダリングスレッドでのみ使用する必要があります。詳しくはScene Graph and Renderingを参照してください。

QSGMaterialScene Graph - Custom MaterialScene Graph - Two Texture ProvidersScene Graph - Graphも参照して ください。

メンバータイプ ドキュメント

enum QSGMaterialShader::Flag
flags QSGMaterialShader::Flags

特別なマテリアルプロパティを示すフラグ値。

定数説明
QSGMaterialShader::UpdatesGraphicsPipelineState0x0001このフラグを設定すると、updateGraphicsPipelineState() を呼び出すことができます。

Flags 型はQFlags<Flag> の typedef です。Flag値のORの組み合わせを格納する。

メンバ関数の説明

QSGMaterialShader::QSGMaterialShader()

新しい QSGMaterialShader を構築します。

[since 6.4] int QSGMaterialShader::combinedImageSamplerCount(int binding) const

binding にある結合イメージサンプラー変数の要素数を返す。この値はシェーダーコードからイントロスペクトされます。変数は配列で、複数の次元を持つことができます。

カウントは、変数内の結合イメージサンプラー項目の総数を反映します。次の例では、srcA のカウントは 1、srcB のカウントは 4、srcC のカウントは 6 です。

layout (binding = 0) uniform sampler2D srcA;
layout (binding = 1) uniform sampler2D srcB[4];
layout (binding = 2) uniform sampler2D srcC[2][3];

このカウントは、QSGMaterialShader::updateSampledImage の texture パラメータ内のQSGTexture ポインタの数です。

この関数は Qt 6.4 で導入されました。

QSGMaterialShader::updateSampledImageも参照してください

QSGMaterialShader::Flags QSGMaterialShader::flags() const

このマテリアルシェーダーに現在設定されているフラグを返します。

setFlags()も参照して ください。

void QSGMaterialShader::setFlag(QSGMaterialShader::Flags flags, bool on = true)

on が真の場合、このマテリアルシェーダにflags を設定します。そうでない場合、指定されたフラグをクリアします。

void QSGMaterialShader::setFlags(QSGMaterialShader::Flags flags)

このマテリアルシェーダにflags を設定します。

flags() も参照

[protected] void QSGMaterialShader::setShader(QSGMaterialShader::Stage stage, const QShader &shader)

指定されたstage に対してshader を設定します。

[protected] void QSGMaterialShader::setShaderFileName(QSGMaterialShader::Stage stage, const QString &filename)

指定されたstage のシェーダーのfilename を設定します。

ファイルには、シリアライズされたQShader が含まれることが期待されます。

[protected, since 6.8] void QSGMaterialShader::setShaderFileName(QSGMaterialShader::Stage stage, const QString &filename, int viewCount)

指定されたstage のシェーダーのfilename を設定します。

ファイルには、シリアライズされたQShader が含まれることが期待されます。

このオーバーロードは、multiview レンダリングを有効にするとき、特にビルドシステムの MULTIVIEW 便利オプションが使用されるときに使用されます。

viewCount は2、3、または4でなければならない。 はこれに基づいて自動的に調整されます。filename

この関数は Qt 6.8 で導入されました。

[virtual] bool QSGMaterialShader::updateGraphicsPipelineState(QSGMaterialShader::RenderState &state, QSGMaterialShader::GraphicsPipelineState *ps, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)

この関数は、シーングラフによって呼び出され、マテリアルがグラフィックスの状態のカスタムセットを提供できるようにします。マテリアルでカスタマイズ可能なステートのセットは、ブレンドと関連する設定に限られています。

注意: この関数は、setFlags ()を介してUpdatesGraphicsPipelineState フラグが有効になっている場合にのみ呼び出されます。デフォルトでは設定されていないため、この関数が呼び出されることはありません。

ps のメンバのいずれかに変更が加えられるたびに、戻り値はtrue でなければならない。

注意: ps の内容は、この関数の呼び出し間で永続化されません。

現在のレンダリングstate はシーングラフから渡される。

サブクラス固有の状態は、newMaterial から抽出できます。oldMaterial が NULL の場合、このシェーダーはちょうどアクティブになったところです。

[virtual] void QSGMaterialShader::updateSampledImage(QSGMaterialShader::RenderState &state, int binding, QSGTexture **texture, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)

この関数はシーングラフによって呼び出され、シェーダでサンプリング画像を使用する準備をします。

binding はサンプラーのバインディング番号です。この関数は、 に関連するシェーダーコードの各複合イメージサンプラー変数に対して呼び出されます。QSGMaterialShader

texture は ポインタの配列です。配列の要素数は、シェーダーコードで指定されたイメージサンプラー変数の要素数と一致します。この変数は配列であってもよく、複数の次元を有してもよい。配列の要素数は、次の方法で求めることができます。QSGTexture QSGMaterialShader::combinedImageSamplerCount

texture の要素が NULL の場合、リターンする前に有効なQSGTexture ポインタに設定する必要があります。nullでない場合、新しいQSGTexture * を格納するか、すでに知られているQSGTexture のパラメータを更新するかは、素材次第である。QSGTexture の所有権は移譲されない。

現在のレンダリングstate はシーングラフから渡される。関連する場合、QSGTexture::commitTextureOperations ()を介してテクスチャデータのアップロードをエンキューイングするトリガーは、マテリアル次第です。

サブクラス固有の状態は、newMaterial から抽出できます。

oldMaterial を使用すると、変更を最小限に抑えることができます。 が NULL の場合、このシェーダはアクティベートされただけです。oldMaterial

QSGMaterialShader::combinedImageSamplerCountも参照してください

[virtual] bool QSGMaterialShader::updateUniformData(QSGMaterialShader::RenderState &state, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)

この関数は、シェーダプログラムのユニフォームバッファの内容を更新するために、シーングラフによって呼び出されます。この実装は、実際のグラフィックス操作を実行することは期待されておらず、単にRenderState::uniformData() から返されたQByteArray にデータをコピーする責任を負うだけです。シーングラフは、シェーダーでそのバッファが見えるようにする面倒を見る。

現在のレンダリングstate は、シーングラフから渡される。状態が関連する状態がダーティであることを示す場合、実装は、RenderState::uniformData ()を介してアクセス可能なバッファデータ内の適切な領域を更新する必要があります。行列や不透明度などの状態がダーティでない場合、データは永続的であるため、対応する領域に触れる必要はない。

一様なデータに何らかの変更が加えられるたびに、戻り値はtrue でなければならない。

フラットカラー素材の色など、サブクラス固有の状態は、それに応じてバッファ内の関連領域を更新するために、newMaterial から抽出する必要があります。

oldMaterial を使用すると、マテリアルの状態を更新する際のバッファの変更(通常はmemcpy呼び出し)を最小限に抑えることができます。 が NULL の場合、このシェーダは起動されたばかりです。oldMaterial

本書に含まれる文書の著作権は、それぞれの所有者に帰属します。 本書で提供されるドキュメントは、Free Software Foundation が発行したGNU Free Documentation License version 1.3に基づいてライセンスされています。 Qtおよびそれぞれのロゴは、フィンランドおよびその他の国におけるThe Qt Company Ltd.の 商標です。その他すべての商標は、それぞれの所有者に帰属します。