Просмотр исходного кода

Render state caching is now only performed on core objects in order to avoid the issue with deserializing a cached object
Added unique IDs to blend/rasterizer/depth-stencil states
Fixed render states so they aren't initializes multiple types if they have been cached

Marko Pintera 10 лет назад
Родитель
Сommit
1583b110f5

+ 17 - 1
BansheeCore/Include/BsBlendState.h

@@ -168,6 +168,11 @@ namespace BansheeEngine
 		 */
 		const BlendProperties& getProperties() const;
 
+		/**
+		 * @brief	Returns a unique state ID. Only the lowest 10 bits are used.
+		 */
+		UINT32 getId() const { return mId; }
+
 		/**
 		 * @brief	Returns the default blend state that you may use
 		 * 			when no other is available.
@@ -177,9 +182,20 @@ namespace BansheeEngine
 	protected:
 		friend class RenderStateCoreManager;
 
-		BlendStateCore(const BLEND_STATE_DESC& desc);
+		BlendStateCore(const BLEND_STATE_DESC& desc, UINT32 id);
+
+		/**
+		 * @copydoc	CoreObjectCore::initialize
+		 */
+		void initialize() override;
+
+		/**
+		 * @brief	Creates any API-specific state objects.
+		 */
+		virtual void createInternal() { }
 
 		BlendProperties mProperties;
+		UINT32 mId;
 	};
 
 	/**

+ 17 - 1
BansheeCore/Include/BsDepthStencilState.h

@@ -173,6 +173,11 @@ namespace BansheeEngine
 		 */
 		const DepthStencilProperties& getProperties() const;
 
+		/**
+		 * @brief	Returns a unique state ID. Only the lowest 10 bits are used.
+		 */
+		UINT32 getId() const { return mId; }
+
 		/**
 		 * @brief	Returns the default depth stencil state that you may use when no other is available.
 		 */
@@ -181,9 +186,20 @@ namespace BansheeEngine
 	protected:
 		friend class RenderStateCoreManager;
 
-		DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc);
+		DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id);
+
+		/**
+		 * @copydoc	CoreObjectCore::initialize
+		 */
+		void initialize() override;
+
+		/**
+		 * @brief	Creates any API-specific state objects.
+		 */
+		virtual void createInternal() { }
 
 		DepthStencilProperties mProperties;
+		UINT32 mId;
 	};
 
 	/**

+ 17 - 1
BansheeCore/Include/BsRasterizerState.h

@@ -148,6 +148,11 @@ namespace BansheeEngine
 		 */
 		const RasterizerProperties& getProperties() const;
 
+		/**
+		 * @brief	Returns a unique state ID. Only the lowest 10 bits are used.
+		 */
+		UINT32 getId() const { return mId; }
+
 		/**
 		 * @brief	Returns the default rasterizer state.
 		 */
@@ -156,9 +161,20 @@ namespace BansheeEngine
 	protected:
 		friend class RenderStateCoreManager;
 
-		RasterizerStateCore(const RASTERIZER_STATE_DESC& desc);
+		RasterizerStateCore(const RASTERIZER_STATE_DESC& desc, UINT32 id);
+
+		/**
+		 * @copydoc	CoreObjectCore::initialize
+		 */
+		void initialize() override;
+
+		/**
+		 * @brief	Creates any API-specific state objects.
+		 */
+		virtual void createInternal() { }
 
 		RasterizerProperties mProperties;
+		UINT32 mId;
 	};
 
 	/**

+ 157 - 119
BansheeCore/Include/BsRenderStateManager.h

@@ -9,118 +9,10 @@
 
 namespace BansheeEngine
 {
-	/**
-	 * @brief	Common methods and data for both sim and core thread versions
-	 *			of RenderStateManager.
-	 */
-	template<bool Core>
-	class BS_CORE_EXPORT TRenderStateManager
-	{
-	public:
-		virtual ~TRenderStateManager() { }
-
-	protected:
-		template<bool Core> struct TSamplerStateType { };
-		template<> struct TSamplerStateType < false > { typedef SamplerState Type; };
-		template<> struct TSamplerStateType < true > { typedef SamplerStateCore Type; };
-
-		template<bool Core> struct TBlendStateType { };
-		template<> struct TBlendStateType < false > { typedef BlendState Type; };
-		template<> struct TBlendStateType < true > { typedef BlendStateCore Type; };
-
-		template<bool Core> struct TRasterizerStateType { };
-		template<> struct TRasterizerStateType < false > { typedef RasterizerState Type; };
-		template<> struct TRasterizerStateType < true > { typedef RasterizerStateCore Type; };
-
-		template<bool Core> struct TDepthStencilStateType { };
-		template<> struct TDepthStencilStateType < false > { typedef DepthStencilState Type; };
-		template<> struct TDepthStencilStateType < true > { typedef DepthStencilStateCore Type; };
-
-		typedef typename TSamplerStateType<Core>::Type SamplerStateType;
-		typedef typename TBlendStateType<Core>::Type BlendStateType;
-		typedef typename TRasterizerStateType<Core>::Type RasterizerStateType;
-		typedef typename TDepthStencilStateType<Core>::Type DepthStencilStateType;
-
-		/**
-		 * @brief	Triggered when a new sampler state is created. 
-		 */
-		void notifySamplerStateCreated(const SAMPLER_STATE_DESC& desc, const SPtr<SamplerStateType>& state) const;
-
-		/**
-		 * @brief	Triggered when a new sampler state is created. 
-		 */
-		void notifyBlendStateCreated(const BLEND_STATE_DESC& desc, const SPtr<BlendStateType>& state) const;
-
-		/**
-		 * @brief	Triggered when a new sampler state is created. 
-		 */
-		void notifyRasterizerStateCreated(const RASTERIZER_STATE_DESC& desc, const SPtr<RasterizerStateType>& state) const;
-
-		/**
-		 * @brief	Triggered when a new sampler state is created. 
-		 */
-		void notifyDepthStencilStateCreated(const DEPTH_STENCIL_STATE_DESC& desc, const SPtr<DepthStencilStateType>& state) const;
-
-		/**
-		 * @brief	Triggered when the last reference to a specific sampler state is destroyed, which
-		 *			means we must clear our cached version as well.
-		 */
-		void notifySamplerStateDestroyed(const SAMPLER_STATE_DESC& desc) const;
-
-		/**
-		 * @brief	Triggered when the last reference to a specific blend state is destroyed, which
-		 *			means we must clear our cached version as well.
-		 */
-		void notifyBlendStateDestroyed(const BLEND_STATE_DESC& desc) const;
-
-		/**
-		 * @brief	Triggered when the last reference to a specific rasterizer state is destroyed, which
-		 *			means we must clear our cached version as well.
-		 */
-		void notifyRasterizerStateDestroyed(const RASTERIZER_STATE_DESC& desc) const;
-
-		/**
-		 * @brief	Triggered when the last reference to a specific depth stencil state is destroyed, which
-		 *			means we must clear our cached version as well.
-		 */
-		void notifyDepthStencilStateDestroyed(const DEPTH_STENCIL_STATE_DESC& desc) const;
-
-		/**
-		 * @brief	Attempts to find a cached sampler state corresponding to the provided descriptor. 
-		 *			Returns null if one doesn't exist.
-		 */
-		SPtr<SamplerStateType> findCachedState(const SAMPLER_STATE_DESC& desc) const;
-
-				/**
-		 * @brief	Attempts to find a cached blend state corresponding to the provided descriptor. 
-		 *			Returns null if one doesn't exist.
-		 */
-		SPtr<BlendStateType> findCachedState(const BLEND_STATE_DESC& desc) const;
-
-				/**
-		 * @brief	Attempts to find a cached rasterizer state corresponding to the provided descriptor. 
-		 *			Returns null if one doesn't exist.
-		 */
-		SPtr<RasterizerStateType> findCachedState(const RASTERIZER_STATE_DESC& desc) const;
-
-		/**
-		 * @brief	Attempts to find a cached depth-stencil state corresponding to the provided descriptor. 
-		 *			Returns null if one doesn't exist.
-		 */
-		SPtr<DepthStencilStateType> findCachedState(const DEPTH_STENCIL_STATE_DESC& desc) const;
-
-		mutable UnorderedMap<SAMPLER_STATE_DESC, std::weak_ptr<SamplerStateType>> mCachedSamplerStates;
-		mutable UnorderedMap<BLEND_STATE_DESC, std::weak_ptr<BlendStateType>> mCachedBlendStates;
-		mutable UnorderedMap<RASTERIZER_STATE_DESC, std::weak_ptr<RasterizerStateType>> mCachedRasterizerStates;
-		mutable UnorderedMap<DEPTH_STENCIL_STATE_DESC, std::weak_ptr<DepthStencilStateType>> mCachedDepthStencilStates;
-
-		BS_MUTEX(mMutex);
-	};
-
 	/**
 	 * @brief	Handles creation of various render states.
 	 */
