diff options
author | Lizzy Fleckenstein <eliasfleckenstein@web.de> | 2023-04-13 18:07:12 +0200 |
---|---|---|
committer | Lizzy Fleckenstein <eliasfleckenstein@web.de> | 2023-04-13 18:07:12 +0200 |
commit | 437b6619f6d3838b38aae0b6468ce7b4f7b2d891 (patch) | |
tree | ef55c521e2ef9b688256b9f6dbc8ba433d0e8491 /source | |
parent | bf90df100e120e272c14c7975a22ed01bf3ad215 (diff) | |
download | irrlicht-light.tar.xz |
Diffstat (limited to 'source')
-rw-r--r-- | source/Irrlicht/CSceneManager.cpp | 187 | ||||
-rw-r--r-- | source/Irrlicht/CSceneManager.h | 8 |
2 files changed, 171 insertions, 24 deletions
diff --git a/source/Irrlicht/CSceneManager.cpp b/source/Irrlicht/CSceneManager.cpp index 6882a5b..de80609 100644 --- a/source/Irrlicht/CSceneManager.cpp +++ b/source/Irrlicht/CSceneManager.cpp @@ -46,7 +46,7 @@ CSceneManager::CSceneManager(video::IVideoDriver* driver, : ISceneNode(0, 0), Driver(driver),
CursorControl(cursorControl),
ActiveCamera(0), ShadowColor(150,0,0,0), AmbientLight(0,0,0,0), Parameters(0),
- MeshCache(cache), CurrentRenderPass(ESNRP_NONE)
+ MeshCache(cache), CurrentRenderPass(ESNRP_NONE), LightManager(0)
{
#ifdef _DEBUG
ISceneManager::setDebugName("CSceneManager ISceneManager");
@@ -117,6 +117,9 @@ CSceneManager::~CSceneManager() if (Parameters)
Parameters->drop();
+ if (LightManager)
+ LightManager->drop();
+
// remove all nodes before dropping the driver
// as render targets may be destroyed twice
@@ -585,15 +588,24 @@ void CSceneManager::drawAll() // let all nodes register themselves
OnRegisterSceneNode();
+ if (LightManager)
+ LightManager->OnPreRender(LightList);
+
//render camera scenes
{
CurrentRenderPass = ESNRP_CAMERA;
Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
+ if (LightManager)
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+
for (i=0; i<CameraList.size(); ++i)
CameraList[i]->render();
CameraList.set_used(0);
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
//render lights scenes
@@ -601,20 +613,28 @@ void CSceneManager::drawAll() CurrentRenderPass = ESNRP_LIGHT;
Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
- core::vector3df camWorldPos(0, 0, 0);
- if (ActiveCamera)
- camWorldPos = ActiveCamera->getAbsolutePosition();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+ }
+ else
+ {
+ // Sort the lights by distance from the camera
+ core::vector3df camWorldPos(0, 0, 0);
+ if (ActiveCamera)
+ camWorldPos = ActiveCamera->getAbsolutePosition();
- core::array<DistanceNodeEntry> SortedLights;
- SortedLights.set_used(LightList.size());
- for (s32 light = (s32)LightList.size() - 1; light >= 0; --light)
- SortedLights[light].setNodeAndDistanceFromPosition(LightList[light], camWorldPos);
+ core::array<DistanceNodeEntry> SortedLights;
+ SortedLights.set_used(LightList.size());
+ for (s32 light = (s32)LightList.size() - 1; light >= 0; --light)
+ SortedLights[light].setNodeAndDistanceFromPosition(LightList[light], camWorldPos);
- SortedLights.set_sorted(false);
- SortedLights.sort();
+ SortedLights.set_sorted(false);
+ SortedLights.sort();
- for(s32 light = (s32)LightList.size() - 1; light >= 0; --light)
- LightList[light] = SortedLights[light].Node;
+ for(s32 light = (s32)LightList.size() - 1; light >= 0; --light)
+ LightList[light] = SortedLights[light].Node;
+ }
Driver->deleteAllDynamicLights();
@@ -622,8 +642,14 @@ void CSceneManager::drawAll() u32 maxLights = LightList.size();
+ if (!LightManager)
+ maxLights = core::min_ ( Driver->getMaximalDynamicLightAmount(), maxLights);
+
for (i=0; i< maxLights; ++i)
LightList[i]->render();
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
// render skyboxes
@@ -631,10 +657,27 @@ void CSceneManager::drawAll() CurrentRenderPass = ESNRP_SKY_BOX;
Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
- for (i=0; i<SkyBoxList.size(); ++i)
- SkyBoxList[i]->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+ for (i=0; i<SkyBoxList.size(); ++i)
+ {
+ ISceneNode* node = SkyBoxList[i];
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<SkyBoxList.size(); ++i)
+ SkyBoxList[i]->render();
+ }
SkyBoxList.set_used(0);
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
// render default objects
@@ -644,10 +687,27 @@ void CSceneManager::drawAll() SolidNodeList.sort(); // sort by textures
- for (i=0; i<SolidNodeList.size(); ++i)
- SolidNodeList[i].Node->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+ for (i=0; i<SolidNodeList.size(); ++i)
+ {
+ ISceneNode* node = SolidNodeList[i].Node;
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<SolidNodeList.size(); ++i)
+ SolidNodeList[i].Node->render();
+ }
SolidNodeList.set_used(0);
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
// render shadows
@@ -655,14 +715,31 @@ void CSceneManager::drawAll() CurrentRenderPass = ESNRP_SHADOW;
Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
- for (i=0; i<ShadowNodeList.size(); ++i)
- ShadowNodeList[i]->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+ for (i=0; i<ShadowNodeList.size(); ++i)
+ {
+ ISceneNode* node = ShadowNodeList[i];
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<ShadowNodeList.size(); ++i)
+ ShadowNodeList[i]->render();
+ }
if (!ShadowNodeList.empty())
Driver->drawStencilShadow(true,ShadowColor, ShadowColor,
ShadowColor, ShadowColor);
ShadowNodeList.set_used(0);
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
// render transparent objects.
@@ -671,10 +748,28 @@ void CSceneManager::drawAll() Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
TransparentNodeList.sort(); // sort by distance from camera
- for (i=0; i<TransparentNodeList.size(); ++i)
- TransparentNodeList[i].Node->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+
+ for (i=0; i<TransparentNodeList.size(); ++i)
+ {
+ ISceneNode* node = TransparentNodeList[i].Node;
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<TransparentNodeList.size(); ++i)
+ TransparentNodeList[i].Node->render();
+ }
TransparentNodeList.set_used(0);
+
+ if (LightManager)
+ LightManager->OnRenderPassPostRender(CurrentRenderPass);
}
// render transparent effect objects.
@@ -684,8 +779,23 @@ void CSceneManager::drawAll() TransparentEffectNodeList.sort(); // sort by distance from camera
- for (i=0; i<TransparentEffectNodeList.size(); ++i)
- TransparentEffectNodeList[i].Node->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+
+ for (i=0; i<TransparentEffectNodeList.size(); ++i)
+ {
+ ISceneNode* node = TransparentEffectNodeList[i].Node;
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<TransparentEffectNodeList.size(); ++i)
+ TransparentEffectNodeList[i].Node->render();
+ }
TransparentEffectNodeList.set_used(0);
}
@@ -695,18 +805,47 @@ void CSceneManager::drawAll() CurrentRenderPass = ESNRP_GUI;
Driver->getOverrideMaterial().Enabled = ((Driver->getOverrideMaterial().EnablePasses & CurrentRenderPass) != 0);
- for (i=0; i<GuiNodeList.size(); ++i)
- GuiNodeList[i]->render();
+ if (LightManager)
+ {
+ LightManager->OnRenderPassPreRender(CurrentRenderPass);
+
+ for (i=0; i<GuiNodeList.size(); ++i)
+ {
+ ISceneNode* node = GuiNodeList[i];
+ LightManager->OnNodePreRender(node);
+ node->render();
+ LightManager->OnNodePostRender(node);
+ }
+ }
+ else
+ {
+ for (i=0; i<GuiNodeList.size(); ++i)
+ GuiNodeList[i]->render();
+ }
GuiNodeList.set_used(0);
}
+
+ if (LightManager)
+ LightManager->OnPostRender();
+
LightList.set_used(0);
clearDeletionList();
CurrentRenderPass = ESNRP_NONE;
}
+void CSceneManager::setLightManager(ILightManager* lightManager)
+{
+ if (lightManager)
+ lightManager->grab();
+ if (LightManager)
+ LightManager->drop();
+
+ LightManager = lightManager;
+}
+
//! Sets the color of stencil buffers shadows drawn by the scene manager.
void CSceneManager::setShadowColor(video::SColor color)
diff --git a/source/Irrlicht/CSceneManager.h b/source/Irrlicht/CSceneManager.h index fded7f8..d2fa156 100644 --- a/source/Irrlicht/CSceneManager.h +++ b/source/Irrlicht/CSceneManager.h @@ -12,6 +12,7 @@ #include "irrArray.h"
#include "IMeshLoader.h"
#include "CAttributes.h"
+#include "ILightManager.h"
namespace irr
{
@@ -198,6 +199,9 @@ namespace scene //! Returns ambient color of the scene
const video::SColorf& getAmbientLight() const override;
+ //! Register a custom callbacks manager which gets callbacks during scene rendering.
+ virtual void setLightManager(ILightManager* lightManager) override;
+
//! Get current render time.
E_SCENE_NODE_RENDER_PASS getCurrentRenderPass() const override { return CurrentRenderPass; }
@@ -325,6 +329,10 @@ namespace scene IMeshCache* MeshCache;
E_SCENE_NODE_RENDER_PASS CurrentRenderPass;
+
+ //! An optional callbacks manager to allow the user app finer control
+ //! over the scene lighting and rendering.
+ ILightManager* LightManager;
};
} // end namespace video
|