Skip to content

Commit

Permalink
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Replace renderOneFrame for per-workspace update calls
Browse files Browse the repository at this point in the history
Add Scene::PostRenderGpuFlush

Breaks ABI.
Needs changes to other components as well, so they call
Scene::PostRenderGpuFlush

Affects gazebosim#323

Signed-off-by: Matias N. Goldberg <[email protected]>
darksylinc committed Jun 19, 2021

Verified

This commit was signed with the committer’s verified signature.
darksylinc Matias N. Goldberg
1 parent 76aa471 commit 7554987
Showing 12 changed files with 130 additions and 43 deletions.
29 changes: 29 additions & 0 deletions include/ignition/rendering/Scene.hh
Original file line number Diff line number Diff line change
@@ -1019,6 +1019,35 @@ namespace ignition
/// changes by traversing scene-graph, calling PreRender on all objects
public: virtual void PreRender() = 0;

/// \brief Flushes all buffered frame data and starts 'a new frame'.
/// CPUs queue up a bunch of rendering commands and then waits
/// for the GPU to finish up.
/// If we flush too often, the CPU will often have to wait for the GPU
/// doing nothing.
/// If we flush too infrequently, RAM consumption will rise due to
/// queueing up unsubmitted work.
/// Note that work may be submitted earlier if required by a specific
/// operation (e.g. reading GPU -> CPU), however RAM may still
/// rise if FlushFrame() isn't called
/// This function must be called at least once per frame
/// This function may be called for any camera, but affects all cameras
///
/// \remarks
/// This function should be called after updating all cameras / once per
/// frame, but it may be called more often if you're updating too many
/// cameras and running out of memory
///
/// Example:
///
/// Cubemap rendering w/ 3 probes and 5 shadowmaps can cause
/// a blow up of passes:
///
/// (5 shadow maps per face + 1 regular render) x 6 faces x 3 probes =
/// 108 render_scene passes.
/// 108 is way too much, causing out of memory situations;
/// so flushing once per probe may make better sense.
public: virtual void PostRenderGpuFlush() = 0;

/// \brief Remove and destroy all objects from the scene graph. This does
/// not completely destroy scene resources, so new objects can be created
/// and added to the scene afterwards.
1 change: 1 addition & 0 deletions include/ignition/rendering/base/BaseCamera.hh
Original file line number Diff line number Diff line change
@@ -388,6 +388,7 @@ namespace ignition
this->Scene()->PreRender();
this->Render();
this->PostRender();
this->Scene()->PostRenderGpuFlush();
}

//////////////////////////////////////////////////
3 changes: 3 additions & 0 deletions include/ignition/rendering/base/BaseScene.hh
Original file line number Diff line number Diff line change
@@ -481,6 +481,9 @@ namespace ignition

public: virtual void Destroy() override;

// Documentation inherited.
public: virtual void PostRenderGpuFlush() override;

protected: virtual unsigned int CreateObjectId();