-	class BS_CORE_EXPORT RenderStateManager : public Module <RenderStateManager>, TRenderStateManager<false>
+	class BS_CORE_EXPORT RenderStateManager : public Module <RenderStateManager>
 	{
 	public:
 		/**
@@ -210,9 +102,63 @@ namespace BansheeEngine
 	/**
 	 * @brief	Handles creation of various render states.
 	 */
-	class BS_CORE_EXPORT RenderStateCoreManager : public Module<RenderStateCoreManager>, TRenderStateManager<true>
+	class BS_CORE_EXPORT RenderStateCoreManager : public Module<RenderStateCoreManager>
 	{
+	private:
+		/**
+		 * @brief	Contains data about a cached blend state
+		 */
+		struct CachedBlendState
+		{
+			CachedBlendState()
+				:id(0)
+			{ }
+
+			CachedBlendState(UINT32 id)
+				:id(id)
+			{ }
+
+			std::weak_ptr<BlendStateCore> state;
+			UINT32 id;
+		};
+
+		/**
+		 * @brief	Contains data about a cached blend state
+		 */
+		struct CachedRasterizerState
+		{
+			CachedRasterizerState()
+				:id(0)
+			{ }
+
+			CachedRasterizerState(UINT32 id)
+				:id(id)
+			{ }
+
+			std::weak_ptr<RasterizerStateCore> state;
+			UINT32 id;
+		};
+
+		/**
+		 * @brief	Contains data about a cached blend state
+		 */
+		struct CachedDepthStencilState
+		{
+			CachedDepthStencilState()
+				:id(0)
+			{ }
+
+			CachedDepthStencilState(UINT32 id)
+				:id(id)
+			{ }
+
+			std::weak_ptr<DepthStencilStateCore> state;
+			UINT32 id;
+		};
+
 	public:
+		RenderStateCoreManager();
+
 		/**
 		 * @copydoc	RenderStateManager::createSamplerState
 		 */
@@ -233,6 +179,38 @@ namespace BansheeEngine
 		 */
 		SPtr<BlendStateCore> createBlendState(const BLEND_STATE_DESC& desc) const;
 
+		/**
+		 * @brief	Creates an uninitialized sampler state. Requires manual initialization
+		 *			after creation.
+		 *
+		 * @note	Internal method.
+		 */
+		SPtr<SamplerStateCore> _createSamplerState(const SAMPLER_STATE_DESC& desc) const;
+
+		/**
+		 * @brief	Creates an uninitialized depth-stencil state. Requires manual initialization
+		 *			after creation.
+		 *
+		 * @note	Internal method.
+		 */
+		SPtr<DepthStencilStateCore> _createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const;
+
+		/**
+		 * @brief	Creates an uninitialized rasterizer state. Requires manual initialization
+		 *			after creation.
+		 *
+		 * @note	Internal method.
+		 */
+		SPtr<RasterizerStateCore> _createRasterizerState(const RASTERIZER_STATE_DESC& desc) const;
+
+		/**
+		 * @brief	Creates an uninitialized blend state. Requires manual initialization
+		 *			after creation.
+		 *
+		 * @note	Internal method.
+		 */
+		SPtr<BlendStateCore> _createBlendState(const BLEND_STATE_DESC& desc) const;
+
 		/**
 		 * @brief	Gets a sampler state initialized with default options.
 		 */
@@ -253,12 +231,6 @@ namespace BansheeEngine
 		 */
 		const SPtr<DepthStencilStateCore>& getDefaultDepthStencilState() const;
 
-	private:
-		mutable SPtr<SamplerStateCore> mDefaultSamplerState;
-		mutable SPtr<BlendStateCore> mDefaultBlendState;
-		mutable SPtr<RasterizerStateCore> mDefaultRasterizerState;
-		mutable SPtr<DepthStencilStateCore> mDefaultDepthStencilState;
-
 	protected:
 		friend class SamplerState;
 		friend class BlendState;
@@ -277,17 +249,83 @@ namespace BansheeEngine
 		/**
 		 * @copydoc	createBlendState
 		 */
-		virtual SPtr<BlendStateCore> createBlendStateInternal(const BLEND_STATE_DESC& desc) const;
+		virtual SPtr<BlendStateCore> createBlendStateInternal(const BLEND_STATE_DESC& desc, UINT32 id) const;
 
 		/**
 		 * @copydoc	createRasterizerState
 		 */
-		virtual SPtr<RasterizerStateCore> createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc) const;
+		virtual SPtr<RasterizerStateCore> createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc, UINT32 id) const;
 
 		/**
 		 * @copydoc	createDepthStencilState
 		 */
-		virtual SPtr<DepthStencilStateCore> createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc) const;
+		virtual SPtr<DepthStencilStateCore> createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id) const;
+
+	private:
+		/**
+		 * @brief	Triggered when a new sampler state is created. 
+		 */
+		void notifySamplerStateCreated(const SAMPLER_STATE_DESC& desc, const SPtr<SamplerStateCore>& state) const;
+
+		/**
+		 * @brief	Triggered when a new sampler state is created. 
+		 */
+		void notifyBlendStateCreated(const BLEND_STATE_DESC& desc, const CachedBlendState& state) const;
 
