#pragma once #include "Ogre.h" #include "OgreTechniqueGroup.h" #include "GTPOgreRenderable.h" using namespace Ogre; /** @brief Structure to store path map cluster information for a subentity. */ struct PathMapClusters { /** @brief the number of clusters this subentity belongs to */ unsigned int count; /** @brief the indices of the cluster this subentity belongs to. */ unsigned int* clusters; /** @brief the name of the path map file this subentity uses */ String pathMapTextureFilename; /** @brief the resolution of the path map file. */ unsigned int pathMapResolution; }; /** @brief Structure of a path map entry point. */ struct PathMapEntryPoint { /** @brief the position of the entry point. */ Vector3 position; /** @brief the normal of the entry point. */ Vector3 normal; /** @brief the probability of the entry point. */ float prob; int clusterID; }; /** @brief Implementation of IlluminationManager in an OGRE environment. */ class __declspec( dllexport ) OgreIlluminationManager: public FrameListener { protected: /** @brief Protected constructor (OgreIlluminationManager is a singleton). */ OgreIlluminationManager(); /** @brief Protected destructor. */ virtual ~OgreIlluminationManager(); /** @brief Searches for visible renderables with valid TechniqueGroups in a renderqueue. @param rq pointer to the RenderQueue instance to search in */ void fillVisibleList( RenderQueue * rq); /** @brief creates a specific type of RenderTechnique for a Renderable's pass. It searches all registered RenderTechniqueFactories. */ void createTechnique(IllumTechniqueParams* params, Pass* pass, OgreRenderable* rend, OgreSharedRuns* sRuns); bool needMaterialCopyForTechnique(IllumTechniqueParams* params); /** @brief A helper function to find the renderable object attached to a particle system (ONLY BILLBOARDSETS ARE SUPPORTED). @param system pointer to the ParticleSystem instance to search in @return pointer the connected BillboardSet instance */ BillboardSet* findRenderableInParticleSystem(ParticleSystem* system); /** @brief Fires preAllUpdates for registered UpdateListeners. This is called in each frame before updating the RenderTechniques. */ void preAllUpdates(); /** @brief Fires postAllUpdates for registered UpdateListeners. This is called in each frame after updating the RenderTechniques. */ void postAllUpdates(); /** @brief registered RenderTechniqueFactories */ std::list techniqueFactories; /** @brief The maximum bounding sphere radius that groupped objects ( see SharedRuns class __declspec( dllexport ) ) can have @see canJoin @see joinRuns */ float maxRad; /** @brief Size of the focusing map. This map is used if the shadow maps should be focused. */ unsigned int focusingMapSize; /** @brief Size of the shadow maps. */ unsigned int shadowMapSizePoint; unsigned int shadowMapSizeSpot; unsigned int shadowMapSizeDirectional; /** @brief Size of area lights for soft shadows. */ float areaLightRadius; /** @brief Sets if light space perspective shadow mapping should be used. */ bool useLISPSMPoint; bool useLISPSMSpot; bool useLISPSMDirectional; /** @brief Sets if the shadow maps should be blurred. Used in variance shadow mapping. */ bool blurSMPoint; bool blurSMSpot; bool blurSMDirectional; /** @brief Sets if shadow maps should be focused. */ bool focusingSMPoint; bool focusingSMSpot; bool focusingSMDirectional; /** @brief The material name that should be used during rendering the shadow maps. There are several predefined materials that can be used to render shadow maps: - GTP/Basic/Depth : writes projected depth values of front facing polygons - GTP/Basic/DepthCCW : writes projected depth values of back facing polygons - GTP/Basic/Distance : writes distance values (from eyepoint) of front facing polygons - GTP/Basic/DistanceCCW : writes distance values (from eyepoint) of back facing polygons - GTP/Basic/Distance_Normalized : writes normalized distance values (distance values devided by projection farplane - which is set to the attenuation range in case of shadow maps) of front facing polygons - GTP/Basic/Distance_NormalizedCCW : writes normalized distance values of back facing polygons The default material is GTP/Basic/Distance_NormalizedCCW. Recommended materials for different light types: - spot and point lights : GTP/Basic/Distance_NormalizedCCW or GTP/Basic/Distance_Normalized - directional lights : GTP/Basic/Depth or GTP/Basic/DepthCCW */ String shadowMapMaterialNamePoint; String shadowMapMaterialNameSpot; String shadowMapMaterialNameDirectional; /** @brief Size of the phase texture. */ unsigned int phaseTextureSize; /** @brief Stores maximum bounding radius values for each rendering run type. */ std::map maxRads; /** @brief Stores PathMapClusters structures for each subentity. The String key is the name of the subentity. */ std::map pathMapClusters; /** @brief PathMapEntryPoint list. */ std::vector pathMapEntryPoints; /** @brief Stores cluster size for each path map cluster. */ std::vector pathMapClusterLengths; /** @brief The camera attached to the player. */ Camera* mainCamera; /** @brief The viewport of the player camera. */ Viewport* mainViewport; /** @brief VisibleFinderVisitor instance. Used for adding visible renderables with valid TechniqueGroups to the visibleObjects vector. */ class __declspec( dllexport ) VisibleFinderVisitor* visitor; /** @brief The one and only OgreIlluminationManager instance. */ static OgreIlluminationManager* instance; /** @brief Vector containing visible renderables with valid TechniqueGroups that must be refreshed. */ std::vector visibleObjects; /** @brief List containing SharedRuns roots. It is the IlluminationManager's task to find the SharedRuns which can be joined. Only the root SharedRuns needs to be checked. */ std::list sharedRunRoots; /** @brief Group of RenderingRuns that are used globaly. Some RenderingRuns have only one instance per application (for example scene depth map). These resources are shared between all RenderTechniques. */ OgreSharedRuns globalSharedRuns; /** @brief Stores groups of RenderingRuns that are attached to individual light sources. These resources need separate instances for each lightsource ( for example depth shadow maps). They are grouped by the name of the lightsource. */ std::map perLightRuns; /** @brief */ std::map globalTargets; /** @brief Stores registered UpdateListeners. */ std::vector updateListeners; bool joinRuns; public: void joinSharedRuns(bool join){joinRuns = join;} /** @brief Registers an UpdateListener instance. @see UpdateListener */ void addUpdateListener(UpdateListener* l){updateListeners.push_back(l);} /** @brief registers a RenderTechniqueFactory */ void addRenderTechniqueFactory(RenderTechniqueFactory* factory) { techniqueFactories.push_back(factory); } /** @brief retirieves the maximum bounding sphere radius with two SharedRuns can be joined. Only valid fi all run types use the same radius. This can be set with calling setMaxJoinRadius(). @see setMaxJoinRadius */ float getMaxJoinRadius(){return maxRad;} /** @brief Retirieves the maximum shared bounding sphere radius for a given run type. */ float getMaxJoinRadius(RenderingRunType type){return maxRads[type];} /** @brief sets the maximum bounding sphere radius with two SharedRuns can be joined for all run type. */ void setMaxJoinRadius(float rad) { std::map ::iterator it = maxRads.begin(); std::map ::iterator itend = maxRads.end(); maxRad = rad; while(it != itend) { (*it).second = maxRad; it++; } } /** @brief Sets the maximum shared bounding sphere radius for a given run type. */ void setMaxJoinRadius(RenderingRunType type, float rad){maxRads[type] = rad;} /** @see focusingMapSize */ void setFocusingMapSize(unsigned int size){focusingMapSize = size;} /** @see phaseTextureSize */ void setPhaseTextureSize(unsigned int size){phaseTextureSize = size;} /** @see shadowMapSize */ void setShadowMapSize(unsigned int size) { shadowMapSizeDirectional = size; shadowMapSizePoint = size; shadowMapSizeSpot = size; } void setShadowMapSize(Light::LightTypes type, unsigned int size) { switch(type) { case Light::LT_DIRECTIONAL: shadowMapSizeDirectional = size;break; case Light::LT_POINT: shadowMapSizePoint = size;break; case Light::LT_SPOTLIGHT: shadowMapSizeSpot = size;break; } } /** @brief Returns the one and only OgreIlluminationManager instance. */ static OgreIlluminationManager& getSingleton(); /** @brief The function to be called to render one frame. This is the main refreshing function. It seasrches for visible objects, manages shared runs, updates render techniques and finally renders the scene to framebuffer. @param frameNumber current framenumber @param rt the rendertarget window. Needed to find the viewports that need to be refresh. */ void update(unsigned long frameNumber, RenderTarget* rt); /** @brief searches for RenderTechniques in materials and creates them for all objects. */ void initTechniques(); /** @brief searches for RenderTechniques in materials and creates them for an Entity. */ void initTechniques(Entity* e); /** @brief searches for RenderTechniques in materials and creates them for a Billboardset. */ void initTechniques(BillboardSet* bbs, ParticleSystem* sys); /** @brief Returns a pointer to the player camera. @return pointer to the main player camera. Needed by RenderTechnique and RenderingRun class __declspec( dllexport )es. */ Camera* getMainCamera(){return mainCamera;} /** @brief Returns a pointer to the viewport attached to the player camera. @return pointer to the viewport. Needed by RenderTechnique and RenderingRun class __declspec( dllexport )es. */ Viewport* getMainViewport(){return mainViewport;} /** @brief Sets the player camera. @param camera pointer to the main player camera */ void setMainCamera(Camera* camera){mainCamera = camera;} /** @brief Sets the viewport attached to the player camera. @param viewport pointer to the viewport */ void setMainViewport(Viewport* viewport){mainViewport = viewport;} /** @brief The function to be called when a shared run is splitted. @param old pointer to the SharedRuns instance that is split @param new1 pointer to one of the SharedRuns instance that remain after split @param new2 pointer to the other SharedRuns instance that remain after split */ void sharedRunSplit(SharedRuns* old, SharedRuns* new1, SharedRuns* new2); /** @brief The function to be called when two shared runs are joined. @param old1 pointer to one of the SharedRuns instance that are joined @param old2 pointer to the other SharedRuns instance that are joined @param newsr pointer to the resulting parent SharedRuns instance */ void sharedRunJoin(SharedRuns* old1, SharedRuns* old2, SharedRuns* newsr); /** @brief Joins shared runs if needed. Searches the registered shared run roots and join them if necessary (they are close enough). */ void joinSharedRuns(); /** @brief Register a shared run object. Only called when new techniques are created. @param runs pointer to the SharedRuns instance to add */ void addSharedRuns(SharedRuns* runs); /** @brief Searches for the nearest object groups (SharedRuns) that are caustic casters from a given point. @param position the point to obtain distances from @param nearestcasters vector to put the nearest caustic caster SharedRuns to @param maxCount the maximum number of nearest casters to search for */ void getNearestCausticCasters(Vector3 position, std::vector* nearestcasters, unsigned int maxCount); /** @brief Creates a global RenderingRun of the given type. If a RenderingRun with the given type already exist there is nothing to do. @param runType type enum of the RenderingRun to create */ void createGlobalRun(RenderingRunType runType); /** @brief Returns the global RendderingRun with the given type @param runType type enum of the RenderingRun to retrieve @return pointer to the RenderingRun, NULL if no RenderingRun with the given type exists */ RenderingRun* getGlobalRun(RenderingRunType runType); // These GlobalUseRenderTargets are only used in fire render technique. Maybe it could be solved with global rendering runs too. GlobalUseRenderTarget* getGlobalTarget(GlobalTargetType type); void addGlobalTarget(GlobalTargetType type, GlobalUseRenderTarget* target); /** @brief Updates a global RenderingRun with the given type. @param runType type enum of the RenderingRun to update @param frameNum current framenumber */ void updateGlobalRun(RenderingRunType runType, unsigned long frameNum); /** @brief Creates a RenderingRun attached to a lightsource with the given type. @param lightName name of the lightsource @param runType type enum of the RenderingRun to create */ void createPerLightRun(String lightName, RenderingRunType runType); /** @brief Retuns a RenderingRun attached to a lightsource with the given type. @param lightName name of the lightsource @param runType type enum of the RenderingRun to return @return pointer to the RenderingRun, NULL if no RenderingRun with the given type exists */ RenderingRun* getPerLightRun(String lightName, RenderingRunType runType); /** @brief Updates a RenderingRun attached to a lightsource with the given type. @param lightName name of the lightsource @param runType type enum of the RenderingRun to update @param frameNum current framenumber */ void updatePerLightRun(String lightName, RenderingRunType runType, unsigned long frameNum); /** @brief Saves the phase texture to the given file. */ void savePhaseTextureToFile(String filename); /** @brief Frame listener event handler function. Inherited from FrameListener. Called at the beginning of each frame. */ bool frameStarted(const FrameEvent& evt) { update(Root::getSingleton().getCurrentFrameNumber(), mainViewport->getTarget()); return FrameListener::frameStarted(evt); } /** @see useLISPSM */ bool getUseLISPSM(Light::LightTypes type) { switch(type) { case Light::LT_DIRECTIONAL: return useLISPSMDirectional; case Light::LT_POINT: return useLISPSMPoint; case Light::LT_SPOTLIGHT: return useLISPSMSpot; } } /** @see focusingSM */ bool getFocusingShadowMap(Light::LightTypes type) { switch(type) { case Light::LT_DIRECTIONAL: return focusingSMDirectional; case Light::LT_POINT: return focusingSMPoint; case Light::LT_SPOTLIGHT: return focusingSMSpot; } } /** @see blurSM */ bool getBlurShadowMap(Light::LightTypes type) { switch(type) { case Light::LT_DIRECTIONAL: return blurSMDirectional; case Light::LT_POINT: return blurSMPoint; case Light::LT_SPOTLIGHT: return blurSMSpot; } } /** @see useLISPSM */ void setUseLISPSM(bool use) { useLISPSMDirectional = use; useLISPSMPoint = use; useLISPSMSpot = use; } void setUseLISPSM(Light::LightTypes type, bool use) { switch(type) { case Light::LT_DIRECTIONAL: useLISPSMDirectional = use;break; case Light::LT_POINT: useLISPSMPoint = use;break; case Light::LT_SPOTLIGHT: useLISPSMSpot = use;break; } } /** @see focusingSM */ void setFocusingSM(bool use) { focusingSMDirectional = use; focusingSMPoint = use; focusingSMSpot = use; } void setFocusingSM(Light::LightTypes type, bool use) { switch(type) { case Light::LT_DIRECTIONAL: focusingSMDirectional = use;break; case Light::LT_POINT: focusingSMPoint = use;break; case Light::LT_SPOTLIGHT: focusingSMSpot = use;break; } } /** @see blurSM */ void setBlurShadowMap(bool use) { blurSMDirectional = use; blurSMPoint = use; blurSMSpot = use; } void setBlurShadowMap(Light::LightTypes type, bool use) { switch(type) { case Light::LT_DIRECTIONAL: blurSMDirectional = use;break; case Light::LT_POINT: blurSMPoint = use;break; case Light::LT_SPOTLIGHT: blurSMSpot = use;break; } } /** @see shadowMapMaterialName */ void setShadowMapMaterialName(String name) { shadowMapMaterialNameDirectional = name; shadowMapMaterialNamePoint = name; shadowMapMaterialNameSpot = name; } void setShadowMapMaterialName(Light::LightTypes type, String name) { switch(type) { case Light::LT_DIRECTIONAL: shadowMapMaterialNameDirectional = name;break; case Light::LT_POINT: shadowMapMaterialNamePoint = name;break; case Light::LT_SPOTLIGHT: shadowMapMaterialNameSpot = name;break; } } /** @brief Registers a PathMapClusters structure for a given subentity. @param subEntityName name of te subentity @param clusters the PathMapClusters that belongs to the given subentity */ void addPathMapClusters(String subEntityName, PathMapClusters clusters) { this->pathMapClusters[subEntityName] = clusters; } /** @brief Returns the PathMapClusters structure registered for a given subentity. @param subEntityName name of te subentity @return pointer to the PathMapClusters structure that belongs to the given subentity */ PathMapClusters* getPathMapClusters(String subEntityName) { return &pathMapClusters[subEntityName]; } /** @brief Adds a new PathMapEntryPoint cluster to the entrypoint list. */ void addPathMapEntryPoint(PathMapEntryPoint p) { this->pathMapEntryPoints.push_back(p); } /** @brief Returns the list of entrypoints. */ std::vector& getPathMapEntryPoints() { return pathMapEntryPoints; } /** @brief Adds a new cluster size. */ void addPathMapClusterLength(unsigned int l) { this->pathMapClusterLengths.push_back(l); } /** @brief Gets the number of clusters. */ unsigned int getPathMapClusterLengthsSize() { return this->pathMapClusterLengths.size(); } /** @brief Gets the size of the given cluster. @param index of the cluster @return the size of the cluster */ unsigned int getPathMapClusterLength(unsigned int index) { return pathMapClusterLengths.at(index); } /** @see areaLightRadius */ float getAreaLightRadius(){return areaLightRadius;} /** @see areaLightRadius */ void setAreaLigtRadius(float radius){areaLightRadius = radius;} /** @brief Sets the fire rendertarget - frame buffer resolution ratio */ inline void setFireRenderTargetSize(int size); void freeAllResources(); };