Browse Source

MaterialParams now hold a pointer to their data to avoid excessive allocations when copying them around
Profiler overlay now caches unused GUI elements to reduce allocations

Marko Pintera 10 years ago
parent
commit
e9db368a3d

+ 10 - 10
BansheeCore/Include/BsMaterialParam.h

@@ -15,7 +15,7 @@ namespace BansheeEngine
 	class BS_CORE_EXPORT TMaterialDataParam
 	{
 	public:
-		TMaterialDataParam(const Vector<TGpuDataParam<T, Core>>& params);
+		TMaterialDataParam(const SPtr<Vector<TGpuDataParam<T, Core>>>& params);
 		TMaterialDataParam() { }
 		
 		/**
@@ -29,7 +29,7 @@ namespace BansheeEngine
 		T get(UINT32 arrayIdx = 0);
 
 	protected:
-		Vector<TGpuDataParam<T, Core>> mParams;
+		SPtr<Vector<TGpuDataParam<T, Core>>> mParams;
 	};
 
 	/**
@@ -39,7 +39,7 @@ namespace BansheeEngine
 	class BS_CORE_EXPORT TMaterialParamStruct
 	{
 	public:
-		TMaterialParamStruct(const Vector<TGpuParamStruct<Core>>& params);
+		TMaterialParamStruct(const SPtr<Vector<TGpuParamStruct<Core>>>& params);
 		TMaterialParamStruct() { }
 
 		/**
@@ -58,7 +58,7 @@ namespace BansheeEngine
 		UINT32 getElementSize() const;
 
 	protected:
-		Vector<TGpuParamStruct<Core>> mParams;
+		SPtr<Vector<TGpuParamStruct<Core>>> mParams;
 	};
 
 	/**
@@ -70,7 +70,7 @@ namespace BansheeEngine
 	public:
 		typedef typename TGpuParamTextureType<Core>::Type TextureType;
 
-		TMaterialParamTexture(const Vector<TGpuParamTexture<Core>>& params);
+		TMaterialParamTexture(const SPtr<Vector<TGpuParamTexture<Core>>>& params);
 		TMaterialParamTexture() { }
 
 		/**
@@ -84,7 +84,7 @@ namespace BansheeEngine
 		TextureType get();
 
 	protected:
-		Vector<TGpuParamTexture<Core>> mParams;
+		SPtr<Vector<TGpuParamTexture<Core>>> mParams;
 	};
 
 	/**
@@ -96,7 +96,7 @@ namespace BansheeEngine
 	public:
 		typedef typename TGpuParamTextureType<Core>::Type TextureType;
 
-		TMaterialParamLoadStoreTexture(const Vector<TGpuParamLoadStoreTexture<Core>>& params);
+		TMaterialParamLoadStoreTexture(const SPtr<Vector<TGpuParamLoadStoreTexture<Core>>>& params);
 		TMaterialParamLoadStoreTexture() { }
 
 		/**
@@ -110,7 +110,7 @@ namespace BansheeEngine
 		TextureType get();
 
 	protected:
-		Vector<TGpuParamLoadStoreTexture<Core>> mParams;
+		SPtr<Vector<TGpuParamLoadStoreTexture<Core>>> mParams;
 	};
 
 	/**
@@ -122,7 +122,7 @@ namespace BansheeEngine
 	public:
 		typedef typename TGpuParamSamplerStateType<Core>::Type SamplerType;
 
-		TMaterialParamSampState(const Vector<TGpuParamSampState<Core>>& params);
+		TMaterialParamSampState(const SPtr<Vector<TGpuParamSampState<Core>>>& params);
 		TMaterialParamSampState() { }
 
 		/**
@@ -136,7 +136,7 @@ namespace BansheeEngine
 		SamplerType get();
 
 	protected:
-		Vector<TGpuParamSampState<Core>> mParams;
+		SPtr<Vector<TGpuParamSampState<Core>>> mParams;
 	};
 
 	typedef TMaterialDataParam<float, false> MaterialParamFloat;

+ 15 - 15
BansheeCore/Source/BsMaterial.cpp

@@ -484,7 +484,7 @@ namespace BansheeEngine
 		}
 
 		const String& gpuVarName = iterFind->second;
-		Vector<TGpuParamStruct<Core>> gpuParams;
+		SPtr<Vector<TGpuParamStruct<Core>>> gpuParams = bs_shared_ptr<Vector<TGpuParamStruct<Core>>>();
 
 		for (auto iter = mParametersPerPass.begin(); iter != mParametersPerPass.end(); ++iter)
 		{
@@ -497,8 +497,8 @@ namespace BansheeEngine
 				{
 					if (paramPtr->hasParam(gpuVarName))
 					{
-						gpuParams.push_back(TGpuParamStruct<Core>());
-						paramPtr->getStructParam(gpuVarName, gpuParams.back());
+						gpuParams->push_back(TGpuParamStruct<Core>());
+						paramPtr->getStructParam(gpuVarName, gpuParams->back());
 					}
 				}
 			}
@@ -520,7 +520,7 @@ namespace BansheeEngine
 		}
 
 		const String& gpuVarName = iterFind->second;
-		Vector<TGpuParamTexture<Core>> gpuParams;
+		SPtr<Vector<TGpuParamTexture<Core>>> gpuParams = bs_shared_ptr<Vector<TGpuParamTexture<Core>>>();
 
 		for (auto iter = mParametersPerPass.begin(); iter != mParametersPerPass.end(); ++iter)
 		{
@@ -533,8 +533,8 @@ namespace BansheeEngine
 				{
 					if (paramPtr->hasTexture(gpuVarName))
 					{
-						gpuParams.push_back(TGpuParamTexture<Core>());
-						paramPtr->getTextureParam(gpuVarName, gpuParams.back());
+						gpuParams->push_back(TGpuParamTexture<Core>());
+						paramPtr->getTextureParam(gpuVarName, gpuParams->back());
 					}
 				}
 			}
@@ -556,7 +556,7 @@ namespace BansheeEngine
 		}
 
 		const String& gpuVarName = iterFind->second;
-		Vector<TGpuParamLoadStoreTexture<Core>> gpuParams;
+		SPtr<Vector<TGpuParamLoadStoreTexture<Core>>> gpuParams = bs_shared_ptr<Vector<TGpuParamLoadStoreTexture<Core>>>();
 
 		for (auto iter = mParametersPerPass.begin(); iter != mParametersPerPass.end(); ++iter)
 		{
@@ -569,8 +569,8 @@ namespace BansheeEngine
 				{
 					if (paramPtr->hasTexture(gpuVarName))
 					{
-						gpuParams.push_back(TGpuParamLoadStoreTexture<Core>());
-						paramPtr->getLoadStoreTextureParam(gpuVarName, gpuParams.back());
+						gpuParams->push_back(TGpuParamLoadStoreTexture<Core>());
+						paramPtr->getLoadStoreTextureParam(gpuVarName, gpuParams->back());
 					}
 				}
 			}
@@ -592,7 +592,7 @@ namespace BansheeEngine
 		}
 
 		const String& gpuVarName = iterFind->second;
-		Vector<TGpuParamSampState<Core>> gpuParams;
+		SPtr<Vector<TGpuParamSampState<Core>>> gpuParams = bs_shared_ptr<Vector<TGpuParamSampState<Core>>>();
 		for (auto iter = mParametersPerPass.begin(); iter != mParametersPerPass.end(); ++iter)
 		{
 			SPtr<TPassParameters<Core>> params = *iter;
@@ -604,8 +604,8 @@ namespace BansheeEngine
 				{
 					if (paramPtr->hasSamplerState(gpuVarName))
 					{
-						gpuParams.push_back(TGpuParamSampState<Core>());
-						paramPtr->getSamplerStateParam(gpuVarName, gpuParams.back());
+						gpuParams->push_back(TGpuParamSampState<Core>());
+						paramPtr->getSamplerStateParam(gpuVarName, gpuParams->back());
 					}
 				}
 			}
@@ -896,7 +896,7 @@ namespace BansheeEngine
 		}
 
 		const String& gpuVarName = iterFind->second;
-		Vector<TGpuDataParam<T, Core>> gpuParams;
+		SPtr<Vector<TGpuDataParam<T, Core>>> gpuParams = bs_shared_ptr<Vector<TGpuDataParam<T, Core>>>();
 
 		for (auto iter = mParametersPerPass.begin(); iter != mParametersPerPass.end(); ++iter)
 		{
@@ -909,8 +909,8 @@ namespace BansheeEngine
 				{
 					if (paramPtr->hasParam(gpuVarName))
 					{
-						gpuParams.push_back(TGpuDataParam<T, Core>());
-						paramPtr->getParam<T>(gpuVarName, gpuParams.back());
+						gpuParams->push_back(TGpuDataParam<T, Core>());
+						paramPtr->getParam<T>(gpuVarName, gpuParams->back());
 					}
 				}
 			}

+ 22 - 22
BansheeCore/Source/BsMaterialParam.cpp

@@ -5,120 +5,120 @@
 namespace BansheeEngine
 {
 	template<class T, bool Core>
-	TMaterialDataParam<T, Core>::TMaterialDataParam(const Vector<TGpuDataParam<T, Core>>& params)
+	TMaterialDataParam<T, Core>::TMaterialDataParam(const SPtr<Vector<TGpuDataParam<T, Core>>>& params)
 		:mParams(params)
 	{ }
 
 	template<class T, bool Core>
 	void TMaterialDataParam<T, Core>::set(const T& value, UINT32 arrayIdx)
 	{
-		for (auto& param : mParams)
+		for (auto& param : *mParams)
 			param.set(value, arrayIdx);
 	}
 
 	template<class T, bool Core>
 	T TMaterialDataParam<T, Core>::get(UINT32 arrayIdx)
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 			return T();
 
-		return mParams[0].get(arrayIdx); // They should all have the same value
+		return (*mParams)[0].get(arrayIdx); // They should all have the same value
 	}
 
 	template<bool Core>
-	TMaterialParamStruct<Core>::TMaterialParamStruct(const Vector<TGpuParamStruct<Core>>& params)
+	TMaterialParamStruct<Core>::TMaterialParamStruct(const SPtr<Vector<TGpuParamStruct<Core>>>& params)
 		:mParams(params)
 	{ }
 
 	template<bool Core>
 	void TMaterialParamStruct<Core>::set(const void* value, UINT32 sizeBytes, UINT32 arrayIdx)
 	{
-		for (auto& param : mParams)
+		for (auto& param : *mParams)
 			param.set(value, sizeBytes, arrayIdx);
 	}
 
 	template<bool Core>
 	void TMaterialParamStruct<Core>::get(void* value, UINT32 sizeBytes, UINT32 arrayIdx)
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 		{
 			value = nullptr;
 			return;
 		}
 
-		return mParams[0].get(value, sizeBytes, arrayIdx); // They should all have the same value
+		return (*mParams)[0].get(value, sizeBytes, arrayIdx); // They should all have the same value
 	}
 
 	template<bool Core>
 	UINT32 TMaterialParamStruct<Core>::getElementSize() const
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 			return 0;
 
-		return mParams[0].getElementSize();
+		return (*mParams)[0].getElementSize();
 	}
 
 	template<bool Core>
-	TMaterialParamTexture<Core>::TMaterialParamTexture(const Vector<TGpuParamTexture<Core>>& params)
+	TMaterialParamTexture<Core>::TMaterialParamTexture(const SPtr<Vector<TGpuParamTexture<Core>>>& params)
 		:mParams(params)
 	{ }
 
 	template<bool Core>
 	void TMaterialParamTexture<Core>::set(const TextureType& texture)
 	{
-		for (auto& param : mParams)
+		for (auto& param : *mParams)
 			param.set(texture);
 	}
 
 	template<bool Core>
 	typename TMaterialParamTexture<Core>::TextureType TMaterialParamTexture<Core>::get()
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 			return TextureType();
 
-		return mParams[0].get(); // They should all have the same value
+		return (*mParams)[0].get(); // They should all have the same value
 	}
 
 	template<bool Core>
-	TMaterialParamLoadStoreTexture<Core>::TMaterialParamLoadStoreTexture(const Vector<TGpuParamLoadStoreTexture<Core>>& params)
+	TMaterialParamLoadStoreTexture<Core>::TMaterialParamLoadStoreTexture(const SPtr<Vector<TGpuParamLoadStoreTexture<Core>>>& params)
 		:mParams(params)
 	{ }
 
 	template<bool Core>
 	void TMaterialParamLoadStoreTexture<Core>::set(const TextureType& texture, const TextureSurface& surface)
 	{
-		for (auto& param : mParams)
+		for (auto& param : *mParams)
 			param.set(texture, surface);
 	}
 
 	template<bool Core>
 	typename TMaterialParamLoadStoreTexture<Core>::TextureType TMaterialParamLoadStoreTexture<Core>::get()
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 			return TextureType();
 
-		return mParams[0].get(); // They should all have the same value
+		return (*mParams)[0].get(); // They should all have the same value
 	}
 
 	template<bool Core>
-	TMaterialParamSampState<Core>::TMaterialParamSampState(const Vector<TGpuParamSampState<Core>>& params)
+	TMaterialParamSampState<Core>::TMaterialParamSampState(const SPtr<Vector<TGpuParamSampState<Core>>>& params)
 		:mParams(params)
 	{ }
 
 	template<bool Core>
 	void TMaterialParamSampState<Core>::set(const SamplerType& sampState)
 	{
-		for (auto& param : mParams)
+		for (auto& param : *mParams)
 			param.set(sampState);
 	}
 
 	template<bool Core>
 	typename TMaterialParamSampState<Core>::SamplerType TMaterialParamSampState<Core>::get()
 	{
-		if (mParams.size() == 0)
+		if (mParams->size() == 0)
 			return SamplerType();
 
-		return mParams[0].get(); // They should all have the same value
+		return (*mParams)[0].get(); // They should all have the same value
 	}
 
 	template class TMaterialDataParam<float, false>;

+ 7 - 7
BansheeEngine/Include/BsGUISpace.h

@@ -36,17 +36,17 @@ namespace BansheeEngine
 		/**
 		 * @copydoc	GUIElementBase::_getOptimalSize
 		 */
-		virtual Vector2I _getOptimalSize() const { return Vector2I(getSize(), getSize()); }
+		virtual Vector2I _getOptimalSize() const override { return Vector2I(getSize(), getSize()); }
 
 		/**
 		 * @copydoc	GUIElementBase::_calculateLayoutSizeRange
 		 */
-		virtual LayoutSizeRange _calculateLayoutSizeRange() const;
+		virtual LayoutSizeRange _calculateLayoutSizeRange() const override;
 
 		/**
 		 * @copydoc	GUIElementBase::_getPadding
 		 */
-		virtual const RectOffset& _getPadding() const 
+		virtual const RectOffset& _getPadding() const  override
 		{
 			static RectOffset padding;
 
@@ -86,22 +86,22 @@ namespace BansheeEngine
 		/**
 		 * @copydoc	GUIElementBase::_getType
 		 */
-		Type _getType() const { return GUIElementBase::Type::FlexibleSpace; }
+		Type _getType() const override { return GUIElementBase::Type::FlexibleSpace; }
 
 		/**
 		 * @copydoc	GUIElementBase::_getOptimalSize
 		 */
-		virtual Vector2I _getOptimalSize() const { return Vector2I(0, 0); }
+		virtual Vector2I _getOptimalSize() const override { return Vector2I(0, 0); }
 
 		/**
 		 * @copydoc	GUIElementBase::_calculateLayoutSizeRange
 		 */
-		virtual LayoutSizeRange _calculateLayoutSizeRange() const;
+		virtual LayoutSizeRange _calculateLayoutSizeRange() const override;
 
 		/**
 		 * @copydoc	GUIElementBase::_getPadding
 		 */
-		virtual const RectOffset& _getPadding() const 
+		virtual const RectOffset& _getPadding() const override
 		{
 			static RectOffset padding;
 

+ 6 - 0
BansheeEngine/Include/BsProfilerOverlay.h

@@ -93,6 +93,8 @@ namespace BansheeEngine
 			HString totalTime;
 			HString avgTimeSelf;
 			HString totalTimeSelf;
+
+			bool disabled;
 		};
 
 		/**
@@ -115,6 +117,8 @@ namespace BansheeEngine
 			HString totalCycles;
 			HString avgCyclesSelf;
 			HString totalCyclesSelf;
+
+			bool disabled;
 		};
 		
 		/**
@@ -128,6 +132,8 @@ namespace BansheeEngine
 
 			HString name;
 			HString time;
+
+			bool disabled;
 		};
 
 	public:

+ 42 - 11
BansheeEngine/Source/BsProfilerOverlay.cpp

@@ -37,8 +37,12 @@ namespace BansheeEngine
 			{
 				ProfilerOverlayInternal::BasicRow& row = rows[curIdx + i];
 
-				GUILayout::destroy(row.labelLayout);
-				GUILayout::destroy(row.contentLayout);
+				if (!row.disabled)
+				{
+					row.labelLayout->disableRecursively();
+					row.contentLayout->disableRecursively();
+					row.disabled = true;
+				}
 			}
 
 			rows.resize(curIdx);
@@ -53,6 +57,7 @@ namespace BansheeEngine
 
 				ProfilerOverlayInternal::BasicRow& newRow = rows.back();
 
+				newRow.disabled = false;
 				newRow.name = HString(L"{0}");
 				newRow.pctOfParent = HString(L"{0} %");
 				newRow.numCalls = HString(L"{0}");
@@ -101,9 +106,7 @@ namespace BansheeEngine
 			
 			ProfilerOverlayInternal::BasicRow& row = rows[curIdx];
 
-			GUIFixedSpace::destroy(row.labelSpace);
-			row.labelSpace = row.labelLayout->insertNewElement<GUIFixedSpace>(0, depth * 20);
-
+			row.labelSpace->setSize(depth * 20);
 			row.name.setParameter(0, toWString(name));
 			row.pctOfParent.setParameter(0, toWString(pctOfParent * 100.0f, 2, 0, ' ', std::ios::fixed));
 			row.numCalls.setParameter(0, toWString(numCalls));
@@ -114,6 +117,13 @@ namespace BansheeEngine
 			row.avgTimeSelf.setParameter(0, toWString(avgSelfTime, 2, 0, ' ', std::ios::fixed));
 			row.totalTimeSelf.setParameter(0, toWString(totalSelfTime, 2, 0, ' ', std::ios::fixed));
 
+			if (row.disabled)
+			{
+				row.labelLayout->enableRecursively();
+				row.contentLayout->enableRecursively();
+				row.disabled = false;
+			}
+
 			curIdx++;
 		}
 	};
@@ -138,8 +148,12 @@ namespace BansheeEngine
 			{
 				ProfilerOverlayInternal::PreciseRow& row = rows[curIdx + i];
 
-				GUILayout::destroy(row.labelLayout);
-				GUILayout::destroy(row.contentLayout);
+				if (!row.disabled)
+				{
+					row.labelLayout->disableRecursively();
+					row.contentLayout->disableRecursively();
+					row.disabled = true;
+				}
 			}
 
 			rows.resize(curIdx);
@@ -154,6 +168,7 @@ namespace BansheeEngine
 
 				ProfilerOverlayInternal::PreciseRow& newRow = rows.back();
 
+				newRow.disabled = false;
 				newRow.name = HString(L"{0}");
 				newRow.pctOfParent = HString(L"{0}");
 				newRow.numCalls = HString(L"{0}");
@@ -202,9 +217,7 @@ namespace BansheeEngine
 
 			ProfilerOverlayInternal::PreciseRow& row = rows[curIdx];
 
-			GUIFixedSpace::destroy(row.labelSpace);
-			row.labelSpace = row.labelLayout->insertNewElement<GUIFixedSpace>(0, depth * 20);
-
+			row.labelSpace->setSize(depth * 20);
 			row.name.setParameter(0, toWString(name));
 			row.pctOfParent.setParameter(0, toWString(pctOfParent * 100.0f, 2, 0, ' ', std::ios::fixed));
 			row.numCalls.setParameter(0, toWString(numCalls));
@@ -215,6 +228,13 @@ namespace BansheeEngine
 			row.avgCyclesSelf.setParameter(0, toWString(avgSelfCycles));
 			row.totalCyclesSelf.setParameter(0, toWString(totalSelfCycles));
 
+			if (row.disabled)
+			{
+				row.labelLayout->enableRecursively();
+				row.contentLayout->enableRecursively();
+				row.disabled = false;
+			}
+
 			curIdx++;
 		}
 	};
@@ -238,7 +258,11 @@ namespace BansheeEngine
 			{
 				ProfilerOverlayInternal::GPUSampleRow& row = rows[curIdx + i];
 
-				GUILayout::destroy(row.layout);
+				if (!row.disabled)
+				{
+					row.layout->disableRecursively();
+					row.disabled = true;
+				}
 			}
 
 			rows.resize(curIdx);
@@ -252,6 +276,7 @@ namespace BansheeEngine
 
 				ProfilerOverlayInternal::GPUSampleRow& newRow = rows.back();
 
+				newRow.disabled = false;
 				newRow.name = HString(L"{1}");
 				newRow.time = HString(L"{0}");
 
@@ -271,6 +296,12 @@ namespace BansheeEngine
 			row.name.setParameter(0, toWString(name));
 			row.time.setParameter(0, toWString(timeMs));
 
+			if (row.disabled)
+			{
+				row.layout->enableRecursively();
+				row.disabled = false;
+			}
+
 			curIdx++;
 		}
 	};