+		/**
+		 * @brief	Triggered when a new sampler state is created. 
+		 */
+		void notifyRasterizerStateCreated(const RASTERIZER_STATE_DESC& desc, const CachedRasterizerState& state) const;
+
+		/**
+		 * @brief	Triggered when a new sampler state is created. 
+		 */
+		void notifyDepthStencilStateCreated(const DEPTH_STENCIL_STATE_DESC& desc, const CachedDepthStencilState& state) const;
+
+		/**
+		 * @brief	Triggered when the last reference to a specific sampler state is destroyed, which
+		 *			means we must clear our cached version as well.
+		 */
+		void notifySamplerStateDestroyed(const SAMPLER_STATE_DESC& desc) const;
+
+		/**
+		 * @brief	Attempts to find a cached sampler state corresponding to the provided descriptor. 
+		 *			Returns null if one doesn't exist.
+		 */
+		SPtr<SamplerStateCore> findCachedState(const SAMPLER_STATE_DESC& desc) const;
+
+				/**
+		 * @brief	Attempts to find a cached blend state corresponding to the provided descriptor. 
+		 *			Returns null if one doesn't exist.
+		 */
+		SPtr<BlendStateCore> findCachedState(const BLEND_STATE_DESC& desc, UINT32& id) const;
+
+				/**
+		 * @brief	Attempts to find a cached rasterizer state corresponding to the provided descriptor. 
+		 *			Returns null if one doesn't exist.
+		 */
+		SPtr<RasterizerStateCore> findCachedState(const RASTERIZER_STATE_DESC& desc, UINT32& id) const;
+
+		/**
+		 * @brief	Attempts to find a cached depth-stencil state corresponding to the provided descriptor. 
+		 *			Returns null if one doesn't exist.
+		 */
+		SPtr<DepthStencilStateCore> findCachedState(const DEPTH_STENCIL_STATE_DESC& desc, UINT32& id) const;
+
+		mutable SPtr<SamplerStateCore> mDefaultSamplerState;
+		mutable SPtr<BlendStateCore> mDefaultBlendState;
+		mutable SPtr<RasterizerStateCore> mDefaultRasterizerState;
+		mutable SPtr<DepthStencilStateCore> mDefaultDepthStencilState;
+
+		mutable UnorderedMap<SAMPLER_STATE_DESC, std::weak_ptr<SamplerStateCore>> mCachedSamplerStates;
+		mutable UnorderedMap<BLEND_STATE_DESC, CachedBlendState> mCachedBlendStates;
+		mutable UnorderedMap<RASTERIZER_STATE_DESC, CachedRasterizerState> mCachedRasterizerStates;
+		mutable UnorderedMap<DEPTH_STENCIL_STATE_DESC, CachedDepthStencilState> mCachedDepthStencilStates;
+
+		mutable UINT32 mNextBlendStateId;
+		mutable UINT32 mNextRasterizerStateId;
+		mutable UINT32 mNextDepthStencilStateId;
+
+		BS_MUTEX(mMutex);
 	};
 }

+ 10 - 0
BansheeCore/Include/BsSamplerState.h

@@ -136,6 +136,16 @@ namespace BansheeEngine
 
 		SamplerStateCore(const SAMPLER_STATE_DESC& desc);
 
+		/**
+		 * @copydoc	CoreObjectCore::initialize
+		 */
+		void initialize() override;
+
+		/**
+		 * @brief	Creates any API-specific state objects.
+		 */
+		virtual void createInternal() { }
+
 		SamplerProperties mProperties;
 	};
 

+ 16 - 5
BansheeCore/Source/BsBlendState.cpp

@@ -94,15 +94,26 @@ namespace BansheeEngine
 		return mData.renderTargetDesc[renderTargetIdx].renderTargetWriteMask;
 	}
 
-	BlendStateCore::BlendStateCore(const BLEND_STATE_DESC& desc)
-		:mProperties(desc)
+	BlendStateCore::BlendStateCore(const BLEND_STATE_DESC& desc, UINT32 id)
+		:mProperties(desc), mId(id)
 	{
 
 	}
 
 	BlendStateCore::~BlendStateCore()
 	{
-		RenderStateCoreManager::instance().notifyBlendStateDestroyed(mProperties.mData);
+
+	}
+
+	void BlendStateCore::initialize()
+	{
+		// Since we cache states it's possible this object was already initialized
+		// (i.e. multiple sim-states can share a single core-state)
+		if (isInitialized())
+			return;
+
+		createInternal();
+		CoreObjectCore::initialize();
 	}
 
 	const BlendProperties& BlendStateCore::getProperties() const
@@ -121,7 +132,7 @@ namespace BansheeEngine
 
 	BlendState::~BlendState()
 	{
-		RenderStateManager::instance().notifyBlendStateDestroyed(mProperties.mData);
+
 	}
 
 	SPtr<BlendStateCore> BlendState::getCore() const
@@ -131,7 +142,7 @@ namespace BansheeEngine
 
 	SPtr<CoreObjectCore> BlendState::createCore() const
 	{
-		return RenderStateCoreManager::instance().createBlendStateInternal(mProperties.mData);
+		return RenderStateCoreManager::instance()._createBlendState(mProperties.mData);
 	}
 
 	const BlendProperties& BlendState::getProperties() const

+ 16 - 5
BansheeCore/Source/BsDepthStencilState.cpp

@@ -31,15 +31,26 @@ namespace BansheeEngine
 
 	}
 
-	DepthStencilStateCore::DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc)
-		: mProperties(desc)
+	DepthStencilStateCore::DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id)
+		: mProperties(desc), mId(id)
 	{
 
 	}
 
 	DepthStencilStateCore::~DepthStencilStateCore()
 	{
-		RenderStateCoreManager::instance().notifyDepthStencilStateDestroyed(mProperties.mData);
+
+	}
+
+	void DepthStencilStateCore::initialize()
+	{
+		// Since we cache states it's possible this object was already initialized
+		// (i.e. multiple sim-states can share a single core-state)
+		if (isInitialized())
+			return;
+
+		createInternal();
+		CoreObjectCore::initialize();
 	}
 
 	const DepthStencilProperties& DepthStencilStateCore::getProperties() const
@@ -60,7 +71,7 @@ namespace BansheeEngine
 
 	DepthStencilState::~DepthStencilState()
 	{
-		RenderStateManager::instance().notifyDepthStencilStateDestroyed(mProperties.mData);
+
 	}
 
 	SPtr<DepthStencilStateCore> DepthStencilState::getCore() const
@@ -70,7 +81,7 @@ namespace BansheeEngine
 
 	SPtr<CoreObjectCore> DepthStencilState::createCore() const
 	{
-		return RenderStateCoreManager::instance().createDepthStencilStateInternal(mProperties.mData);
+		return RenderStateCoreManager::instance()._createDepthStencilState(mProperties.mData);
 	}
 
 	const DepthStencilStatePtr& DepthStencilState::getDefault()

+ 16 - 5
BansheeCore/Source/BsRasterizerState.cpp

@@ -23,15 +23,26 @@ namespace BansheeEngine
 		:mData(desc), mHash(RasterizerState::generateHash(desc))
 	{ }
 
-	RasterizerStateCore::RasterizerStateCore(const RASTERIZER_STATE_DESC& desc)
-		: mProperties(desc)
+	RasterizerStateCore::RasterizerStateCore(const RASTERIZER_STATE_DESC& desc, UINT32 id)
+		: mProperties(desc), mId(id)
 	{
 
 	}
 
 	RasterizerStateCore::~RasterizerStateCore()
 	{
-		RenderStateCoreManager::instance().notifyRasterizerStateDestroyed(mProperties.mData);
+
+	}
+
+	void RasterizerStateCore::initialize()
+	{
+		// Since we cache states it's possible this object was already initialized
+		// (i.e. multiple sim-states can share a single core-state)
+		if (isInitialized())
+			return;
+
+		createInternal();
+		CoreObjectCore::initialize();
 	}
 
 	const RasterizerProperties& RasterizerStateCore::getProperties() const
@@ -52,7 +63,7 @@ namespace BansheeEngine
 
 	RasterizerState::~RasterizerState()
 	{
-		RenderStateManager::instance().notifyRasterizerStateDestroyed(mProperties.mData);
+
 	}
 
 	SPtr<RasterizerStateCore> RasterizerState::getCore() const
@@ -62,7 +73,7 @@ namespace BansheeEngine
 
 	SPtr<CoreObjectCore> RasterizerState::createCore() const
 	{
-		return RenderStateCoreManager::instance().createRasterizerStateInternal(mProperties.mData);
+		return RenderStateCoreManager::instance()._createRasterizerState(mProperties.mData);
 	}
 
 	const RasterizerProperties& RasterizerState::getProperties() const

+ 233 - 189
BansheeCore/Source/BsRenderStateManager.cpp

