Browse Source

Added clone() method to material to make it easier to modify individual instances

Marko Pintera 10 years ago
parent
commit
a637a4a168

+ 5 - 0
BansheeCore/Include/BsMaterial.h

@@ -639,6 +639,11 @@ namespace BansheeEngine
 		 */
 		void initialize() override;
 
+		/**
+		 * @brief	Creates a deep copy of the material and returns the new object.
+		 */
+		HMaterial Material::clone();
+
 		/**
 		 * @brief	Creates a new empty material.
 		 * 			

+ 14 - 0
BansheeCore/Source/BsMaterial.cpp

@@ -15,6 +15,7 @@
 #include "BsFrameAlloc.h"
 #include "BsMatrixNxM.h"
 #include "BsVectorNI.h"
+#include "BsMemorySerializer.h"
 
 namespace BansheeEngine
 {
@@ -1248,6 +1249,19 @@ namespace BansheeEngine
 		initializeIfLoaded();
 	}
 
+	HMaterial Material::clone()
+	{
+		UINT32 bufferSize = 0;
+
+		MemorySerializer serializer;
+		UINT8* buffer = serializer.encode(this, bufferSize, (void*(*)(UINT32))&bs_alloc);
+
+		std::shared_ptr<Material> cloneObj = std::static_pointer_cast<Material>(serializer.decode(buffer, bufferSize));
+		bs_free(buffer);
+
+		return static_resource_cast<Material>(gResources()._createResourceHandle(cloneObj));
+	}
+
 	HMaterial Material::create()
 	{
 		MaterialPtr materialPtr = MaterialManager::instance().create();

+ 2 - 2
BansheeEditor/Source/BsGUITreeViewEditBox.cpp

@@ -47,8 +47,8 @@ namespace BansheeEngine
 		}
 		else if(ev.getType() == GUICommandEventType::FocusLost)
 		{
-			if(!onInputCanceled.empty())
-				onInputCanceled();
+			if(!onFocusLost.empty())
+				onFocusLost();
 
 			return true;
 		}

+ 3 - 3
BansheeUtility/Include/BsMemoryAllocator.h

@@ -107,7 +107,7 @@ namespace BansheeEngine
 	 * @brief	Allocates the specified number of bytes.
 	 */
 	template<class Alloc> 
-	inline void* bs_alloc(size_t count)
+	inline void* bs_alloc(UINT32 count)
 	{
 		return MemoryAllocator<Alloc>::allocate(count);
 	}
@@ -183,7 +183,7 @@ namespace BansheeEngine
 	/**
 	 * @brief	Allocates the specified number of bytes.
 	 */
-	inline void* bs_alloc(size_t count)
+	inline void* bs_alloc(UINT32 count)
 	{
 		return MemoryAllocator<GenAlloc>::allocate(count);
 	}
@@ -313,7 +313,7 @@ namespace BansheeEngine
 		 */
 		pointer allocate (size_type num, const void* = 0) 
 		{
-			pointer ret = (pointer)(bs_alloc<Alloc>((size_t)num*sizeof(T)));
+			pointer ret = (pointer)(bs_alloc<Alloc>((UINT32)num*sizeof(T)));
 			return ret;
 		}
 

+ 2 - 2
BansheeUtility/Include/BsStringFormat.h

@@ -231,7 +231,7 @@ namespace BansheeEngine
 				return;
 
 			std::basic_string<char> sourceParam = toString(param);
-			parameters[idx].buffer = (char*)bs_alloc(sourceParam.size() * sizeof(char));
+			parameters[idx].buffer = (char*)bs_alloc((UINT32)sourceParam.size() * sizeof(char));
 			parameters[idx].size = (UINT32)sourceParam.size();
 
 			sourceParam.copy(parameters[idx].buffer, parameters[idx].size, 0);
@@ -250,7 +250,7 @@ namespace BansheeEngine
 				return;
 
 			std::basic_string<wchar_t> sourceParam = toWString(param);
-			parameters[idx].buffer = (wchar_t*)bs_alloc(sourceParam.size() * sizeof(wchar_t));
+			parameters[idx].buffer = (wchar_t*)bs_alloc((UINT32)sourceParam.size() * sizeof(wchar_t));
 			parameters[idx].size = (UINT32)sourceParam.size();
 			
 			sourceParam.copy(parameters[idx].buffer, parameters[idx].size, 0);

+ 4 - 4
BansheeUtility/Source/BsDataStream.cpp