protected: virtual std::string CreateObjectName(unsigned int _id,
3 changes: 3 additions & 0 deletions ogre2/include/ignition/rendering/ogre2/Ogre2Scene.hh
Original file line number Diff line number Diff line change
@@ -94,6 +94,9 @@ namespace ignition
// Documentation inherited
public: virtual bool SkyEnabled() const override;

// Documentation inherited
public: virtual void PostRenderGpuFlush() override;

/// \brief Get a pointer to the ogre scene manager
/// \return Pointer to the ogre scene manager
public: virtual Ogre::SceneManager *OgreSceneManager() const;
13 changes: 9 additions & 4 deletions ogre2/src/Ogre2DepthCamera.cc
Original file line number Diff line number Diff line change
@@ -941,10 +941,15 @@ void Ogre2DepthCamera::CreateWorkspaceInstance()
void Ogre2DepthCamera::Render()
{
// update the compositors
this->dataPtr->ogreCompositorWorkspace->setEnabled(true);
auto engine = Ogre2RenderEngine::Instance();
engine->OgreRoot()->renderOneFrame();
this->dataPtr->ogreCompositorWorkspace->setEnabled(false);
this->dataPtr->ogreCompositorWorkspace->_validateFinalTarget();
//engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
this->dataPtr->ogreCompositorWorkspace->_beginUpdate(false);
this->dataPtr->ogreCompositorWorkspace->_update();
this->dataPtr->ogreCompositorWorkspace->_endUpdate(false);

Ogre::vector<Ogre::RenderTarget*>::type swappedTargets;
swappedTargets.reserve( 2u );
this->dataPtr->ogreCompositorWorkspace->_swapFinalTarget( swappedTargets );
}

//////////////////////////////////////////////////
13 changes: 9 additions & 4 deletions ogre2/src/Ogre2GpuRays.cc
Original file line number Diff line number Diff line change
@@ -1091,10 +1091,15 @@ void Ogre2GpuRays::UpdateRenderTarget1stPass()
/////////////////////////////////////////////////
void Ogre2GpuRays::UpdateRenderTarget2ndPass()
{
this->dataPtr->ogreCompositorWorkspace2nd->setEnabled(true);
auto engine = Ogre2RenderEngine::Instance();
engine->OgreRoot()->renderOneFrame();
this->dataPtr->ogreCompositorWorkspace2nd->setEnabled(false);
this->dataPtr->ogreCompositorWorkspace2nd->_validateFinalTarget();
//engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
this->dataPtr->ogreCompositorWorkspace2nd->_beginUpdate(false);
this->dataPtr->ogreCompositorWorkspace2nd->_update();
this->dataPtr->ogreCompositorWorkspace2nd->_endUpdate(false);

Ogre::vector<Ogre::RenderTarget*>::type swappedTargets;
swappedTargets.reserve( 2u );
this->dataPtr->ogreCompositorWorkspace2nd->_swapFinalTarget( swappedTargets );
}

//////////////////////////////////////////////////
36 changes: 9 additions & 27 deletions ogre2/src/Ogre2RenderTarget.cc
Original file line number Diff line number Diff line change
@@ -425,33 +425,15 @@ void Ogre2RenderTarget::PostRender()
//////////////////////////////////////////////////
void Ogre2RenderTarget::Render()
{
// TODO(anyone)
// There is current not an easy solution to manually updating
// render textures:
// https://forums.ogre3d.org/viewtopic.php?t=84687
this->ogreCompositorWorkspace->setEnabled(true);
auto engine = Ogre2RenderEngine::Instance();
engine->OgreRoot()->renderOneFrame();
this->ogreCompositorWorkspace->setEnabled(false);

// The code below for manual updating render textures was suggested in ogre
// forum but it does not seem to work
// this->scene->OgreSceneManager()->updateSceneGraph();
// this->ogreCompositorWorkspace->_validateFinalTarget();
// engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
// this->ogreCompositorWorkspace->_beginUpdate(false);
// this->ogreCompositorWorkspace->_update();
// this->ogreCompositorWorkspace->_endUpdate(false);

// this->scene->OgreSceneManager()->_frameEnded();
// for (size_t i=0; i < Ogre::HLMS_MAX; ++i)
// {
// Ogre::Hlms *hlms = engine->OgreRoot()->getHlmsManager()->getHlms(
// static_cast<Ogre::HlmsTypes>(i));
// if(hlms)
// hlms->frameEnded();
// }
// engine->OgreRoot()->getRenderSystem()->_update();
this->ogreCompositorWorkspace->_validateFinalTarget();
//engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
this->ogreCompositorWorkspace->_beginUpdate(false);
this->ogreCompositorWorkspace->_update();
this->ogreCompositorWorkspace->_endUpdate(false);

Ogre::vector<Ogre::RenderTarget*>::type swappedTargets;
swappedTargets.reserve( 2u );
this->ogreCompositorWorkspace->_swapFinalTarget( swappedTargets );
}

//////////////////////////////////////////////////
35 changes: 35 additions & 0 deletions ogre2/src/Ogre2Scene.cc
Original file line number Diff line number Diff line change
@@ -57,6 +57,10 @@
#include <OgreSceneManager.h>
#include <Overlay/OgreOverlayManager.h>
#include <Overlay/OgreOverlaySystem.h>
#if OGRE_VERSION_MAJOR == 2 && OGRE_VERSION_MINOR == 1
#include <OgreHlms.h>
#include <OgreHlmsManager.h>
#endif
#ifdef _MSC_VER
#pragma warning(pop)
#endif
@@ -166,6 +170,37 @@ void Ogre2Scene::PreRender()
}

BaseScene::PreRender();

this->ogreSceneManager->updateSceneGraph();
}

