456QByteArray QShader::serialized(SerializedFormatVersion version)
const
458 static QShaderPrivate sd;
459 QShaderPrivate *dd = d ? d : &sd;
462 QDataStream ds(&buf);
463 ds.setVersion(QDataStream::Qt_5_10);
464 if (!buf.open(QIODevice::WriteOnly))
467 const int qsbVersion = QShaderPrivate::qtQsbVersion(version);
470 ds <<
int(dd->stage);
471 dd->desc.serialize(&ds, qsbVersion);
472 ds <<
int(dd->shaders.size());
473 for (
auto it = dd->shaders.cbegin(), itEnd = dd->shaders.cend(); it != itEnd; ++it) {
474 const QShaderKey &k(it.key());
475 writeShaderKey(&ds, k);
476 const QShaderCode &shader(dd->shaders.value(k));
477 ds << shader.shader();
478 ds << shader.entryPoint();
480 ds <<
int(dd->bindings.size());
481 for (
auto it = dd->bindings.cbegin(), itEnd = dd->bindings.cend(); it != itEnd; ++it) {
482 const QShaderKey &k(it.key());
483 writeShaderKey(&ds, k);
484 const NativeResourceBindingMap &map(it.value());
485 ds <<
int(map.size());
486 for (
auto mapIt = map.cbegin(), mapItEnd = map.cend(); mapIt != mapItEnd; ++mapIt) {
488 ds << mapIt.value().first;
489 ds << mapIt.value().second;
492 ds <<
int(dd->combinedImageMap.size());
493 for (
auto it = dd->combinedImageMap.cbegin(), itEnd = dd->combinedImageMap.cend(); it != itEnd; ++it) {
494 const QShaderKey &k(it.key());
495 writeShaderKey(&ds, k);
496 const SeparateToCombinedImageSamplerMappingList &list(it.value());
497 ds <<
int(list.size());
498 for (
auto listIt = list.cbegin(), listItEnd = list.cend(); listIt != listItEnd; ++listIt) {
499 ds << listIt->combinedSamplerName;
500 ds << listIt->textureBinding;
501 ds << listIt->samplerBinding;
504 if (qsbVersion > QShaderPrivate::QSB_VERSION_WITHOUT_NATIVE_SHADER_INFO) {
505 ds <<
int(dd->nativeShaderInfoMap.size());
506 for (
auto it = dd->nativeShaderInfoMap.cbegin(), itEnd = dd->nativeShaderInfoMap.cend(); it != itEnd; ++it) {
507 const QShaderKey &k(it.key());
508 writeShaderKey(&ds, k);
510 ds <<
int(it->extraBufferBindings.size());
511 for (
auto mapIt = it->extraBufferBindings.cbegin(), mapItEnd = it->extraBufferBindings.cend();
512 mapIt != mapItEnd; ++mapIt)
520 return qCompress(buf.buffer());
551QShader QShader::fromSerialized(
const QByteArray &data)
553 QByteArray udata = qUncompress(data);
555 QDataStream ds(&buf);
556 ds.setVersion(QDataStream::Qt_5_10);
557 if (!buf.open(QIODevice::ReadOnly))
562 QShaderPrivate *d = QShaderPrivate::get(&bs);
563 Q_ASSERT(d->ref.loadRelaxed() == 1);
566 d->qsbVersion = intVal;
567 if (d->qsbVersion != QShaderPrivate::QSB_VERSION
568 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_INPUT_OUTPUT_INTERFACE_BLOCKS
569 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_EXTENDED_STORAGE_BUFFER_INFO
570 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_NATIVE_SHADER_INFO
571 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_SEPARATE_IMAGES_AND_SAMPLERS
572 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_VAR_ARRAYDIMS
573 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITH_CBOR
574 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITH_BINARY_JSON
575 && d->qsbVersion != QShaderPrivate::QSB_VERSION_WITHOUT_BINDINGS)
577 qWarning(
"Attempted to deserialize QShader with unknown version %d.", d->qsbVersion);
582 d->stage = Stage(intVal);
583 if (d->qsbVersion > QShaderPrivate::QSB_VERSION_WITH_CBOR) {
584 d->desc = QShaderDescription::deserialize(&ds, d->qsbVersion);
585 }
else if (d->qsbVersion > QShaderPrivate::QSB_VERSION_WITH_BINARY_JSON) {
586 qWarning(
"Can no longer load QShaderDescription from CBOR.");
587 d->desc = QShaderDescription();
589 qWarning(
"Can no longer load QShaderDescription from binary JSON.");
590 d->desc = QShaderDescription();
594 for (
int i = 0; i < count; ++i) {
596 readShaderKey(&ds, &k);
602 shader.setEntryPoint(s);
603 d->shaders[k] = shader;
606 if (d->qsbVersion > QShaderPrivate::QSB_VERSION_WITHOUT_BINDINGS) {
608 for (
int i = 0; i < count; ++i) {
610 readShaderKey(&ds, &k);
611 NativeResourceBindingMap map;
614 for (
int b = 0; b < mapSize; ++b) {
617 int firstNativeBinding;
618 ds >> firstNativeBinding;
619 int secondNativeBinding;
620 ds >> secondNativeBinding;
621 map.insert(binding, { firstNativeBinding, secondNativeBinding });
623 d->bindings.insert(k, map);
627 if (d->qsbVersion > QShaderPrivate::QSB_VERSION_WITHOUT_SEPARATE_IMAGES_AND_SAMPLERS) {
629 for (
int i = 0; i < count; ++i) {
631 readShaderKey(&ds, &k);
632 SeparateToCombinedImageSamplerMappingList list;
635 for (
int b = 0; b < listSize; ++b) {
636 QByteArray combinedSamplerName;
637 ds >> combinedSamplerName;
639 ds >> textureBinding;
641 ds >> samplerBinding;
642 list.append({ combinedSamplerName, textureBinding, samplerBinding });
644 d->combinedImageMap.insert(k, list);
648 if (d->qsbVersion > QShaderPrivate::QSB_VERSION_WITHOUT_NATIVE_SHADER_INFO) {
650 for (
int i = 0; i < count; ++i) {
652 readShaderKey(&ds, &k);
655 QMap<
int,
int> extraBufferBindings;
658 for (
int b = 0; b < mapSize; ++b) {
662 extraBufferBindings.insert(k, v);
664 d->nativeShaderInfoMap.insert(k, { flags, extraBufferBindings });
816 QtPrivate::QHashCombineWithSeed hash(seed);
817 seed = hash(seed, s.stage());
818 if (!s.d->shaders.isEmpty()) {
819 seed = hash(seed, s.d->shaders.firstKey());
820 seed = hash(seed, std::as_const(s.d->shaders).first());