@@ -6,128 +6,114 @@
 
 namespace BansheeEngine
 {
-	template<bool Core>
-	void TRenderStateManager<Core>::notifySamplerStateCreated(const SAMPLER_STATE_DESC& desc, const SPtr<SamplerStateType>& state) const
+	SamplerStatePtr RenderStateManager::createSamplerState(const SAMPLER_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		SPtr<SamplerState> state = _createSamplerStatePtr(desc);
+		state->initialize();
 
-		mCachedSamplerStates[desc] = state;
+		return state;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyBlendStateCreated(const BLEND_STATE_DESC& desc, const SPtr<BlendStateType>& state) const
+	DepthStencilStatePtr RenderStateManager::createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		SPtr<DepthStencilState> state = _createDepthStencilStatePtr(desc);
+		state->initialize();
 
-		mCachedBlendStates[desc] = state;
+		return state;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyRasterizerStateCreated(const RASTERIZER_STATE_DESC& desc, const SPtr<RasterizerStateType>& state) const
+	RasterizerStatePtr RenderStateManager::createRasterizerState(const RASTERIZER_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		SPtr<RasterizerState> state = _createRasterizerStatePtr(desc);
+		state->initialize();
 
-		mCachedRasterizerStates[desc] = state;
+		return state;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyDepthStencilStateCreated(const DEPTH_STENCIL_STATE_DESC& desc, const SPtr<DepthStencilStateType>& state) const
+	BlendStatePtr RenderStateManager::createBlendState(const BLEND_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		SPtr<BlendState> state = _createBlendStatePtr(desc);
+		state->initialize();
 
-		mCachedDepthStencilStates[desc] = state;
+		return state;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifySamplerStateDestroyed(const SAMPLER_STATE_DESC& desc) const
+	SamplerStatePtr RenderStateManager::_createSamplerStatePtr(const SAMPLER_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		SamplerStatePtr samplerState = bs_core_ptr<SamplerState>(new (bs_alloc<SamplerState>()) SamplerState(desc));
+		samplerState->_setThisPtr(samplerState);
 
-		mCachedSamplerStates.erase(desc);
+		return samplerState;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyBlendStateDestroyed(const BLEND_STATE_DESC& desc) const
+	DepthStencilStatePtr RenderStateManager::_createDepthStencilStatePtr(const DEPTH_STENCIL_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		DepthStencilStatePtr depthStencilState = bs_core_ptr<DepthStencilState>(new (bs_alloc<DepthStencilState>()) DepthStencilState(desc));
+		depthStencilState->_setThisPtr(depthStencilState);
 
-		mCachedBlendStates.erase(desc);
+		return depthStencilState;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyRasterizerStateDestroyed(const RASTERIZER_STATE_DESC& desc) const
+	RasterizerStatePtr RenderStateManager::_createRasterizerStatePtr(const RASTERIZER_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		RasterizerStatePtr rasterizerState = bs_core_ptr<RasterizerState>(new (bs_alloc<RasterizerState>()) RasterizerState(desc));
+		rasterizerState->_setThisPtr(rasterizerState);
 
-		mCachedRasterizerStates.erase(desc);
+		return rasterizerState;
 	}
 
-	template<bool Core>
-	void TRenderStateManager<Core>::notifyDepthStencilStateDestroyed(const DEPTH_STENCIL_STATE_DESC& desc) const
+	BlendStatePtr RenderStateManager::_createBlendStatePtr(const BLEND_STATE_DESC& desc) const
 	{
-		BS_LOCK_MUTEX(mMutex);
+		BlendStatePtr blendState = bs_core_ptr<BlendState>(new (bs_alloc<BlendState>()) BlendState(desc));
+		blendState->_setThisPtr(blendState);
 
-		mCachedDepthStencilStates.erase(desc);
+		return blendState;
 	}
 
-	template<bool Core>
-	SPtr<typename TRenderStateManager<Core>::SamplerStateType> TRenderStateManager<Core>::findCachedState(const SAMPLER_STATE_DESC& desc) const
-	{
-		BS_LOCK_MUTEX(mMutex);
-
-		auto iterFind = mCachedSamplerStates.find(desc);
-		if (iterFind != mCachedSamplerStates.end())
-			return iterFind->second.lock();
+	const SamplerStatePtr& RenderStateManager::getDefaultSamplerState() const 
+	{ 
+		if(mDefaultSamplerState == nullptr)
+			mDefaultSamplerState = createSamplerState(SAMPLER_STATE_DESC());
 
-		return nullptr;
+		return mDefaultSamplerState; 
 	}
 
-	template<bool Core>
-	SPtr<typename TRenderStateManager<Core>::BlendStateType> TRenderStateManager<Core>::findCachedState(const BLEND_STATE_DESC& desc) const
-	{
-		BS_LOCK_MUTEX(mMutex);
-
-		auto iterFind = mCachedBlendStates.find(desc);
-		if (iterFind != mCachedBlendStates.end())
-			return iterFind->second.lock();
+	const BlendStatePtr& RenderStateManager::getDefaultBlendState() const 
+	{ 
+		if(mDefaultBlendState == nullptr)
+			mDefaultBlendState = createBlendState(BLEND_STATE_DESC());
 
-		return nullptr;
+		return mDefaultBlendState; 
 	}
 
-	template<bool Core>
-	SPtr<typename TRenderStateManager<Core>::RasterizerStateType> TRenderStateManager<Core>::findCachedState(const RASTERIZER_STATE_DESC& desc) const
-	{
-		BS_LOCK_MUTEX(mMutex);
-
-		auto iterFind = mCachedRasterizerStates.find(desc);
-		if (iterFind != mCachedRasterizerStates.end())
-			return iterFind->second.lock();
+	const RasterizerStatePtr& RenderStateManager::getDefaultRasterizerState() const 
+	{ 
+		if(mDefaultRasterizerState == nullptr)
+			mDefaultRasterizerState = createRasterizerState(RASTERIZER_STATE_DESC());
 
-		return nullptr;
+		return mDefaultRasterizerState; 
 	}
 
-	template<bool Core>
-	SPtr<typename TRenderStateManager<Core>::DepthStencilStateType> TRenderStateManager<Core>::findCachedState(const DEPTH_STENCIL_STATE_DESC& desc) const
-	{
-		BS_LOCK_MUTEX(mMutex);
-
-		auto iterFind = mCachedDepthStencilStates.find(desc);
-		if (iterFind != mCachedDepthStencilStates.end())
-			return iterFind->second.lock();
+	const DepthStencilStatePtr& RenderStateManager::getDefaultDepthStencilState() const 
+	{ 
+		if(mDefaultDepthStencilState == nullptr)
+			mDefaultDepthStencilState = createDepthStencilState(DEPTH_STENCIL_STATE_DESC());
 
-		return nullptr;
+		return mDefaultDepthStencilState; 
 	}
 
-	template class TRenderStateManager < true > ;
-	template class TRenderStateManager < false >;
+	RenderStateCoreManager::RenderStateCoreManager()
+		:mNextBlendStateId(0), mNextDepthStencilStateId(0), mNextRasterizerStateId(0)
+	{
+		
+	}
 
-	SamplerStatePtr RenderStateManager::createSamplerState(const SAMPLER_STATE_DESC& desc) const
+	SPtr<SamplerStateCore> RenderStateCoreManager::createSamplerState(const SAMPLER_STATE_DESC& desc) const
 	{
-		SPtr<SamplerState> state = findCachedState(desc);
+		SPtr<SamplerStateCore> state = findCachedState(desc);
 		if (state == nullptr)
 		{
-			state = bs_core_ptr<SamplerState>(new (bs_alloc<SamplerState>()) SamplerState(desc));
-			state->_setThisPtr(state);
+			state = createSamplerStateInternal(desc);
 			state->initialize();
 
 			notifySamplerStateCreated(desc, state);
@@ -136,235 +122,293 @@ namespace BansheeEngine
 		return state;
 	}
 
-	DepthStencilStatePtr RenderStateManager::createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const
+	SPtr<DepthStencilStateCore> RenderStateCoreManager::createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const
 	{
-		SPtr<DepthStencilState> state = findCachedState(desc);
+		UINT32 id = 0;
+		SPtr<DepthStencilStateCore> state = findCachedState(desc, id);
 		if (state == nullptr)
 		{
-			state = bs_core_ptr<DepthStencilState>(new (bs_alloc<DepthStencilState>()) DepthStencilState(desc));
-			state->_setThisPtr(state);
+			state = createDepthStencilStateInternal(desc, id);
 			state->initialize();
 
-			notifyDepthStencilStateCreated(desc, state);
+			CachedDepthStencilState cachedData(id);
+			cachedData.state = state;
+
+			notifyDepthStencilStateCreated(desc, cachedData);
 		}
 
 		return state;
 	}
 
-	RasterizerStatePtr RenderStateManager::createRasterizerState(const RASTERIZER_STATE_DESC& desc) const
+	SPtr<RasterizerStateCore> RenderStateCoreManager::createRasterizerState(const RASTERIZER_STATE_DESC& desc) const
 	{
-		SPtr<RasterizerState> state = findCachedState(desc);
+		UINT32 id = 0;
+		SPtr<RasterizerStateCore> state = findCachedState(desc, id);
 		if (state == nullptr)
 		{
-			state = bs_core_ptr<RasterizerState>(new (bs_alloc<RasterizerState>()) RasterizerState(desc));
-			state->_setThisPtr(state);
+			state = createRasterizerStateInternal(desc, id);
 			state->initialize();
 
-			notifyRasterizerStateCreated(desc, state);
+			CachedRasterizerState cachedData(id);
+			cachedData.state = state;
+
+			notifyRasterizerStateCreated(desc, cachedData);
 		}
 
 		return state;
 	}
 
-	BlendStatePtr RenderStateManager::createBlendState(const BLEND_STATE_DESC& desc) const
+	SPtr<BlendStateCore> RenderStateCoreManager::createBlendState(const BLEND_STATE_DESC& desc) const
 	{
-		SPtr<BlendState> state = findCachedState(desc);
+		UINT32 id = 0;
+		SPtr<BlendStateCore> state = findCachedState(desc, id);
 		if (state == nullptr)
 		{
-			state = bs_core_ptr<BlendState>(new (bs_alloc<BlendState>()) BlendState(desc));
-			state->_setThisPtr(state);
+			state = createBlendStateInternal(desc, id);
 			state->initialize();
 
-			notifyBlendStateCreated(desc, state);
+			CachedBlendState cachedData(id);
+			cachedData.state = state;
+
+			notifyBlendStateCreated(desc, cachedData);
 		}
 
 		return state;
 	}
 
-	SamplerStatePtr RenderStateManager::_createSamplerStatePtr(const SAMPLER_STATE_DESC& desc) const
+	SPtr<SamplerStateCore> RenderStateCoreManager::_createSamplerState(const SAMPLER_STATE_DESC& desc) const
 	{
-		SamplerStatePtr samplerState = bs_core_ptr<SamplerState>(
-			new (bs_alloc<SamplerState>()) SamplerState(desc));
-		samplerState->_setThisPtr(samplerState);
+		SPtr<SamplerStateCore> state = findCachedState(desc);
+		if (state == nullptr)
+		{
+			state = createSamplerStateInternal(desc);
 
-		return samplerState;
+			notifySamplerStateCreated(desc, state);
+		}
+
+		return state;
 	}
 
-	DepthStencilStatePtr RenderStateManager::_createDepthStencilStatePtr(const DEPTH_STENCIL_STATE_DESC& desc) const
+	SPtr<DepthStencilStateCore> RenderStateCoreManager::_createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const
 	{
-		DepthStencilStatePtr depthStencilState = bs_core_ptr<DepthStencilState>(
-			new (bs_alloc<DepthStencilState>()) DepthStencilState(desc));
-		depthStencilState->_setThisPtr(depthStencilState);
+		UINT32 id = 0;
+		SPtr<DepthStencilStateCore> state = findCachedState(desc, id);
+		if (state == nullptr)
+		{
+			state = createDepthStencilStateInternal(desc, id);
 
-		return depthStencilState;
+			CachedDepthStencilState cachedData(id);
+			cachedData.state = state;
+
+			notifyDepthStencilStateCreated(desc, cachedData);
+		}
+
+		return state;
 	}
 
-	RasterizerStatePtr RenderStateManager::_createRasterizerStatePtr(const RASTERIZER_STATE_DESC& desc) const
+	SPtr<RasterizerStateCore> RenderStateCoreManager::_createRasterizerState(const RASTERIZER_STATE_DESC& desc) const
 	{
-		RasterizerStatePtr rasterizerState = bs_core_ptr<RasterizerState>(
-			new (bs_alloc<RasterizerState>()) RasterizerState(desc));
-		rasterizerState->_setThisPtr(rasterizerState);
+		UINT32 id = 0;
+		SPtr<RasterizerStateCore> state = findCachedState(desc, id);
+		if (state == nullptr)
+		{
+			state = createRasterizerStateInternal(desc, id);
 
-		return rasterizerState;
+			CachedRasterizerState cachedData(id);
+			cachedData.state = state;
+
+			notifyRasterizerStateCreated(desc, cachedData);
+		}
+
+		return state;
 	}
 
-	BlendStatePtr RenderStateManager::_createBlendStatePtr(const BLEND_STATE_DESC& desc) const
+	SPtr<BlendStateCore> RenderStateCoreManager::_createBlendState(const BLEND_STATE_DESC& desc) const
 	{
-		BlendStatePtr blendState = bs_core_ptr<BlendState>(
-			new (bs_alloc<BlendState>()) BlendState(desc));
-		blendState->_setThisPtr(blendState);
+		UINT32 id = 0;
+		SPtr<BlendStateCore> state = findCachedState(desc, id);
+		if (state == nullptr)
+		{
+			state = createBlendStateInternal(desc, id);
 
-		return blendState;
+			CachedBlendState cachedData(id);
+			cachedData.state = state;
+
+			notifyBlendStateCreated(desc, cachedData);
+		}
+
+		return state;
 	}
 
-	const SamplerStatePtr& RenderStateManager::getDefaultSamplerState() const 
-	{ 
-		if(mDefaultSamplerState == nullptr)
+	const SPtr<SamplerStateCore>& RenderStateCoreManager::getDefaultSamplerState() const
+	{
+		if (mDefaultSamplerState == nullptr)
 			mDefaultSamplerState = createSamplerState(SAMPLER_STATE_DESC());
 
-		return mDefaultSamplerState; 
+		return mDefaultSamplerState;
 	}
 
-	const BlendStatePtr& RenderStateManager::getDefaultBlendState() const 
-	{ 
-		if(mDefaultBlendState == nullptr)
+	const SPtr<BlendStateCore>& RenderStateCoreManager::getDefaultBlendState() const
+	{
+		if (mDefaultBlendState == nullptr)
 			mDefaultBlendState = createBlendState(BLEND_STATE_DESC());
 
-		return mDefaultBlendState; 
+		return mDefaultBlendState;
 	}
 
-	const RasterizerStatePtr& RenderStateManager::getDefaultRasterizerState() const 
-	{ 
-		if(mDefaultRasterizerState == nullptr)
+	const SPtr<RasterizerStateCore>& RenderStateCoreManager::getDefaultRasterizerState() const
+	{
+		if (mDefaultRasterizerState == nullptr)
 			mDefaultRasterizerState = createRasterizerState(RASTERIZER_STATE_DESC());
 
-		return mDefaultRasterizerState; 
+		return mDefaultRasterizerState;
 	}
 
-	const DepthStencilStatePtr& RenderStateManager::getDefaultDepthStencilState() const 
-	{ 
-		if(mDefaultDepthStencilState == nullptr)
+	const SPtr<DepthStencilStateCore>& RenderStateCoreManager::getDefaultDepthStencilState() const
+	{
+		if (mDefaultDepthStencilState == nullptr)
 			mDefaultDepthStencilState = createDepthStencilState(DEPTH_STENCIL_STATE_DESC());
 
-		return mDefaultDepthStencilState; 
+		return mDefaultDepthStencilState;
 	}
 
-	SPtr<SamplerStateCore> RenderStateCoreManager::createSamplerState(const SAMPLER_STATE_DESC& desc) const
+	void RenderStateCoreManager::notifySamplerStateCreated(const SAMPLER_STATE_DESC& desc, const SPtr<SamplerStateCore>& state) const
 	{
-		SPtr<SamplerStateCore> samplerState = createSamplerStateInternal(desc);
-		samplerState->initialize();
+		BS_LOCK_MUTEX(mMutex);
 
-		return samplerState;
+		mCachedSamplerStates[desc] = state;
 	}
 
-	SPtr<DepthStencilStateCore> RenderStateCoreManager::createDepthStencilState(const DEPTH_STENCIL_STATE_DESC& desc) const
+	void RenderStateCoreManager::notifyBlendStateCreated(const BLEND_STATE_DESC& desc, const CachedBlendState& state) const
 	{
-		SPtr<DepthStencilStateCore> depthStencilState = createDepthStencilStateInternal(desc);
-		depthStencilState->initialize();
+		BS_LOCK_MUTEX(mMutex);
 
-		return depthStencilState;
+		mCachedBlendStates[desc] = state;
 	}
 
-	SPtr<RasterizerStateCore> RenderStateCoreManager::createRasterizerState(const RASTERIZER_STATE_DESC& desc) const
+	void RenderStateCoreManager::notifyRasterizerStateCreated(const RASTERIZER_STATE_DESC& desc, const CachedRasterizerState& state) const
 	{
-		SPtr<RasterizerStateCore> rasterizerState = createRasterizerStateInternal(desc);
-		rasterizerState->initialize();
+		BS_LOCK_MUTEX(mMutex);
 
-		return rasterizerState;
+		mCachedRasterizerStates[desc] = state;
 	}
 
-	SPtr<BlendStateCore> RenderStateCoreManager::createBlendState(const BLEND_STATE_DESC& desc) const
+	void RenderStateCoreManager::notifyDepthStencilStateCreated(const DEPTH_STENCIL_STATE_DESC& desc, const CachedDepthStencilState& state) const
 	{
-		SPtr<BlendStateCore> blendState = createBlendStateInternal(desc);
-		blendState->initialize();
+		BS_LOCK_MUTEX(mMutex);
 
-		return blendState;
+		mCachedDepthStencilStates[desc] = state;
 	}
 
-	const SPtr<SamplerStateCore>& RenderStateCoreManager::getDefaultSamplerState() const
+	void RenderStateCoreManager::notifySamplerStateDestroyed(const SAMPLER_STATE_DESC& desc) const
 	{
-		if (mDefaultSamplerState == nullptr)
-			mDefaultSamplerState = createSamplerState(SAMPLER_STATE_DESC());
+		BS_LOCK_MUTEX(mMutex);
 
-		return mDefaultSamplerState;
+		mCachedSamplerStates.erase(desc);
 	}
 
-	const SPtr<BlendStateCore>& RenderStateCoreManager::getDefaultBlendState() const
+	SPtr<SamplerStateCore> RenderStateCoreManager::findCachedState(const SAMPLER_STATE_DESC& desc) const
 	{
-		if (mDefaultBlendState == nullptr)
-			mDefaultBlendState = createBlendState(BLEND_STATE_DESC());
+		BS_LOCK_MUTEX(mMutex);
 
-		return mDefaultBlendState;
+		auto iterFind = mCachedSamplerStates.find(desc);
+		if (iterFind != mCachedSamplerStates.end())
+			return iterFind->second.lock();
+
+		return nullptr;
 	}
 
-	const SPtr<RasterizerStateCore>& RenderStateCoreManager::getDefaultRasterizerState() const
+	SPtr<BlendStateCore> RenderStateCoreManager::findCachedState(const BLEND_STATE_DESC& desc, UINT32& id) const
 	{
-		if (mDefaultRasterizerState == nullptr)
-			mDefaultRasterizerState = createRasterizerState(RASTERIZER_STATE_DESC());
+		BS_LOCK_MUTEX(mMutex);
 
-		return mDefaultRasterizerState;
-	}
+		auto iterFind = mCachedBlendStates.find(desc);
+		if (iterFind != mCachedBlendStates.end())
+		{
+			id = iterFind->second.id;
 
-	const SPtr<DepthStencilStateCore>& RenderStateCoreManager::getDefaultDepthStencilState() const
-	{
-		if (mDefaultDepthStencilState == nullptr)
-			mDefaultDepthStencilState = createDepthStencilState(DEPTH_STENCIL_STATE_DESC());
+			if (!iterFind->second.state.expired())
+				return iterFind->second.state.lock();
 
-		return mDefaultDepthStencilState;
+			return nullptr;
+		}
+
+		id = mNextBlendStateId++;
+		assert(id <= 0x3FF); // 10 bits maximum
+
+		return nullptr;
 	}
 
-	SPtr<SamplerStateCore> RenderStateCoreManager::createSamplerStateInternal(const SAMPLER_STATE_DESC& desc) const
+	SPtr<RasterizerStateCore> RenderStateCoreManager::findCachedState(const RASTERIZER_STATE_DESC& desc, UINT32& id) const
 	{
-		SPtr<SamplerStateCore> state = findCachedState(desc);
-		if (state == nullptr)
+		BS_LOCK_MUTEX(mMutex);
+
+		auto iterFind = mCachedRasterizerStates.find(desc);
+		if (iterFind != mCachedRasterizerStates.end())
 		{
-			state = bs_shared_ptr<SamplerStateCore>(new (bs_alloc<SamplerStateCore>()) SamplerStateCore(desc));
-			state->_setThisPtr(state);
+			id = iterFind->second.id;
 
-			notifySamplerStateCreated(desc, state);
+			if (!iterFind->second.state.expired())
+				return iterFind->second.state.lock();
+
+			return nullptr;
 		}
 
-		return state;
+		id = mNextRasterizerStateId++;
+		assert(id <= 0x3FF); // 10 bits maximum
+
+		return nullptr;
 	}
 
-	SPtr<DepthStencilStateCore> RenderStateCoreManager::createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc) const
+	SPtr<DepthStencilStateCore> RenderStateCoreManager::findCachedState(const DEPTH_STENCIL_STATE_DESC& desc, UINT32& id) const
 	{
-		SPtr<DepthStencilStateCore> state = findCachedState(desc);
-		if (state == nullptr)
+		BS_LOCK_MUTEX(mMutex);
+
+		auto iterFind = mCachedDepthStencilStates.find(desc);
+		if (iterFind != mCachedDepthStencilStates.end())
 		{
-			SPtr<DepthStencilStateCore> state = bs_shared_ptr<DepthStencilStateCore>(new (bs_alloc<DepthStencilStateCore>()) DepthStencilStateCore(desc));
-			state->_setThisPtr(state);
+			id = iterFind->second.id;
 
-			notifyDepthStencilStateCreated(desc, state);
+			if (!iterFind->second.state.expired())
+				return iterFind->second.state.lock();
+
+			return nullptr;
 		}
 
-		return state;
+		id = mNextDepthStencilStateId++;
+		assert(id <= 0x3FF); // 10 bits maximum
+
+		return nullptr;
 	}
 
-	SPtr<RasterizerStateCore> RenderStateCoreManager::createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc) const
+	SPtr<SamplerStateCore> RenderStateCoreManager::createSamplerStateInternal(const SAMPLER_STATE_DESC& desc) const
 	{
-		SPtr<RasterizerStateCore> state = findCachedState(desc);
-		if (state == nullptr)
-		{
-			SPtr<RasterizerStateCore> state = bs_shared_ptr<RasterizerStateCore>(new (bs_alloc<RasterizerStateCore>()) RasterizerStateCore(desc));
-			state->_setThisPtr(state);
+		SPtr<SamplerStateCore> state = bs_shared_ptr<SamplerStateCore>(new (bs_alloc<SamplerStateCore>()) SamplerStateCore(desc));
+		state->_setThisPtr(state);
 
-			notifyRasterizerStateCreated(desc, state);
-		}
+		return state;
+	}
+
+	SPtr<DepthStencilStateCore> RenderStateCoreManager::createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id) const
+	{
+		SPtr<DepthStencilStateCore> state = bs_shared_ptr<DepthStencilStateCore>(new (bs_alloc<DepthStencilStateCore>()) DepthStencilStateCore(desc, id));
+		state->_setThisPtr(state);
 
 		return state;
 	}
 
-	SPtr<BlendStateCore> RenderStateCoreManager::createBlendStateInternal(const BLEND_STATE_DESC& desc) const
+	SPtr<RasterizerStateCore> RenderStateCoreManager::createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc, UINT32 id) const
 	{
-		SPtr<BlendStateCore> state = findCachedState(desc);
-		if (state == nullptr)
-		{
-			state = bs_shared_ptr<BlendStateCore>(new (bs_alloc<BlendStateCore>()) BlendStateCore(desc));
-			state->_setThisPtr(state);
+		SPtr<RasterizerStateCore> state = bs_shared_ptr<RasterizerStateCore>(new (bs_alloc<RasterizerStateCore>()) RasterizerStateCore(desc, id));
+		state->_setThisPtr(state);
 
-			notifyBlendStateCreated(desc, state);
-		}
+		return state;
+	}
+
+	SPtr<BlendStateCore> RenderStateCoreManager::createBlendStateInternal(const BLEND_STATE_DESC& desc, UINT32 id) const
+	{
+		SPtr<BlendStateCore> state = bs_shared_ptr<BlendStateCore>(new (bs_alloc<BlendStateCore>()) BlendStateCore(desc, id));
+		state->_setThisPtr(state);
 
 		return state;
 	}

+ 13 - 2
BansheeCore/Source/BsSamplerState.cpp

@@ -56,6 +56,17 @@ namespace BansheeEngine
 		RenderStateCoreManager::instance().notifySamplerStateDestroyed(mProperties.mData);
 	}
 
+	void SamplerStateCore::initialize()
+	{
+		// Since we cache states it's possible this object was already initialized
+		// (i.e. multiple sim-states can share a single core-state)
+		if (isInitialized())
+			return;
+
+		createInternal();
+		CoreObjectCore::initialize();
+	}
+
 	const SamplerProperties& SamplerStateCore::getProperties() const
 	{
 		return mProperties;
@@ -74,7 +85,7 @@ namespace BansheeEngine
 
 	SamplerState::~SamplerState()
 	{
-		RenderStateManager::instance().notifySamplerStateDestroyed(mProperties.mData);
+
 	}
 
 	SPtr<SamplerStateCore> SamplerState::getCore() const
@@ -84,7 +95,7 @@ namespace BansheeEngine
 
 	SPtr<CoreObjectCore> SamplerState::createCore() const
 	{
-		return RenderStateCoreManager::instance().createSamplerStateInternal(mProperties.mData);
+		return RenderStateCoreManager::instance()._createSamplerState(mProperties.mData);
 	}
 
 	SamplerStatePtr SamplerState::create(const SAMPLER_STATE_DESC& desc)

+ 3 - 3
BansheeD3D11RenderAPI/Include/BsD3D11BlendState.h

@@ -22,12 +22,12 @@ namespace BansheeEngine
 	protected:
 		friend class D3D11RenderStateCoreManager;
 
-		D3D11BlendStateCore(const BLEND_STATE_DESC& desc);
+		D3D11BlendStateCore(const BLEND_STATE_DESC& desc, UINT32 id);
 
 		/**
-		 * @copydoc BlendStateCore::initialize
+		 * @copydoc BlendStateCore::createInternal
 		 */
-		void initialize();
+		void createInternal() override;
 
 		ID3D11BlendState* mBlendState;
 	};

+ 3 - 3
BansheeD3D11RenderAPI/Include/BsD3D11DepthStencilState.h

@@ -22,12 +22,12 @@ namespace BansheeEngine
 	protected:
 		friend class D3D11RenderStateCoreManager;
 
-		D3D11DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc);
+		D3D11DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id);
 
 		/**
-		 * @copydoc DepthStencilStateCore::initialize()
+		 * @copydoc DepthStencilStateCore::createInternal()
 		 */
-		void initialize();
+		void createInternal() override;
 
 		ID3D11DepthStencilState* mDepthStencilState;
 	};

+ 3 - 3
BansheeD3D11RenderAPI/Include/BsD3D11RasterizerState.h

@@ -18,12 +18,12 @@ namespace BansheeEngine
 	protected:
 		friend class D3D11RenderStateCoreManager;
 
-		D3D11RasterizerStateCore(const RASTERIZER_STATE_DESC& desc);
+		D3D11RasterizerStateCore(const RASTERIZER_STATE_DESC& desc, UINT32 id);
 
 		/**
-		 * @copydoc RasterizerStateCore::initialize
+		 * @copydoc RasterizerStateCore::createInternal
 		 */
-		void initialize();
+		void createInternal() override;
 
 		ID3D11RasterizerState* mRasterizerState;
 	};

+ 3 - 3
BansheeD3D11RenderAPI/Include/BsD3D11RenderStateManager.h

@@ -19,16 +19,16 @@ namespace BansheeEngine
 		/**
 		 * @copydoc	RenderStateCoreManager::createBlendStateInternal
 		 */
-		virtual SPtr<BlendStateCore> createBlendStateInternal(const BLEND_STATE_DESC& desc) const override;
+		virtual SPtr<BlendStateCore> createBlendStateInternal(const BLEND_STATE_DESC& desc, UINT32 id) const override;
 
 		/**
 		 * @copydoc	RenderStateCoreManager::createRasterizerStateInternal
 		 */
-		virtual SPtr<RasterizerStateCore> createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc) const override;
+		virtual SPtr<RasterizerStateCore> createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc, UINT32 id) const override;
 
 		/**
 		 * @copydoc	RenderStateCoreManager::createDepthStencilStateInternal
 		 */
-		virtual SPtr<DepthStencilStateCore> createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc) const override;
+		virtual SPtr<DepthStencilStateCore> createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id) const override;
 	};
 }

