From 4a50c4cbc0399b4ac5fb79e2032ad6fb9e9e5318 Mon Sep 17 00:00:00 2001 From: Emma Broman Date: Wed, 8 Mar 2023 10:59:32 +0100 Subject: [PATCH] Double renderbins for renderables (#2520) --- include/openspace/rendering/renderable.h | 11 ++++-- modules/globebrowsing/src/renderableglobe.cpp | 18 ++++++++-- modules/globebrowsing/src/renderableglobe.h | 1 + src/rendering/renderable.cpp | 13 +++++-- src/scene/scenegraphnode.cpp | 34 ++++++++++++------- 5 files changed, 58 insertions(+), 19 deletions(-) diff --git a/include/openspace/rendering/renderable.h b/include/openspace/rendering/renderable.h index 3d49bc20e1..ba411b493c 100644 --- a/include/openspace/rendering/renderable.h +++ b/include/openspace/rendering/renderable.h @@ -82,8 +82,9 @@ public: std::string_view typeAsString() const; - virtual void render(const RenderData& data, RendererTasks& rendererTask); virtual void update(const UpdateData& data); + virtual void render(const RenderData& data, RendererTasks& rendererTask); + virtual void renderSecondary(const RenderData& data, RendererTasks& rendererTask); // The 'surface' in this case is the interaction sphere of this renderable. In some // cases (i.e., planets) this corresponds directly to the physical surface, but in @@ -97,7 +98,9 @@ public: RenderBin renderBin() const; void setRenderBin(RenderBin bin); - bool matchesRenderBinMask(int binMask); + bool matchesRenderBinMask(int binMask) const noexcept; + + bool matchesSecondaryRenderBin(int binMask) const noexcept; void setFade(float fade); @@ -129,6 +132,10 @@ protected: bool _shouldUpdateIfDisabled = false; RenderBin _renderBin = RenderBin::Opaque; + // An optional renderbin that renderables can use for certain components, in cases + // where all parts of the renderable should not be rendered in the same bin + std::optional _secondaryRenderBin; + private: // We only want the SceneGraphNode to be able manipulate the parent, so we don't want // to provide a set method for this. Otherwise, anyone might mess around with our diff --git a/modules/globebrowsing/src/renderableglobe.cpp b/modules/globebrowsing/src/renderableglobe.cpp index dd0119a9eb..439a939b0e 100644 --- a/modules/globebrowsing/src/renderableglobe.cpp +++ b/modules/globebrowsing/src/renderableglobe.cpp @@ -64,6 +64,8 @@ namespace std { #endif namespace { + constexpr std::string_view _loggerCat = "RenderableGlobe"; + // Global flags to modify the RenderableGlobe constexpr bool LimitLevelByAvailableData = true; constexpr bool PerformFrustumCulling = true; @@ -664,6 +666,10 @@ RenderableGlobe::RenderableGlobe(const ghoul::Dictionary& dictionary) _generalProperties.shadowMapping = true; } _generalProperties.shadowMapping.onChange(notifyShaderRecompilation); + + // Use a secondary renderbin for labels, and other things that we want to be able to + // render with transparency, on top of the globe, after the atmosphere step + _secondaryRenderBin = RenderBin::PostDeferredTransparent; } void RenderableGlobe::initializeGL() { @@ -735,9 +741,6 @@ void RenderableGlobe::render(const RenderData& data, RendererTasks& rendererTask if ((distanceToCamera < distance) || (_generalProperties.renderAtDistance)) { try { - // Before Shadows - _globeLabelsComponent.draw(data); - if (_hasShadows && _shadowComponent.isEnabled()) { // Set matrices and other GL states RenderData lightRenderData(_shadowComponent.begin(data)); @@ -806,6 +809,15 @@ void RenderableGlobe::render(const RenderData& data, RendererTasks& rendererTask _lastChangedLayer = nullptr; } +void RenderableGlobe::renderSecondary(const RenderData& data, RendererTasks&) { + try { + _globeLabelsComponent.draw(data); + } + catch (const ghoul::opengl::TextureUnit::TextureUnitError& e) { + LERROR(fmt::format("Error on drawing globe labels: '{}'", e.message)); + } +} + void RenderableGlobe::update(const UpdateData& data) { ZoneScoped; diff --git a/modules/globebrowsing/src/renderableglobe.h b/modules/globebrowsing/src/renderableglobe.h index 56778d70e8..32d31c814d 100644 --- a/modules/globebrowsing/src/renderableglobe.h +++ b/modules/globebrowsing/src/renderableglobe.h @@ -103,6 +103,7 @@ public: bool isReady() const override; void render(const RenderData& data, RendererTasks& rendererTask) override; + void renderSecondary(const RenderData& data, RendererTasks&) override; void update(const UpdateData& data) override; SurfacePositionHandle calculateSurfacePositionHandle( diff --git a/src/rendering/renderable.cpp b/src/rendering/renderable.cpp index ccfc3dbbce..83a17a07e6 100644 --- a/src/rendering/renderable.cpp +++ b/src/rendering/renderable.cpp @@ -224,6 +224,8 @@ void Renderable::update(const UpdateData&) {} void Renderable::render(const RenderData&, RendererTasks&) {} +void Renderable::renderSecondary(const RenderData&, RendererTasks&) {} + void Renderable::setBoundingSphere(double boundingSphere) { _boundingSphere = boundingSphere; } @@ -267,8 +269,15 @@ void Renderable::setRenderBin(RenderBin bin) { _renderBin = bin; } -bool Renderable::matchesRenderBinMask(int binMask) { - return binMask & static_cast(renderBin()); +bool Renderable::matchesRenderBinMask(int binMask) const noexcept { + return binMask & static_cast(_renderBin); +} + +bool Renderable::matchesSecondaryRenderBin(int binMask) const noexcept { + if (!_secondaryRenderBin.has_value()) { + return false; + } + return binMask & static_cast(*_secondaryRenderBin); } void Renderable::setFade(float fade) { diff --git a/src/scene/scenegraphnode.cpp b/src/scene/scenegraphnode.cpp index 2dfdd7c531..b1596f3e6a 100644 --- a/src/scene/scenegraphnode.cpp +++ b/src/scene/scenegraphnode.cpp @@ -737,7 +737,7 @@ void SceneGraphNode::render(const RenderData& data, RendererTasks& tasks) { } const bool visible = _renderable && _renderable->isVisible() && - _renderable->isReady() && _renderable->matchesRenderBinMask(data.renderBinMask); + _renderable->isReady(); if (!visible) { return; @@ -747,21 +747,31 @@ void SceneGraphNode::render(const RenderData& data, RendererTasks& tasks) { return; } + RenderData newData = { + .camera = data.camera, + .time = data.time, + .renderBinMask = data.renderBinMask, + .modelTransform = { + .translation = _worldPositionCached, + .rotation = _worldRotationCached, + .scale = _worldScaleCached + } + }; + + if (_renderable->matchesSecondaryRenderBin(data.renderBinMask)) { + TracyGpuZone("Render Secondary Bin") + _renderable->renderSecondary(newData, tasks); + } + + if (!_renderable->matchesRenderBinMask(data.renderBinMask)) { + return; + } + { TracyGpuZone("Render") - RenderData newData = { - .camera = data.camera, - .time = data.time, - .renderBinMask = data.renderBinMask, - .modelTransform = { - .translation = _worldPositionCached, - .rotation = _worldRotationCached, - .scale = _worldScaleCached - } - }; - _renderable->render(newData, tasks); + if (_computeScreenSpaceValues) { computeScreenSpaceData(newData); }