7#include <QtQuick3DRuntimeRender/private/qssgrenderer_p.h>
8#include <QtQuick3DRuntimeRender/private/qssgrenderlight_p.h>
10#include <QtQuick3DRuntimeRender/private/qssgrendershadercache_p.h>
11#include <QtQuick3DRuntimeRender/private/qssgrendershaderlibrarymanager_p.h>
12#include <QtQuick3DRuntimeRender/private/qssgrendershadercodegenerator_p.h>
13#include <QtQuick3DRuntimeRender/private/qssgrenderdefaultmaterialshadergenerator_p.h>
14#include <QtQuick3DRuntimeRender/private/qssgshadermaterialadapter_p.h>
21 : m_programGenerator(&programGen)
22 , defaultMaterialShaderKeyProperties(materialProperties)
23 , materialAdapter(materialAdapter)
24 , hasCustomShadedMain(
false)
25 , skipCustomFragmentSnippet(
false)
29static inline void insertProcessorArgs(
QByteArray &snippet,
const char *argKey,
const char* (*argListFunc)(),
bool usesShared =
false,
bool isSharedInout =
false)
31 const int argKeyLen = int(strlen(argKey));
32 const int argKeyPos = snippet.indexOf(argKey);
35 snippet = snippet.left(argKeyPos) + argListFunc() + snippet.mid(argKeyPos + argKeyLen);
37 const char *inoutString = isSharedInout ?
", inout " :
", in ";
38 snippet = snippet.left(argKeyPos) + argListFunc() + inoutString +
QByteArrayLiteral(
"QT_SHARED_VARS SHARED") + snippet.mid(argKeyPos + argKeyLen);
96 return " qt_customMain(qt_vertPosition.xyz, qt_vertNormal, qt_vertUV0, qt_vertUV1, qt_vertTangent, qt_vertBinormal, qt_vertJoints, qt_vertWeights, qt_vertColor, qt_instancedModelMatrix, qt_instancedMVPMatrix);";
98 return " qt_customMain(qt_vertPosition.xyz, qt_vertNormal, qt_vertUV0, qt_vertUV1, qt_vertTangent, qt_vertBinormal, qt_vertJoints, qt_vertWeights, qt_vertColor);\n";
142 vertexShader.
addIncoming(
"qt_instanceTransform0",
"vec4");
143 vertexShader.
addIncoming(
"qt_instanceTransform1",
"vec4");
144 vertexShader.
addIncoming(
"qt_instanceTransform2",
"vec4");
145 vertexShader.
addIncoming(
"qt_instanceColor",
"vec4");
146 vertexShader.
addIncoming(
"qt_instanceData",
"vec4");
148 if (blendParticles) {
150 vertexShader.
addUniform(
"qt_particleTexture",
"sampler2D");
151 vertexShader.
addUniform(
"qt_countPerSlice",
"uint");
152 vertexShader.
addUniform(
"qt_oneOverParticleImageSize",
"vec2");
153 vertexShader.
addUniform(
"qt_particleMatrix",
"mat4");
154 vertexShader.
addUniform(
"qt_particleIndexOffset",
"uint");
159 if (usesFloatJointIndices)
165 vertexShader.
addUniform(
"qt_boneTexture",
"sampler2D");
170 vertexShader.
addUniform(
"qt_morphTargetTexture",
"sampler2DArray");
175 if (hasCustomVertexShader) {
177 shaderLibraryManager,
181 shaderLibraryManager))
190 vertexShader.
addUniform(
"qt_boneTexture",
"sampler2D");
195 vertexShader.
addInclude(
"morphanim_custom.glsllib");
198 vertexShader.
addUniform(
"qt_morphTargetTexture",
"sampler2DArray");
206 vertexShader << snippet;
209 vertexShader <<
"void main()"
216 vertexShader.
append(
" vec4 qt_vertPosition = vec4(attr_pos, 1.0);");
217 vertexShader.
append(
" vec3 qt_vertNormal = vec3(0.0);");
218 vertexShader.
append(
" vec3 qt_vertTangent = vec3(0.0);");
219 vertexShader.
append(
" vec3 qt_vertBinormal = vec3(0.0);");
220 if (meshHasTexCoord0 || hasCustomVertexShader)
221 vertexShader.
append(
" vec2 qt_vertUV0 = vec2(0.0);");
222 if (meshHasTexCoord1 || hasCustomVertexShader)
223 vertexShader.
append(
" vec2 qt_vertUV1 = vec2(0.0);");
225 vertexShader.
append(
" ivec4 qt_vertJoints = ivec4(0);");
226 if (meshHasJointsAndWeights ||
m_hasSkinning || hasCustomVertexShader)
227 vertexShader.
append(
" vec4 qt_vertWeights = vec4(0.0);");
228 if (meshHasColors ||
usesInstancing || blendParticles || hasCustomVertexShader || hasCustomFragmentShader)
229 vertexShader.
append(
" vec4 qt_vertColor = vec4(1.0);");
233 vertexShader.
addUniform(
"qt_modelViewProjection",
"mat4");
238 vertexShader.
addUniform(
"qt_modelMatrix",
"mat4");
239 vertexShader.
addUniform(
"qt_parentMatrix",
"mat4");
241 vertexShader.
addUniform(
"qt_viewProjectionMatrix",
"mat4");
254 if (hasCustomVertexShader || hasCustomFragmentShader) {
260 vertexShader.
addUniform(
"qt_viewProjectionMatrix",
"mat4");
261 vertexShader.
addUniform(
"qt_viewMatrix",
"mat4");
262 vertexShader.
addUniform(
"qt_cameraPosition",
"vec3");
263 vertexShader.
addUniform(
"qt_cameraDirection",
"vec3");
264 if (usesProjectionMatrix)
265 vertexShader.
addUniform(
"qt_projectionMatrix",
"mat4");
266 if (usesInvProjectionMatrix)
267 vertexShader.
addUniform(
"qt_inverseProjectionMatrix",
"mat4");
273 if (usesProjectionMatrix)
275 if (usesInvProjectionMatrix)
278 vertexShader.
addUniform(
"qt_modelMatrix",
"mat4");
279 vertexShader.
addUniform(
"qt_normalMatrix",
"mat3");
280 vertexShader.
addUniform(
"qt_cameraProperties",
"vec2");
288 vertexShader.
append(
" qt_viewIndex = gl_ViewIndex;");
289 }
else if (usesViewIndex) {
291 vertexShader.
append(
" qt_viewIndex = 0;");
294 if (meshHasNormals) {
295 vertexShader.
append(
" qt_vertNormal = attr_norm;");
298 if (meshHasTexCoord0) {
299 vertexShader.
append(
" qt_vertUV0 = attr_uv0;");
302 if (meshHasTexCoord1) {
303 vertexShader.
append(
" qt_vertUV1 = attr_uv1;");
306 if (meshHasTexCoordLightmap) {
307 vertexShader.
append(
" vec2 qt_vertLightmapUV = attr_lightmapuv;");
308 vertexShader.
addIncoming(
"attr_lightmapuv",
"vec2");
310 if (meshHasTangents) {
311 vertexShader.
append(
" qt_vertTangent = attr_textan;");
314 if (meshHasBinormals) {
315 vertexShader.
append(
" qt_vertBinormal = attr_binormal;");
319 vertexShader.
append(
" qt_vertColor = attr_color;");
323 if (meshHasJointsAndWeights && (
m_hasSkinning || hasCustomVertexShader)) {
324 if (usesFloatJointIndices) {
326 vertexShader.
append(
" qt_vertJoints = ivec4(attr_joints);");
329 vertexShader.
append(
" qt_vertJoints = attr_joints;");
332 vertexShader.
append(
" qt_vertWeights = attr_weights;");
336 vertexShader.
append(
" qt_vertColor *= qt_instanceColor;");
337 vertexShader.
append(
" mat4 qt_instanceMatrix = mat4(qt_instanceTransform0, qt_instanceTransform1, qt_instanceTransform2, vec4(0.0, 0.0, 0.0, 1.0));");
339 vertexShader.
append(
" mat4 qt_instancedModelMatrix = qt_parentMatrix * transpose(qt_instanceMatrix);");
341 vertexShader.
append(
" mat4 qt_instancedModelMatrix = qt_parentMatrix * transpose(qt_instanceMatrix) * qt_modelMatrix;");
342 vertexShader.
append(
" mat3 qt_instancedNormalMatrix = mat3(transpose(inverse(qt_instancedModelMatrix)));");
344 vertexShader.
append(
" mat4 qt_instancedMVPMatrix = qt_viewProjectionMatrix * qt_instancedModelMatrix;");
346 vertexShader.
append(
" mat4 qt_instancedMVPMatrix = qt_viewProjectionMatrix[qt_viewIndex] * qt_instancedModelMatrix;");
350 vertexShader <<
" vec3 qt_uTransform;\n";
351 vertexShader <<
" vec3 qt_vTransform;\n";
357 vertexShader.
append(
" qt_vertPosition.xyz = qt_getTargetPosition(qt_vertPosition.xyz);");
360 vertexShader.
append(
" mat4 skinMat = mat4(1);");
361 vertexShader.
append(
" if (qt_vertWeights != vec4(0.0)) {");
362 vertexShader.
append(
" skinMat = qt_getSkinMatrix(qt_vertJoints, qt_vertWeights);");
363 vertexShader.
append(
" qt_vertPosition = skinMat * qt_vertPosition;");
364 vertexShader.
append(
" }");
366 if (blendParticles) {
367 vertexShader.
append(
" qt_vertPosition.xyz = qt_applyParticle(qt_vertPosition.xyz, qt_vertNormal, qt_vertColor, qt_vertNormal, qt_vertColor, qt_particleMatrix);");
373 vertexShader.
append(
" gl_Position = qt_modelViewProjection * qt_vertPosition;");
375 vertexShader.
append(
" gl_Position = qt_modelViewProjection[qt_viewIndex] * qt_vertPosition;");
377 vertexShader.
append(
" gl_Position = qt_instancedMVPMatrix * qt_vertPosition;");
382 if (usesPointsTopology && !hasCustomVertexShader) {
383 vertexShader.
addUniform(
"qt_materialPointSize",
"float");
384 vertexShader.
append(
" gl_PointSize = qt_materialPointSize;");
395 shaderLibraryManager,
417 fragment() <<
" float qt_objectOpacity = qt_material_properties.a;\n";
422 vertex() <<
" " << inVarName <<
" = " << inVarValue <<
";\n";
430 vertexGenerator.addUniform(
"qt_normalMatrix",
"mat3");
432 vertexGenerator.append(
" qt_vertNormal = qt_getTargetNormal(qt_vertNormal);");
434 vertexGenerator.append(
" if (qt_vertWeights != vec4(0.0))");
435 vertexGenerator.append(
" qt_vertNormal = qt_getSkinNormalMatrix(qt_vertJoints, qt_vertWeights) * qt_vertNormal;");
441 vertexGenerator.append(
" vec3 qt_world_normal = normalize(qt_vertNormal);");
443 vertexGenerator.append(
" vec3 qt_world_normal = normalize(qt_normalMatrix * qt_vertNormal);");
445 vertexGenerator.append(
" vec3 qt_world_normal = normalize(qt_instancedNormalMatrix * qt_vertNormal);");
447 vertexGenerator.append(
" qt_varNormal = qt_world_normal;");
453 vertex() <<
" qt_vertTangent = qt_getTargetTangent(qt_vertTangent);\n";
455 vertex() <<
" if (qt_vertWeights != vec4(0.0))\n"
456 <<
" qt_vertTangent = (skinMat * vec4(qt_vertTangent, 0.0)).xyz;\n";
462 vertex() <<
" qt_varTangent = (qt_modelMatrix * vec4(qt_vertTangent, 0.0)).xyz;\n";
464 vertex() <<
" qt_varTangent = qt_vertTangent;\n";
466 vertex() <<
" qt_varTangent = (qt_instancedModelMatrix * vec4(qt_vertTangent, 0.0)).xyz;\n";
473 vertex() <<
" qt_vertBinormal = qt_getTargetBinormal(qt_vertBinormal);\n";
475 vertex() <<
" if (qt_vertWeights != vec4(0.0))\n"
476 <<
" qt_vertBinormal = (skinMat * vec4(qt_vertBinormal, 0.0)).xyz;\n";
481 vertex() <<
" qt_varBinormal = (qt_modelMatrix * vec4(qt_vertBinormal, 0.0)).xyz;\n";
483 vertex() <<
" qt_varBinormal = qt_vertBinormal;\n";
485 vertex() <<
" qt_varBinormal = (qt_instancedModelMatrix * vec4(qt_vertBinormal, 0.0)).xyz;\n";
505 fragment() <<
" qt_customMain();\n";
static constexpr QSSGShaderGeneratorStageFlags defaultFlags()
void beginProgram(QSSGShaderGeneratorStageFlags inEnabledStages=defaultFlags())
Combined button and popup list for selecting options.
#define QByteArrayLiteral(str)
static void insertVertexMainArgs(QByteArray &snippet)
static void insertPostProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertPointLightProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertAmbientLightProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertProcessorArgs(QByteArray &snippet, const char *argKey, const char *(*argListFunc)(), bool usesShared=false, bool isSharedInout=false)
static const char * customMainCallWithArguments(bool usesInstancing)
static void insertFragmentMainArgs(QByteArray &snippet, bool usesShared=false)
static void insertIblProbeProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertSpecularLightProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertVertexInstancedMainArgs(QByteArray &snippet)
static void insertVertexMainArgs(QByteArray &snippet)
static void insertSpotLightProcessorArgs(QByteArray &snippet, bool usesShared)
static void insertDirectionalLightProcessorArgs(QByteArray &snippet, bool usesShared)
static const char * vertexMainArgumentList()
static const char * vertexInstancedMainArgumentList()
static const char * postProcessorArgumentList()
static const char * specularLightProcessorArgumentList()
static const char * ambientLightProcessorArgumentList()
static const char * iblProbeProcessorArgumentList()
static const char * spotLightProcessorArgumentList()
static const char * pointLightProcessorArgumentList()
static const char * directionalLightProcessorArgumentList()
static const char * shadedFragmentMainArgumentList()
void addFlatParameter(const QByteArray &inParamName, const QByteArray &inParamType)
void beginVertexGeneration(const QSSGShaderDefaultMaterialKey &inKey, const QSSGShaderFeatures &inFeatureSet, QSSGShaderLibraryManager &shaderLibraryManager)
QSSGStageGeneratorBase & vertex()
QSSGShaderMaterialAdapter * materialAdapter
QSSGMaterialVertexPipeline(QSSGProgramGenerator &inProgram, const QSSGShaderDefaultMaterialKeyProperties &materialProperties, QSSGShaderMaterialAdapter *materialAdapter)
QSSGStageGeneratorBase & fragment()
void doGenerateVarTangent(const QSSGShaderDefaultMaterialKey &inKey)
void beginFragmentGeneration(QSSGShaderLibraryManager &shaderLibraryManager)
const QSSGShaderDefaultMaterialKeyProperties & defaultMaterialShaderKeyProperties
void doGenerateVarBinormal(const QSSGShaderDefaultMaterialKey &inKey)
void addInterpolationParameter(const QByteArray &inParamName, const QByteArray &inParamType)
void doGenerateWorldNormal(const QSSGShaderDefaultMaterialKey &inKey)
bool skipCustomFragmentSnippet
QSSGStageGeneratorBase & activeStage()
void endFragmentGeneration()
bool hasAttributeInKey(QSSGShaderKeyVertexAttribute::VertexAttributeBits inAttr, const QSSGShaderDefaultMaterialKey &inKey)
void assignOutput(const QByteArray &inVarName, const QByteArray &inVarValueExpr)
QSSGProgramGenerator * programGenerator() const
void endVertexGeneration()
QSSGShaderKeyBoolean m_usesInverseProjectionMatrix
QSSGShaderKeyBoolean m_usesProjectionMatrix
QSSGShaderKeyBoolean m_usesInstancing
QSSGShaderKeyBoolean m_blendParticles
QSSGShaderKeyBoolean m_overridesPosition
QSSGShaderKeyBoolean m_usesFloatJointIndices
QSSGShaderKeyBoolean m_usesViewIndex
QSSGShaderKeyUnsigned< 16 > m_boneCount
QSSGShaderKeyVertexAttribute m_vertexAttributes
QSSGShaderKeyUnsigned< 3 > m_viewCount
QSSGShaderKeyUnsigned< 8 > m_targetCount
QSSGShaderKeyBoolean m_usesPointsTopology
bool getValue(QSSGDataView< quint32 > inDataStore) const
quint32 getValue(QSSGDataView< quint32 > inDataStore) const
bool getBitValue(VertexAttributeBits bit, QSSGDataView< quint32 > inKeySet) const
virtual bool usesCustomMorphing()=0
virtual bool isUnshaded()
virtual bool usesCustomSkinning()=0
virtual bool hasCustomShaderFunction(QSSGShaderCache::ShaderType shaderType, const QByteArray &funcName, QSSGShaderLibraryManager &shaderLibraryManager)
virtual QByteArray customShaderSnippet(QSSGShaderCache::ShaderType type, QSSGShaderLibraryManager &shaderLibraryManager, bool multiViewCompatible)
virtual bool hasCustomShaderSnippet(QSSGShaderCache::ShaderType type)
virtual bool usesSharedVariables()
virtual void addFlatIncoming(const QByteArray &name, const QByteArray &type)
virtual void addFlatOutgoing(const QByteArray &name, const QByteArray &type)
virtual void addUniformArray(const QByteArray &name, const QByteArray &type, quint32 size)
virtual void addUniform(const QByteArray &name, const QByteArray &type)
virtual void append(const QByteArray &data)
virtual void addOutgoing(const QByteArray &name, const QByteArray &type)
virtual void addIncoming(const QByteArray &name, const QByteArray &type)
virtual void addInclude(const QByteArray &name) final