+ 2 - 2
BansheeD3D11RenderAPI/Include/BsD3D11SamplerState.h

@@ -21,9 +21,9 @@ namespace BansheeEngine
 		D3D11SamplerStateCore(const SAMPLER_STATE_DESC& desc);
 
 		/**
-		 * @copydoc SamplerStateCore::initialize
+		 * @copydoc SamplerStateCore::createInternal
 		 */
-		void initialize();
+		void createInternal() override;
 
 		ID3D11SamplerState* mSamplerState;
 	};

+ 4 - 4
BansheeD3D11RenderAPI/Source/BsD3D11BlendState.cpp

@@ -6,8 +6,8 @@
 
 namespace BansheeEngine
 {
-	D3D11BlendStateCore::D3D11BlendStateCore(const BLEND_STATE_DESC& desc)
-		:BlendStateCore(desc), mBlendState(nullptr)
+	D3D11BlendStateCore::D3D11BlendStateCore(const BLEND_STATE_DESC& desc, UINT32 id)
+		:BlendStateCore(desc, id), mBlendState(nullptr)
 	{ }
 
 	D3D11BlendStateCore::~D3D11BlendStateCore()
@@ -17,7 +17,7 @@ namespace BansheeEngine
 		BS_INC_RENDER_STAT_CAT(ResDestroyed, RenderStatObject_BlendState);
 	}
 
