summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAntti Määttä <antti.maatta@qt.io>2020-02-07 14:12:42 +0200
committerAntti Määttä <antti.maatta@qt.io>2020-02-10 14:02:35 +0200
commitbff0bf78b328b730843abf0e79f58e8411908de5 (patch)
tree6fcf341f3d79dfc6d9af50d52b99f4c603fba287
parent90dd0bdcf1c9e3a1eddee8abcf4307c06e82e37b (diff)
Implement shader cache loading error handling
Task-number: QT3DS-4040 Change-Id: Ie5f8284ab76cd4aa5f3ff0701457f4ef84c3e215 Reviewed-by: Tomi Korpipää <tomi.korpipaa@qt.io> Reviewed-by: Miikka Heikkinen <miikka.heikkinen@qt.io>
-rw-r--r--src/api/studio3d/q3dspresentation.h1
-rw-r--r--src/api/studio3dqml/q3dsrenderer.cpp2
-rw-r--r--src/api/studio3dqml/q3dsrenderer_p.h1
-rw-r--r--src/api/studio3dqml/q3dsstudio3d.cpp2
-rw-r--r--src/engine/Qt3DSRuntimeView.cpp9
-rw-r--r--src/engine/Qt3DSRuntimeView.h3
-rw-r--r--src/runtime/Qt3DSApplication.cpp11
-rw-r--r--src/runtime/Qt3DSApplication.h3
-rw-r--r--src/runtimerender/Qt3DSRenderShaderCache.cpp19
-rw-r--r--src/runtimerender/Qt3DSRenderShaderCache.h2
-rw-r--r--src/viewer/Qt3DSViewerApp.cpp7
-rw-r--r--src/viewer/Qt3DSViewerApp.h1
12 files changed, 45 insertions, 16 deletions
diff --git a/src/api/studio3d/q3dspresentation.h b/src/api/studio3d/q3dspresentation.h
index 114eaec..1e8dedf 100644
--- a/src/api/studio3d/q3dspresentation.h
+++ b/src/api/studio3d/q3dspresentation.h
@@ -160,6 +160,7 @@ Q_SIGNALS:
void meshesCreated(const QStringList &meshNames, const QString &error);
void shaderCacheFileChanged(const QUrl &fileName);
void shaderCacheExported(bool success);
+ void shaderCacheLoadErrors(const QString &errors);
private:
Q_DISABLE_COPY(Q3DSPresentation)
diff --git a/src/api/studio3dqml/q3dsrenderer.cpp b/src/api/studio3dqml/q3dsrenderer.cpp
index c902934..1f78bf7 100644
--- a/src/api/studio3dqml/q3dsrenderer.cpp
+++ b/src/api/studio3dqml/q3dsrenderer.cpp
@@ -235,6 +235,8 @@ bool Q3DSRenderer::initializeRuntime(QOpenGLFramebufferObject *inFbo)
this, &Q3DSRenderer::presentationReady);
connect(m_runtime, &Q3DSViewer::Q3DSViewerApp::SigPresentationLoaded,
this, &Q3DSRenderer::presentationLoaded);
+ connect(m_runtime, &Q3DSViewer::Q3DSViewerApp::SigLoadShaderCacheErrors,
+ this, &Q3DSRenderer::shaderCacheLoadErrors);
int theWidth = inFbo->width();
int theHeight = inFbo->height();
diff --git a/src/api/studio3dqml/q3dsrenderer_p.h b/src/api/studio3dqml/q3dsrenderer_p.h
index dbc85a2..0ba6c31 100644
--- a/src/api/studio3dqml/q3dsrenderer_p.h
+++ b/src/api/studio3dqml/q3dsrenderer_p.h
@@ -81,6 +81,7 @@ Q_SIGNALS:
void materialsCreated(const QStringList &materialNames, const QString &error);
void meshesCreated(const QStringList &meshNames, const QString &error);
void dataOutputValueUpdated(const QString &name, const QVariant &newValue);
+ void shaderCacheLoadErrors(const QString &errors);
protected Q_SLOTS:
void handleRuntimeInitializedAsync();
diff --git a/src/api/studio3dqml/q3dsstudio3d.cpp b/src/api/studio3dqml/q3dsstudio3d.cpp
index f1e383f..503b713 100644
--- a/src/api/studio3dqml/q3dsstudio3d.cpp
+++ b/src/api/studio3dqml/q3dsstudio3d.cpp
@@ -430,6 +430,8 @@ QQuickFramebufferObject::Renderer *Q3DSStudio3D::createRenderer() const
m_presentation->d_ptr, &Q3DSPresentationPrivate::handleMaterialsCreated);
connect(renderer, &Q3DSRenderer::meshesCreated,
m_presentation->d_ptr, &Q3DSPresentationPrivate::handleMeshesCreated);
+ connect(renderer, &Q3DSRenderer::shaderCacheLoadErrors,
+ m_presentation, &Q3DSPresentation::shaderCacheLoadErrors);
connect(renderer, &Q3DSRenderer::exitSlide,
m_presentation, &Q3DSPresentation::slideExited);
connect(renderer, &Q3DSRenderer::customSignalEmitted,
diff --git a/src/engine/Qt3DSRuntimeView.cpp b/src/engine/Qt3DSRuntimeView.cpp
index c1b5669..7cebdd6 100644
--- a/src/engine/Qt3DSRuntimeView.cpp
+++ b/src/engine/Qt3DSRuntimeView.cpp
@@ -172,7 +172,8 @@ public:
bool BeginLoad(const QString &sourcePath, const QStringList &variantList) override;
bool HasOfflineLoadingCompleted() override;
bool InitializeGraphics(const QSurfaceFormat &format, bool delayedLoading,
- bool initInRenderThread, const QByteArray &shaderCache) override;
+ bool initInRenderThread, const QByteArray &shaderCache,
+ QString &errors) override;
void connectSignals() override;
void finishAsyncInit() override;
@@ -302,7 +303,8 @@ bool CRuntimeView::HasOfflineLoadingCompleted()
}
bool CRuntimeView::InitializeGraphics(const QSurfaceFormat &format, bool delayedLoading,
- bool initInRenderThread, const QByteArray &shaderCache)
+ bool initInRenderThread, const QByteArray &shaderCache,
+ QString &errors)
{
m_ApplicationCore->EndLoad();
// Next call will initialize the render portion of the scenes. This *must* have a loaded
@@ -311,7 +313,8 @@ bool CRuntimeView::InitializeGraphics(const QSurfaceFormat &format, bool delayed
m_Application
= m_ApplicationCore->CreateApplication(*m_InputEngine, m_AudioPlayer,
*m_RuntimeFactory, shaderCache,
- initInRenderThread);
+ initInRenderThread,
+ errors);
if (!m_Application->createSuccessful())
return false;
diff --git a/src/engine/Qt3DSRuntimeView.h b/src/engine/Qt3DSRuntimeView.h
index e0061b0..e114633 100644
--- a/src/engine/Qt3DSRuntimeView.h
+++ b/src/engine/Qt3DSRuntimeView.h
@@ -177,7 +177,8 @@ public: // loading
virtual bool BeginLoad(const QString &sourcePath, const QStringList &variantList) = 0;
virtual bool HasOfflineLoadingCompleted() = 0;
virtual bool InitializeGraphics(const QSurfaceFormat &format, bool delayedLoading,
- bool initInRenderThread, const QByteArray &shaderCache) = 0;
+ bool initInRenderThread, const QByteArray &shaderCache,
+ QString &errors) = 0;
virtual void connectSignals() = 0;
virtual void finishAsyncInit() = 0;
diff --git a/src/runtime/Qt3DSApplication.cpp b/src/runtime/Qt3DSApplication.cpp
index 20a8e5a..b8d3d31 100644
--- a/src/runtime/Qt3DSApplication.cpp
+++ b/src/runtime/Qt3DSApplication.cpp
@@ -1801,7 +1801,8 @@ struct SApp : public IApplication
Q3DStudio::IAudioPlayer *inAudioPlayer,
Q3DStudio::IRuntimeFactory &inFactory,
const QByteArray &shaderCache,
- bool initInRenderThread) override
+ bool initInRenderThread,
+ QString &shaderCacheErrors) override
{
{
QT3DS_PERF_SCOPED_TIMER(m_CoreFactory->GetPerfTimer(),
@@ -1871,8 +1872,12 @@ struct SApp : public IApplication
}
- if (!shaderCache.isEmpty())
- inFactory.GetQt3DSRenderContext().GetShaderCache().importShaderCache(shaderCache);
+ if (!shaderCache.isEmpty()) {
+ QString errors;
+ inFactory.GetQt3DSRenderContext().GetShaderCache().importShaderCache(shaderCache, errors);
+ if (!errors.isEmpty())
+ shaderCacheErrors = errors;
+ }
m_AudioPlayer.SetPlayer(inAudioPlayer);
diff --git a/src/runtime/Qt3DSApplication.h b/src/runtime/Qt3DSApplication.h
index 97d8528..ce1b366 100644
--- a/src/runtime/Qt3DSApplication.h
+++ b/src/runtime/Qt3DSApplication.h
@@ -251,7 +251,8 @@ public:
Q3DStudio::IAudioPlayer *inAudioPlayer,
Q3DStudio::IRuntimeFactory &inFactory,
const QByteArray &shaderCache,
- bool initInRenderThread) = 0;
+ bool initInRenderThread,
+ QString &shaderCacheErrors) = 0;
// maintains reference to runtime factory core. AppDir is where the executable is located;
// the system will expect res directory
diff --git a/src/runtimerender/Qt3DSRenderShaderCache.cpp b/src/runtimerender/Qt3DSRenderShaderCache.cpp
index e26405c..3794a83 100644
--- a/src/runtimerender/Qt3DSRenderShaderCache.cpp
+++ b/src/runtimerender/Qt3DSRenderShaderCache.cpp
@@ -571,10 +571,11 @@ struct ShaderCache : public IShaderCache
return retval;
}
- void importShaderCache(const QByteArray &shaderCache) override
+ void importShaderCache(const QByteArray &shaderCache, QString &errors) override
{
#define BAILOUT(details) { \
- qWarning() << "importShaderCache failed to import shader cache:" << details; \
+ errors = "importShaderCache failed to import shader cache: " details; \
+ qWarning() << errors; \
return; \
}
@@ -634,9 +635,13 @@ struct ShaderCache : public IShaderCache
qCInfo(TRACE_INFO) << "Loading binary program from shader cache: '<" << key << ">'";
eastl::pair<TShaderMap::iterator, bool> theInserter = m_Shaders.insert(tempKey);
- theInserter.first->second
- = m_RenderContext.CompileBinary(theKey, format, binary).mShader;
- theShader = theInserter.first->second;
+ auto ret = m_RenderContext.CompileBinary(theKey, format, binary);
+ if (!ret.errors.isEmpty()) {
+ errors += ret.errors + "\n";
+ } else {
+ theInserter.first->second = ret.mShader;
+ theShader = ret.mShader;
+ }
} else {
QByteArray loadVertexData;
QByteArray loadFragmentData;
@@ -663,6 +668,10 @@ struct ShaderCache : public IShaderCache
qt3ds::foundation::toDataRef(
features.data(), static_cast<QT3DSU32>(features.size())),
error, false, true);
+ if (!error.isEmpty()) {
+ errors += error + "\n";
+ theShader = nullptr;
+ }
}
}
// If something doesn't save or load correctly, get the runtime to re-generate.
diff --git a/src/runtimerender/Qt3DSRenderShaderCache.h b/src/runtimerender/Qt3DSRenderShaderCache.h
index d03bc65..35713bd 100644
--- a/src/runtimerender/Qt3DSRenderShaderCache.h
+++ b/src/runtimerender/Qt3DSRenderShaderCache.h
@@ -103,7 +103,7 @@ namespace render {
// source code is exported
virtual QByteArray exportShaderCache(bool binaryShaders) = 0;
// This call immediately blocks and attempts to load all shaders from the shaderCache
- virtual void importShaderCache(const QByteArray &shaderCache) = 0;
+ virtual void importShaderCache(const QByteArray &shaderCache, QString &errors) = 0;
// It is up to the caller to ensure that inFeatures contains unique keys.
// It is also up the the caller to ensure the keys are ordered in some way.
virtual NVRenderShaderProgram *
diff --git a/src/viewer/Qt3DSViewerApp.cpp b/src/viewer/Qt3DSViewerApp.cpp
index ce8163f..ae671d0 100644
--- a/src/viewer/Qt3DSViewerApp.cpp
+++ b/src/viewer/Qt3DSViewerApp.cpp
@@ -427,10 +427,13 @@ bool Q3DSViewerApp::InitializeApp(int winWidth, int winHeight, const QSurfaceFor
qCritical() << m_Impl.m_error;
return false;
}
-
+ QString errors;
bool success = m_Impl.m_view->InitializeGraphics(format, delayedLoading,
initInRenderThread,
- shaderCache);
+ shaderCache, errors);
+ if (!errors.isEmpty())
+ Q_EMIT SigLoadShaderCacheErrors(errors);
+
if (!success) {
m_Impl.m_error = QObject::tr("Viewer launch failure! Failed to load: '%1'").arg(source);
m_Impl.m_error.append("\n");
diff --git a/src/viewer/Qt3DSViewerApp.h b/src/viewer/Qt3DSViewerApp.h
index db8ba57..a23b5f9 100644
--- a/src/viewer/Qt3DSViewerApp.h
+++ b/src/viewer/Qt3DSViewerApp.h
@@ -549,6 +549,7 @@ Q_SIGNALS:
void SigDataOutputValueUpdated(const QString &name, const QVariant &newValue);
void SigPresentationReady();
void SigPresentationLoaded();
+ void SigLoadShaderCacheErrors(const QString &errors);
};
} // end namespace