//////////////////////////////////////////////////
void Ogre2Scene::PostRenderGpuFlush()
{
auto engine = Ogre2RenderEngine::Instance();
auto ogreRoot = engine->OgreRoot();
Ogre::CompositorManager2 *ogreCompMgr = ogreRoot->getCompositorManager2();

//engine->OgreRoot()->renderOneFrame();

#if OGRE_VERSION_MAJOR == 2 && OGRE_VERSION_MINOR == 1
auto hlmsManager = ogreRoot->getHlmsManager();
// Updating the compositor with all workspaces disables achieves our goal
ogreCompMgr->_update( Ogre::SceneManagerEnumerator::getSingleton(),
hlmsManager );
#else
// Updating the compositor with all workspaces disables achieves our goal
ogreCompMgr->_update();
#endif

ogreCompMgr->_swapAllFinalTargets();

auto itor = ogreRoot->getSceneManagerIterator();
while( itor.hasMoreElements() )
{
Ogre::SceneManager *sceneManager = itor.getNext();
sceneManager->clearFrameData();
}
}

//////////////////////////////////////////////////
14 changes: 10 additions & 4 deletions ogre2/src/Ogre2SelectionBuffer.cc
Original file line number Diff line number Diff line change
@@ -128,10 +128,16 @@ void Ogre2SelectionBuffer::Update()
this->dataPtr->materialSwitcher->Reset();

// manual update
this->dataPtr->ogreCompositorWorkspace->setEnabled(true);
auto engine = Ogre2RenderEngine::Instance();
engine->OgreRoot()->renderOneFrame();
this->dataPtr->ogreCompositorWorkspace->setEnabled(false);
this->dataPtr->scene->OgreSceneManager()->updateSceneGraph();
this->dataPtr->ogreCompositorWorkspace->_validateFinalTarget();
//engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
this->dataPtr->ogreCompositorWorkspace->_beginUpdate(false);
this->dataPtr->ogreCompositorWorkspace->_update();
this->dataPtr->ogreCompositorWorkspace->_endUpdate(false);

Ogre::vector<Ogre::RenderTarget*>::type swappedTargets;
swappedTargets.reserve( 2u );
this->dataPtr->ogreCompositorWorkspace->_swapFinalTarget( swappedTargets );

this->dataPtr->renderTexture->copyContentsToMemory(*this->dataPtr->pixelBox,
Ogre::RenderTarget::FB_FRONT);
7 changes: 7 additions & 0 deletions ogre2/src/Ogre2Sensor.cc
Original file line number Diff line number Diff line change
@@ -16,6 +16,13 @@
*/
#include "ignition/rendering/ogre2/Ogre2Sensor.hh"

#include <ignition/rendering/ogre2/Ogre2RenderEngine.hh>

#include <Compositor/OgreCompositorManager2.h>
#include <OgreHlms.h>
#include <OgreHlmsManager.h>
#include <OgreRoot.h>

using namespace ignition;
using namespace rendering;

14 changes: 10 additions & 4 deletions ogre2/src/Ogre2ThermalCamera.cc
Original file line number Diff line number Diff line change
@@ -827,10 +827,16 @@ void Ogre2ThermalCamera::CreateThermalTexture()
void Ogre2ThermalCamera::Render()
{
// update the compositors
this->dataPtr->ogreCompositorWorkspace->setEnabled(true);
auto engine = Ogre2RenderEngine::Instance();
engine->OgreRoot()->renderOneFrame();
this->dataPtr->ogreCompositorWorkspace->setEnabled(false);
this->scene->OgreSceneManager()->updateSceneGraph();
this->dataPtr->ogreCompositorWorkspace->_validateFinalTarget();
//engine->OgreRoot()->getRenderSystem()->_beginFrameOnce();
this->dataPtr->ogreCompositorWorkspace->_beginUpdate(false);
this->dataPtr->ogreCompositorWorkspace->_update();
this->dataPtr->ogreCompositorWorkspace->_endUpdate(false);

Ogre::vector<Ogre::RenderTarget*>::type swappedTargets;
swappedTargets.reserve( 2u );
this->dataPtr->ogreCompositorWorkspace->_swapFinalTarget( swappedTargets );
}

//////////////////////////////////////////////////
5 changes: 5 additions & 0 deletions src/base/BaseScene.cc
Original file line number Diff line number Diff line change
@@ -1235,6 +1235,11 @@ void BaseScene::PreRender()
this->RootVisual()->PreRender();
}

//////////////////////////////////////////////////
void BaseScene::PostRenderGpuFlush()
{
}

//////////////////////////////////////////////////
void BaseScene::Clear()
{

0 comments on commit 7554987

Please sign in to comment.