-	void D3D11BlendStateCore::initialize()
+	void D3D11BlendStateCore::createInternal()
 	{
 		D3D11_BLEND_DESC blendStateDesc;
 		ZeroMemory(&blendStateDesc, sizeof(D3D11_BLEND_DESC));
@@ -49,6 +49,6 @@ namespace BansheeEngine
 
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_BlendState);
 
-		BlendStateCore::initialize();
+		BlendStateCore::createInternal();
 	}
 }

+ 4 - 4
BansheeD3D11RenderAPI/Source/BsD3D11DepthStencilState.cpp

@@ -6,8 +6,8 @@
 
 namespace BansheeEngine
 {
-	D3D11DepthStencilStateCore::D3D11DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc)
-		:DepthStencilStateCore(desc), mDepthStencilState(nullptr)
+	D3D11DepthStencilStateCore::D3D11DepthStencilStateCore(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id)
+		:DepthStencilStateCore(desc, id), mDepthStencilState(nullptr)
 	{ }
 
 	D3D11DepthStencilStateCore::~D3D11DepthStencilStateCore()
@@ -17,7 +17,7 @@ namespace BansheeEngine
 		BS_INC_RENDER_STAT_CAT(ResDestroyed, RenderStatObject_DepthStencilState);
 	}
 