@@ -63,7 +63,7 @@ namespace BansheeEngine
 		// Read the entire buffer - ideally in one read, but if the size of
 		// the buffer is unknown, do multiple fixed size reads.
 		size_t bufSize = (mSize > 0 ? mSize : 4096);
-		std::stringstream::char_type* tempBuffer = (std::stringstream::char_type*)bs_alloc(bufSize);
+		std::stringstream::char_type* tempBuffer = (std::stringstream::char_type*)bs_alloc((UINT32)bufSize);
 
 		// Ensure read from begin of stream
 		seek(0);
@@ -153,7 +153,7 @@ namespace BansheeEngine
 		// Read the entire buffer - ideally in one read, but if the size of
 		// the buffer is unknown, do multiple fixed size reads.
 		size_t bufSize = (mSize > 0 ? mSize : 4096);
-		std::stringstream::char_type* tempBuffer = (std::stringstream::char_type*)bs_alloc(bufSize);
+		std::stringstream::char_type* tempBuffer = (std::stringstream::char_type*)bs_alloc((UINT32)bufSize);
 
 		// Ensure read from begin of stream
 		seek(0);
@@ -238,7 +238,7 @@ namespace BansheeEngine
         // Copy data from incoming stream
         mSize = sourceStream.size();
 
-		mData = (UINT8*)bs_alloc(sizeof(UINT8) * mSize);
+		mData = (UINT8*)bs_alloc((UINT32)mSize);
 		mPos = mData;
 		mEnd = mData + sourceStream.read(mData, mSize);
 
@@ -251,7 +251,7 @@ namespace BansheeEngine
         // Copy data from incoming stream
         mSize = sourceStream->size();
 
-		mData = (UINT8*)bs_alloc(sizeof(UINT8) * mSize);
+		mData = (UINT8*)bs_alloc((UINT32)mSize);
 		mPos = mData;
 		mEnd = mData + sourceStream->read(mData, mSize);
 

+ 8 - 0
MBansheeEngine/Material.cs

@@ -147,6 +147,11 @@ namespace BansheeEngine
             return Internal_GetTextureCube(mCachedPtr, name);
         }
 
+        public Material Clone()
+        {
+            return Internal_Clone(mCachedPtr);
+        }
+
         [MethodImpl(MethodImplOptions.InternalCall)]
         private static extern void Internal_CreateInstance(Material instance, IntPtr shader);
 
@@ -215,5 +220,8 @@ namespace BansheeEngine
 
         [MethodImpl(MethodImplOptions.InternalCall)]
         private static extern TextureCube Internal_GetTextureCube(IntPtr nativeInstance, string name);
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern Material Internal_Clone(IntPtr nativeInstance);
     }
 }

+ 1 - 0
SBansheeEngine/Include/BsScriptMaterial.h

@@ -50,6 +50,7 @@ namespace BansheeEngine
 		/* 								CLR HOOKS						   		*/
 		/************************************************************************/
 		static void internal_CreateInstance(MonoObject* instance, ScriptShader* shader);
+		static MonoObject* internal_Clone(ScriptMaterial* nativeInstance);
 
 		static MonoObject* internal_GetShader(ScriptMaterial* nativeInstance);
 		static void internal_SetShader(ScriptMaterial* nativeInstance, ScriptShader* shader);

+ 11 - 0
SBansheeEngine/Source/BsScriptMaterial.cpp

@@ -22,6 +22,7 @@ namespace BansheeEngine
 	void ScriptMaterial::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptMaterial::internal_CreateInstance);
+		metaData.scriptClass->addInternalCall("Internal_Clone", &ScriptMaterial::internal_Clone);
 
 		metaData.scriptClass->addInternalCall("Internal_GetShader", &ScriptMaterial::internal_GetShader);
 		metaData.scriptClass->addInternalCall("Internal_SetShader", &ScriptMaterial::internal_SetShader);
@@ -64,6 +65,16 @@ namespace BansheeEngine
 		ScriptResourceManager::instance().createScriptResource(instance, material, &scriptInstance);
 	}
 
+	MonoObject* ScriptMaterial::internal_Clone(ScriptMaterial* nativeInstance)
+	{
+		HMaterial clone = nativeInstance->mMaterial->clone();
+
+		ScriptMaterial* scriptClone;
+		ScriptResourceManager::instance().createScriptResource(clone, &scriptClone);
+
+		return scriptClone->getManagedInstance();
+	}
+
 	MonoObject* ScriptMaterial::internal_GetShader(ScriptMaterial* nativeInstance)
 	{
 		HShader shader = nativeInstance->getMaterialHandle()->getShader();