198void QSGMaterialShaderPrivate::prepare(QShader::Variant vertexShaderVariant)
203 memset(
static_cast<
void *>(combinedImageSamplerBindings), 0,
sizeof(combinedImageSamplerBindings));
204 memset(
static_cast<
void *>(combinedImageSamplerCount), 0,
sizeof(combinedImageSamplerCount));
205 vertexShader = fragmentShader =
nullptr;
206 masterUniformData.clear();
208 clearCachedRendererData();
210 for (QShader::Stage stage : { QShader::VertexStage, QShader::FragmentStage }) {
211 auto it = shaderFileNames.constFind(stage);
212 if (it != shaderFileNames.cend()) {
213 const QShader s = loadShader(*it);
216 shaders[stage] = ShaderStageData(s);
218 shaderFileNames.erase(it);
222 auto vsIt = shaders.find(QShader::VertexStage);
223 if (vsIt != shaders.end()) {
224 vsIt->shaderVariant = vertexShaderVariant;
225 vsIt->vertexInputLocations.clear();
226 vsIt->qt_order_attrib_location = -1;
228 const QShaderDescription desc = vsIt->shader.description();
229 const QVector<QShaderDescription::InOutVariable> vertexInputs = desc.inputVariables();
230 for (
const QShaderDescription::InOutVariable &v : vertexInputs) {
231 if (vertexShaderVariant == QShader::BatchableVertexShader
232 && v.name == QByteArrayLiteral(
"_qt_order")) {
233 vsIt->qt_order_attrib_location = v.location;
235 vsIt->vertexInputLocations.append(v.location);
239 if (vsIt->vertexInputLocations.contains(vsIt->qt_order_attrib_location)) {
240 qWarning(
"Vertex input clash in rewritten (batchable) vertex shader at input location %d. "
241 "Vertex shaders must avoid using this location.", vsIt->qt_order_attrib_location);
245 for (
auto it = shaders.begin(); it != shaders.end(); ++it) {
246 const QShaderDescription desc = it->shader.description();
248 const QVector<QShaderDescription::UniformBlock> ubufs = desc.uniformBlocks();
249 const int ubufCount = ubufs.size();
251 qWarning(
"Multiple uniform blocks found in shader. "
252 "This should be avoided as Qt Quick supports only one.");
254 for (
int i = 0; i < ubufCount; ++i) {
255 const QShaderDescription::UniformBlock &ubuf(ubufs[i]);
256 if (ubufBinding == -1 && ubuf.binding >= 0) {
257 ubufBinding = ubuf.binding;
258 ubufSize = ubuf.size;
259 ubufStages |= toSrbStage(it->shader.stage());
260 masterUniformData.fill(
'\0', ubufSize);
261 }
else if (ubufBinding == ubuf.binding && ubuf.binding >= 0) {
262 if (ubuf.size > ubufSize) {
263 ubufSize = ubuf.size;
264 masterUniformData.fill(
'\0', ubufSize);
266 ubufStages |= toSrbStage(it->shader.stage());
268 qWarning(
"Uniform block %s (binding %d) ignored", ubuf.blockName.constData(),
273 const QVector<QShaderDescription::InOutVariable> imageSamplers = desc.combinedImageSamplers();
274 const int imageSamplersCount = imageSamplers.size();
275 for (
int i = 0; i < imageSamplersCount; ++i) {
276 const QShaderDescription::InOutVariable &var(imageSamplers[i]);
281 if (var.binding < MAX_SHADER_RESOURCE_BINDINGS) {
282 combinedImageSamplerBindings[var.binding] |= toSrbStage(it->shader.stage());
285 for (
int dim : var.arrayDims)
288 combinedImageSamplerCount[var.binding] = count;
290 qWarning(
"Encountered invalid combined image sampler (%s) binding %d",
291 var.name.constData(), var.binding);
295 if (it.key() == QShader::VertexStage)
296 vertexShader = &it.value();
297 else if (it.key() == QShader::FragmentStage)
298 fragmentShader = &it.value();
301 if (vertexShader && vertexShaderVariant == QShader::BatchableVertexShader && vertexShader->qt_order_attrib_location == -1)
302 qWarning(
"No rewriter-inserted attribute found, this should not happen.");