-	void D3D11DepthStencilStateCore::initialize()
+	void D3D11DepthStencilStateCore::createInternal()
 	{
 		D3D11_DEPTH_STENCIL_DESC depthStencilState;
 		ZeroMemory(&depthStencilState, sizeof(D3D11_DEPTH_STENCIL_DESC));
@@ -49,6 +49,6 @@ namespace BansheeEngine
 
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_DepthStencilState);
 
-		DepthStencilStateCore::initialize();
+		DepthStencilStateCore::createInternal();
 	}
 }

+ 4 - 4
BansheeD3D11RenderAPI/Source/BsD3D11RasterizerState.cpp

@@ -6,8 +6,8 @@
 
 namespace BansheeEngine
 {
-	D3D11RasterizerStateCore::D3D11RasterizerStateCore(const RASTERIZER_STATE_DESC& desc)
-		:RasterizerStateCore(desc), mRasterizerState(nullptr)
+	D3D11RasterizerStateCore::D3D11RasterizerStateCore(const RASTERIZER_STATE_DESC& desc, UINT32 id)
+		:RasterizerStateCore(desc, id), mRasterizerState(nullptr)
 	{ }
 
 	D3D11RasterizerStateCore::~D3D11RasterizerStateCore()
@@ -17,7 +17,7 @@ namespace BansheeEngine
 		BS_INC_RENDER_STAT_CAT(ResDestroyed, RenderStatObject_RasterizerState);
 	}
 
-	void D3D11RasterizerStateCore::initialize()
+	void D3D11RasterizerStateCore::createInternal()
 	{
 		INT32 scaledDepthBias = Math::floorToInt(-mProperties.getDepthBias() * float((1 << 24))); // Note: Assumes 24-bit depth buffer
 
@@ -46,6 +46,6 @@ namespace BansheeEngine
 		}
 
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_RasterizerState);
-		RasterizerStateCore::initialize();
+		RasterizerStateCore::createInternal();
 	}
 }

+ 6 - 6
BansheeD3D11RenderAPI/Source/BsD3D11RenderStateManager.cpp

@@ -14,25 +14,25 @@ namespace BansheeEngine
 		return ret;
 	}
 
-	SPtr<BlendStateCore> D3D11RenderStateCoreManager::createBlendStateInternal(const BLEND_STATE_DESC& desc) const
+	SPtr<BlendStateCore> D3D11RenderStateCoreManager::createBlendStateInternal(const BLEND_STATE_DESC& desc, UINT32 id) const
 	{
-		SPtr<BlendStateCore> ret = bs_shared_ptr<D3D11BlendStateCore>(new (bs_alloc<D3D11BlendStateCore>()) D3D11BlendStateCore(desc));
+		SPtr<BlendStateCore> ret = bs_shared_ptr<D3D11BlendStateCore>(new (bs_alloc<D3D11BlendStateCore>()) D3D11BlendStateCore(desc, id));
 		ret->_setThisPtr(ret);
 
 		return ret;
 	}
 
-	SPtr<RasterizerStateCore> D3D11RenderStateCoreManager::createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc) const
+	SPtr<RasterizerStateCore> D3D11RenderStateCoreManager::createRasterizerStateInternal(const RASTERIZER_STATE_DESC& desc, UINT32 id) const
 	{
-		SPtr<RasterizerStateCore> ret = bs_shared_ptr<D3D11RasterizerStateCore>(new (bs_alloc<D3D11RasterizerStateCore>()) D3D11RasterizerStateCore(desc));
+		SPtr<RasterizerStateCore> ret = bs_shared_ptr<D3D11RasterizerStateCore>(new (bs_alloc<D3D11RasterizerStateCore>()) D3D11RasterizerStateCore(desc, id));
 		ret->_setThisPtr(ret);
 
 		return ret;
 	}
 
-	SPtr<DepthStencilStateCore> D3D11RenderStateCoreManager::createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc) const
+	SPtr<DepthStencilStateCore> D3D11RenderStateCoreManager::createDepthStencilStateInternal(const DEPTH_STENCIL_STATE_DESC& desc, UINT32 id) const
 	{
-		SPtr<DepthStencilStateCore> ret = bs_shared_ptr<D3D11DepthStencilStateCore>(new (bs_alloc<D3D11DepthStencilStateCore>()) D3D11DepthStencilStateCore(desc));
+		SPtr<DepthStencilStateCore> ret = bs_shared_ptr<D3D11DepthStencilStateCore>(new (bs_alloc<D3D11DepthStencilStateCore>()) D3D11DepthStencilStateCore(desc, id));
 		ret->_setThisPtr(ret);
 
 		return ret;

+ 2 - 2
BansheeD3D11RenderAPI/Source/BsD3D11SamplerState.cpp

@@ -17,7 +17,7 @@ namespace BansheeEngine
 		BS_INC_RENDER_STAT_CAT(ResDestroyed, RenderStatObject_SamplerState);
 	}
 
-	void D3D11SamplerStateCore::initialize()
+	void D3D11SamplerStateCore::createInternal()
 	{
 		D3D11_SAMPLER_DESC samplerState;
 		ZeroMemory(&samplerState, sizeof(D3D11_SAMPLER_DESC));
@@ -104,6 +104,6 @@ namespace BansheeEngine
 
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_SamplerState);
 
-		SamplerStateCore::initialize();
+		SamplerStateCore::createInternal();
 	}
 }

+ 0 - 7
TODOExperimentation.txt

@@ -30,11 +30,6 @@ Make GUI and Overlay render separately without using the main render queue
 Make scene grid rendering more akin to handle & gizmo rendering so I can remove the onRenderViewport callback
  - Similar thing with dock manager
 
-Add material flag "transparent". 
- - Priority is always applied within its transparent/opaque queue. Priority and sort order are kept as is. 
- - Transparent flag just determines the rendering method. Later I can probably also add "animated" and similar.
- - Depending on set flag populate two different render queues per camera (+ a special render queue for GUI and overlay)
-
 Rendering procedure should be:
  - For each camera go over each renderable and determine if their layers match
  - If they match do frustum culling
@@ -68,8 +63,6 @@ Light queues:
 
 --------------------------- DESIGN ---------------------------
 
-Issue with state caching: State caching doesn't work when deserializing
-
 How will cameras interact with the renderer? The cameras currently available shouldn't have depth buffers
  - Need to modify RenderWindow so it doesn't create depth buffers
   - Find all places where I create windows and modify this