Browse Source

Refactoring ScriptObject so destruction and construction is encapsulated within it

Marko Pintera 11 years ago
parent
commit
ce8ea08d5c
70 changed files with 454 additions and 788 deletions
  1. 3 9
      Inspector.txt
  2. 2 2
      MBansheeEngine/ScriptObject.cs
  3. 5 6
      SBansheeEditor/Include/BsScriptEditorWindow.h
  4. 3 5
      SBansheeEditor/Include/BsScriptGUIFoldout.h
  5. 6 17
      SBansheeEditor/Source/BsScriptEditorWindow.cpp
  6. 10 20
      SBansheeEditor/Source/BsScriptGUIFoldout.cpp
  7. 4 5
      SBansheeEngine/Include/BsScriptComponent.h
  8. 2 2
      SBansheeEngine/Include/BsScriptDebug.h
  9. 2 5
      SBansheeEngine/Include/BsScriptFont.h
  10. 3 5
      SBansheeEngine/Include/BsScriptGUIArea.h
  11. 3 5
      SBansheeEngine/Include/BsScriptGUIButton.h
  12. 3 3
      SBansheeEngine/Include/BsScriptGUIContent.h
  13. 4 6
      SBansheeEngine/Include/BsScriptGUIElementStateStyle.h
  14. 4 41
      SBansheeEngine/Include/BsScriptGUIElementStyle.h
  15. 3 5
      SBansheeEngine/Include/BsScriptGUIFixedSpace.h
  16. 3 5
      SBansheeEngine/Include/BsScriptGUIFlexibleSpace.h
  17. 3 5
      SBansheeEngine/Include/BsScriptGUIInputBox.h
  18. 3 5
      SBansheeEngine/Include/BsScriptGUILabel.h
  19. 3 5
      SBansheeEngine/Include/BsScriptGUILayout.h
  20. 3 5
      SBansheeEngine/Include/BsScriptGUIListBox.h
  21. 2 5
      SBansheeEngine/Include/BsScriptGUIPanel.h
  22. 3 5
      SBansheeEngine/Include/BsScriptGUIScrollArea.h
  23. 3 5
      SBansheeEngine/Include/BsScriptGUITexture.h
  24. 3 5
      SBansheeEngine/Include/BsScriptGUIToggle.h
  25. 2 5
      SBansheeEngine/Include/BsScriptGUIToggleGroup.h
  26. 2 5
      SBansheeEngine/Include/BsScriptHString.h
  27. 36 29
      SBansheeEngine/Include/BsScriptObject.h
  28. 19 0
      SBansheeEngine/Include/BsScriptObjectImpl.h
  29. 3 5
      SBansheeEngine/Include/BsScriptSceneObject.h
  30. 2 6
      SBansheeEngine/Include/BsScriptSerializableArray.h
  31. 2 7
      SBansheeEngine/Include/BsScriptSerializableField.h
  32. 2 6
      SBansheeEngine/Include/BsScriptSerializableObject.h
  33. 4 6
      SBansheeEngine/Include/BsScriptSerializableProperty.h
  34. 3 5
      SBansheeEngine/Include/BsScriptSpriteTexture.h
  35. 2 4
      SBansheeEngine/Include/BsScriptStringTable.h
  36. 3 5
      SBansheeEngine/Include/BsScriptTexture2D.h
  37. 3 0
      SBansheeEngine/SBansheeEngine.vcxproj
  38. 9 0
      SBansheeEngine/SBansheeEngine.vcxproj.filters
  39. 5 15
      SBansheeEngine/Source/BsScriptComponent.cpp
  40. 3 6
      SBansheeEngine/Source/BsScriptDebug.cpp
  41. 4 19
      SBansheeEngine/Source/BsScriptFont.cpp
  42. 10 21
      SBansheeEngine/Source/BsScriptGUIArea.cpp
  43. 10 20
      SBansheeEngine/Source/BsScriptGUIButton.cpp
  44. 3 7
      SBansheeEngine/Source/BsScriptGUIContent.cpp
  45. 6 25
      SBansheeEngine/Source/BsScriptGUIElementStateStyle.cpp
  46. 38 20
      SBansheeEngine/Source/BsScriptGUIElementStyle.cpp
  47. 10 20
      SBansheeEngine/Source/BsScriptGUIFixedSpace.cpp
  48. 10 20
      SBansheeEngine/Source/BsScriptGUIFlexibleSpace.cpp
  49. 10 20
      SBansheeEngine/Source/BsScriptGUIInputBox.cpp
  50. 10 20
      SBansheeEngine/Source/BsScriptGUILabel.cpp
  51. 13 32
      SBansheeEngine/Source/BsScriptGUILayout.cpp
  52. 10 20
      SBansheeEngine/Source/BsScriptGUIListBox.cpp
  53. 3 18
      SBansheeEngine/Source/BsScriptGUIPanel.cpp
  54. 10 20
      SBansheeEngine/Source/BsScriptGUIScrollArea.cpp
  55. 10 20
      SBansheeEngine/Source/BsScriptGUITexture.cpp
  56. 10 20
      SBansheeEngine/Source/BsScriptGUIToggle.cpp
  57. 3 19
      SBansheeEngine/Source/BsScriptGUIToggleGroup.cpp
  58. 2 10
      SBansheeEngine/Source/BsScriptGameObjectManager.cpp
  59. 3 19
      SBansheeEngine/Source/BsScriptHString.cpp
  60. 43 0
      SBansheeEngine/Source/BsScriptObject.cpp
  61. 21 0
      SBansheeEngine/Source/BsScriptObjectImpl.cpp
  62. 2 8
      SBansheeEngine/Source/BsScriptResourceManager.cpp
  63. 7 15
      SBansheeEngine/Source/BsScriptSceneObject.cpp
  64. 3 21
      SBansheeEngine/Source/BsScriptSerializableArray.cpp
  65. 3 20
      SBansheeEngine/Source/BsScriptSerializableField.cpp
  66. 3 20
      SBansheeEngine/Source/BsScriptSerializableObject.cpp
  67. 3 20
      SBansheeEngine/Source/BsScriptSerializableProperty.cpp
  68. 4 12
      SBansheeEngine/Source/BsScriptSpriteTexture.cpp
  69. 3 5
      SBansheeEngine/Source/BsScriptStringTable.cpp
  70. 4 12
      SBansheeEngine/Source/BsScriptTexture2D.cpp

+ 3 - 9
Inspector.txt

@@ -1,13 +1,7 @@
 
-Add SerializableField.GetProperty
- - Also GetObject & GetArray
- - Remove existing GetValue/SetValue
-
-Do the same for SerializableObject/SerializableArray, etc.
-
- ------------------------------------------------
-
-Add ability to create InspectableObject directly from "object".
+Port all remaining Script* classes to new ScriptObject system
+GUIElement script objects need to be fixed to have a common base class. Currently I'm trying to implement an internal method in specific Script  types, but that method only exists on GUIElement.
+When I change an object in InspectableObject field I probably need to rebuild entire GUI hierarchy for that object. Right now I'm not.
 
 -----------------------------------------------
 LESS IMPORTANT

+ 2 - 2
MBansheeEngine/ScriptObject.cs

@@ -9,10 +9,10 @@ namespace BansheeEngine
 
         ~ScriptObject()
         {
-            Internal_DestroyInstance(mCachedPtr);
+            Internal_ManagedInstanceDeleted(mCachedPtr);
         }
 
         [MethodImpl(MethodImplOptions.InternalCall)]
-        private static extern void Internal_DestroyInstance(IntPtr nativeInstance);
+        private static extern void Internal_ManagedInstanceDeleted(IntPtr nativeInstance);
     }
 }

+ 5 - 6
SBansheeEditor/Include/BsScriptEditorWindow.h

@@ -16,22 +16,19 @@ namespace BansheeEngine
 			ScriptEditorWindow* nativeObj;
 		};
 	public:
+		SCRIPT_OBJ(BansheeEditorAssemblyName, "BansheeEditor", "EditorWindow")
+
 		~ScriptEditorWindow();
 
 		EditorWidgetBase* getEditorWidget() const { return mEditorWidget; }
 
-		static void initMetaData();
-
 		static void registerManagedEditorWindows();
 	private:
 		friend class ScriptEditorWidget;
 
-		ScriptEditorWindow(const String& windowName, const String& displayName, EditorWidgetBase* editorWidget);
+		ScriptEditorWindow(MonoObject* instance, const String& windowName, const String& displayName, EditorWidgetBase* editorWidget);
 
 		static MonoObject* internal_createOrGetInstance(MonoString* ns, MonoString* typeName);
-		static void internal_destroyInstance(ScriptEditorWindow* thisPtr);
-
-		static void initRuntimeData();
 
 		static UINT32 internal_getWidth(ScriptEditorWindow* thisPtr);
 		static UINT32 internal_getHeight(ScriptEditorWindow* thisPtr);
@@ -42,6 +39,8 @@ namespace BansheeEngine
 		void onWidgetResized(UINT32 width, UINT32 height);
 		void onWidgetParentChanged(EditorWidgetContainer* newParent);
 
+		void _onManagedInstanceDeleted();
+
 		String mName;
 		EditorWidgetBase* mEditorWidget;
 		Vector<ScriptGUIPanel*>::type mPanels;

+ 3 - 5
SBansheeEditor/Include/BsScriptGUIFoldout.h

@@ -8,26 +8,24 @@ namespace BansheeEngine
 	class BS_SCR_BED_EXPORT ScriptGUIFoldout : public ScriptObject<ScriptGUIFoldout>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEditorAssemblyName, "BansheeEditor", "GUIFoldout")
 
 		GUIFoldout* getInternalValue() const { return mFoldout; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIFoldout* nativeInstance);
 		static void internal_setContent(ScriptGUIFoldout* nativeInstance, MonoObject* content);
 
 		static void internal_destroy(ScriptGUIFoldout* nativeInstance);
 		static void internal_setVisible(ScriptGUIFoldout* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIFoldout* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
 		static void onToggled(MonoObject* instance, bool expanded);
 
-		ScriptGUIFoldout(GUIFoldout* foldout);
+		ScriptGUIFoldout(MonoObject* instance, GUIFoldout* foldout);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIFoldout* mFoldout;
 		bool mIsDestroyed;

+ 6 - 17
SBansheeEditor/Source/BsScriptEditorWindow.cpp

@@ -18,8 +18,8 @@ namespace BansheeEngine
 	UnorderedMap<String, ScriptEditorWindow::EditorWindowHandle>::type ScriptEditorWindow::OpenScriptEditorWindows;
 	MonoMethod* ScriptEditorWindow::onResizedMethod = nullptr;
 
-	ScriptEditorWindow::ScriptEditorWindow(const String& windowName, const String& displayName, EditorWidgetBase* editorWidget)
-		:mName(windowName), mEditorWidget(editorWidget)
+	ScriptEditorWindow::ScriptEditorWindow(MonoObject* instance, const String& windowName, const String& displayName, EditorWidgetBase* editorWidget)
+		:ScriptObject(instance), mName(windowName), mEditorWidget(editorWidget)
 	{
 		mOnWidgetMovedConn = editorWidget->onMoved.connect(std::bind(&ScriptEditorWindow::onWidgetMoved, this, _1, _2));
 		mOnWidgetResizedConn = editorWidget->onResized.connect(std::bind(&ScriptEditorWindow::onWidgetResized, this, _1, _2));
@@ -34,17 +34,9 @@ namespace BansheeEngine
 		mOnParentChangedConn.disconnect();
 	}
 
-	void ScriptEditorWindow::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEditorAssemblyName, "BansheeEditor", "EditorWindow", &ScriptEditorWindow::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptEditorWindow::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateOrGetInstance", &ScriptEditorWindow::internal_createOrGetInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptEditorWindow::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_InitializeGUIPanel", &ScriptEditorWindow::internal_initializeGUIPanel);
 		metaData.scriptClass->addInternalCall("Internal_GetWidth", &ScriptEditorWindow::internal_getWidth);
 		metaData.scriptClass->addInternalCall("Internal_GetHeight", &ScriptEditorWindow::internal_getHeight);
@@ -71,10 +63,10 @@ namespace BansheeEngine
 		return nullptr;
 	}
 
-	void ScriptEditorWindow::internal_destroyInstance(ScriptEditorWindow* thisPtr)
+	void ScriptEditorWindow::_onManagedInstanceDeleted()
 	{
 #if CM_DEBUG_MODE
-		auto iterFind = OpenScriptEditorWindows.find(thisPtr->mName);
+		auto iterFind = OpenScriptEditorWindows.find(mName);
 
 		// It is assumed that this method will only be called after "unregisterScriptEditorWindow" is called,
 		// since that is the only place keeping a reference to the managed editor window. So if window was
@@ -82,7 +74,7 @@ namespace BansheeEngine
 		assert(iterFind == OpenScriptEditorWindows.end());
 #endif
 
-		cm_delete(thisPtr);
+		ScriptObject::_onManagedInstanceDeleted();
 	}
 
 	UINT32 ScriptEditorWindow::internal_getWidth(ScriptEditorWindow* thisPtr)
@@ -179,10 +171,7 @@ namespace BansheeEngine
 		String displayName = MonoManager::instance().getTypeName(editorWindowInstance);
 
 		ScriptEditorWidget* editorWidget = cm_new<ScriptEditorWidget>(windowFullTypeName, HString(toWString(displayName)), parentContainer);
-		ScriptEditorWindow* nativeInstance = new (cm_alloc<ScriptEditorWindow>()) ScriptEditorWindow(windowFullTypeName, displayName, editorWidget);
-		nativeInstance->createInstance(editorWindowInstance);
-
-		metaData.thisPtrField->setValue(editorWindowInstance, &nativeInstance);
+		ScriptEditorWindow* nativeInstance = new (cm_alloc<ScriptEditorWindow>()) ScriptEditorWindow(editorWindowInstance, windowFullTypeName, displayName, editorWidget);
 
 		ScriptEditorWindow::registerScriptEditorWindow(nativeInstance);
 

+ 10 - 20
SBansheeEditor/Source/BsScriptGUIFoldout.cpp

@@ -22,23 +22,15 @@ namespace BansheeEngine
 {
 	ScriptGUIFoldout::OnToggledThunkDef ScriptGUIFoldout::onToggledThunk;
 
-	ScriptGUIFoldout::ScriptGUIFoldout(GUIFoldout* foldout)
-		:mFoldout(foldout), mIsDestroyed(false)
+	ScriptGUIFoldout::ScriptGUIFoldout(MonoObject* instance, GUIFoldout* foldout)
+		:ScriptObject(instance), mFoldout(foldout), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIFoldout::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEditorAssemblyName, "BansheeEditor", "GUIFoldout", &ScriptGUIFoldout::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIFoldout::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIFoldout::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIFoldout::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetContent", &ScriptGUIFoldout::internal_setContent);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIFoldout::internal_destroy);
@@ -59,6 +51,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIFoldout::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIFoldout::internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions)
 	{
 		GUIOptions options;
@@ -72,10 +71,7 @@ namespace BansheeEngine
 
 		guiFoldout->onStateChanged.connect(std::bind(&ScriptGUIFoldout::onToggled, instance, _1));
 
-		ScriptGUIFoldout* nativeInstance = new (cm_alloc<ScriptGUIFoldout>()) ScriptGUIFoldout(guiFoldout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIFoldout* nativeInstance = new (cm_alloc<ScriptGUIFoldout>()) ScriptGUIFoldout(instance, guiFoldout);
 	}
 
 	void ScriptGUIFoldout::internal_setContent(ScriptGUIFoldout* nativeInstance, MonoObject* content)
@@ -90,12 +86,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUIFoldout::internal_destroyInstance(ScriptGUIFoldout* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUIFoldout::internal_setVisible(ScriptGUIFoldout* nativeInstance, bool visible)
 	{
 		if(visible)

+ 4 - 5
SBansheeEngine/Include/BsScriptComponent.h

@@ -10,7 +10,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptComponent : public ScriptGameObject, public ScriptObject<ScriptComponent>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "Component")
 
 		virtual HGameObject getNativeHandle() const { return mManagedComponent; }
 		virtual void setNativeHandle(const HGameObject& gameObject);
@@ -22,13 +22,12 @@ namespace BansheeEngine
 		static MonoObject* internal_getComponent(MonoObject* parentSceneObject, MonoReflectionType* type);
 		static MonoArray* internal_getComponents(MonoObject* parentSceneObject);
 		static void internal_removeComponent(MonoObject* parentSceneObject, MonoReflectionType* type);
-		static void internal_destroyInstance(ScriptComponent* nativeInstance);
 
-		static void initRuntimeData();
-
-		ScriptComponent(const GameObjectHandle<ManagedComponent>& managedComponent);
+		ScriptComponent(MonoObject* instance, const GameObjectHandle<ManagedComponent>& managedComponent);
 		~ScriptComponent() {}
 
+		void _onManagedInstanceDeleted();
+
 		GameObjectHandle<ManagedComponent> mManagedComponent;
 	};
 }

+ 2 - 2
SBansheeEngine/Include/BsScriptDebug.h

@@ -8,13 +8,13 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptDebug : public ScriptObject<ScriptDebug>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "Debug")
 
 	private:
 		static void internal_log(MonoString* message);
 		static void internal_logWarning(MonoString* message);
 		static void internal_logError(MonoString* message);
 
-		static void initRuntimeData();
+		ScriptDebug(MonoObject* instance);
 	};
 }

+ 2 - 5
SBansheeEngine/Include/BsScriptFont.h

@@ -9,18 +9,15 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptFont : public ScriptObject<ScriptFont>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "Font")
 
 		void* getNativeRaw() const;
 		const HFont& getInternalValue() const { return mFont; }
 
 	private:
 		static void internal_createInstanceExternal(MonoObject* instance, const HFont& font);
-		static void internal_destroyInstance(ScriptFont* nativeInstance);
 
-		static void initRuntimeData();
-
-		ScriptFont(const HFont& font);
+		ScriptFont(MonoObject* instance, const HFont& font);
 
 		HFont mFont;
 	};

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIArea.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIArea : public ScriptObject<ScriptGUIArea>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIArea")
 
 		GUIArea* getInternalValue() const { return mGUIArea; }
 		void* getNativeRaw() const { return mGUIArea; }
@@ -18,17 +18,15 @@ namespace BansheeEngine
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* parentGUI, INT32 x, INT32 y, UINT32 width, UINT32 height, UINT16 depth);
-		static void internal_destroyInstance(ScriptGUIArea* nativeInstance);
 
 		static void internal_destroy(ScriptGUIArea* thisPtr);
 		static void internal_setVisible(ScriptGUIArea* thisPtr, bool visible);
 		static void internal_setArea(ScriptGUIArea* thisPtr, INT32 x, INT32 y, UINT32 width, UINT32 height, UINT16 depth);
 
-		static void initRuntimeData();
-
-		ScriptGUIArea(GUIArea* area, ScriptGUIPanel* panel);
+		ScriptGUIArea(MonoObject* instance, GUIArea* area, ScriptGUIPanel* panel);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIArea* mGUIArea;
 		RectI mArea;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIButton.h

@@ -8,29 +8,27 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIButton : public ScriptObject<ScriptGUIButton>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIButton")
 
 		GUIButton* getInternalValue() const { return mButton; }
 		void* getNativeRaw() const { return mButton; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIButton* nativeInstance);
 		static void internal_setContent(ScriptGUIButton* nativeInstance, MonoObject* content);
 
 		static void internal_destroy(ScriptGUIButton* nativeInstance);
 		static void internal_setVisible(ScriptGUIButton* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIButton* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
 		static void onClick(MonoObject* instance);
 		static void onHover(MonoObject* instance);
 		static void onOut(MonoObject* instance);
 
-		ScriptGUIButton(GUIButton* button);
+		ScriptGUIButton(MonoObject* instance, GUIButton* button);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIButton* mButton;
 		bool mIsDestroyed;

+ 3 - 3
SBansheeEngine/Include/BsScriptGUIContent.h

@@ -8,17 +8,17 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIContent : public ScriptObject<ScriptGUIContent>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIContent")
 
 		static const HString& getText(MonoObject* instance);
 		static const HString& getTooltip(MonoObject* instance);
 		static HSpriteTexture getImage(MonoObject* instance);
 
 	private:
-		static void initRuntimeData();
-
 		static MonoField* mTextField;
 		static MonoField* mTooltipField;
 		static MonoField* mImageField;
+
+		ScriptGUIContent(MonoObject* instance);
 	};
 }

+ 4 - 6
SBansheeEngine/Include/BsScriptGUIElementStateStyle.h

@@ -12,23 +12,21 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIElementStateStyle : public ScriptObject<ScriptGUIElementStateStyle>
 	{
 	public:
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIElementStateStyle")
+
 		~ScriptGUIElementStateStyle();
 
-		static void initMetaData();
 		GUIElementStyle::GUIElementStateStyle getInternalValue() const { return *mElementStateStyle; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance);
 		static void internal_createInstanceExternal(MonoObject* instance, GUIElementStyle::GUIElementStateStyle* externalStateStyle);
-		static void internal_destroyInstance(ScriptGUIElementStateStyle* nativeInstance);
-
-		static void initRuntimeData();
 
 		CM_SCRIPT_GETSET_OBJECT_SHRDPTR(ScriptGUIElementStateStyle, ScriptSpriteTexture, Texture, mElementStateStyle->texture, mSpriteTexture);
 		CM_SCRIPT_GETSET_VALUE_REF(ScriptGUIElementStateStyle, Color, TextColor, mElementStateStyle->textColor);
 
-		ScriptGUIElementStateStyle();
-		ScriptGUIElementStateStyle(GUIElementStyle::GUIElementStateStyle* externalStyle);
+		ScriptGUIElementStateStyle(MonoObject* instance);
+		ScriptGUIElementStateStyle(MonoObject* instance, GUIElementStyle::GUIElementStateStyle* externalStyle);
 
 		GUIElementStyle::GUIElementStateStyle* mElementStateStyle;
 		ScriptSpriteTexture* mSpriteTexture;

+ 4 - 41
SBansheeEngine/Include/BsScriptGUIElementStyle.h

@@ -21,52 +21,15 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIElementStyle : public ScriptObject<ScriptGUIElementStyle>
 	{
 	public:
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIElementStyle")
+
 		~ScriptGUIElementStyle();
 
-		static void initMetaData();
 		GUIElementStyle* getInternalValue() const { return mElementStyle; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoString* name);
 		static void internal_createInstanceExternal(MonoObject* instance, MonoString* name, GUIElementStyle* externalStyle);
-		static void internal_destroyInstance(ScriptGUIElementStyle* nativeInstance);
-
-		static void initRuntimeData()
-		{
-			metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIElementStyle::internal_createInstance);
-			metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIElementStyle::internal_destroyInstance);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Font);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FontSize);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, TextHorzAlign);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, TextVertAlign);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ImagePosition);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, WordWrap);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Normal);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Hover);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Active);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Focused);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, NormalOn);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, HoverOn);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ActiveOn);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FocusedOn);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Border);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Margins);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ContentOffset);
-
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Width);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Height);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MinWidth);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MaxWidth);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MinHeight);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MaxHeight);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FixedWidth);
-			CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FixedHeight);
-		}
 
 		CM_SCRIPT_GETSET_OBJECT_SHRDPTR(ScriptGUIElementStyle, ScriptFont, Font, mElementStyle->font, mFont);
 
@@ -99,8 +62,8 @@ namespace BansheeEngine
 		CM_SCRIPT_GETSET_VALUE(ScriptGUIElementStyle, bool, FixedWidth, mElementStyle->fixedWidth);
 		CM_SCRIPT_GETSET_VALUE(ScriptGUIElementStyle, bool, FixedHeight, mElementStyle->fixedHeight);
 
-		ScriptGUIElementStyle(const String& name);
-		ScriptGUIElementStyle(const String& name, GUIElementStyle* externalStyle);
+		ScriptGUIElementStyle(MonoObject* instance, const String& name);
+		ScriptGUIElementStyle(MonoObject* instance, const String& name, GUIElementStyle* externalStyle);
 
 		String mName;
 		GUIElementStyle* mElementStyle;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIFixedSpace.h

@@ -8,21 +8,19 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIFixedSpace : public ScriptObject<ScriptGUIFixedSpace>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIFixedSpace")
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* parentLayout, UINT32 size);
-		static void internal_destroyInstance(ScriptGUIFixedSpace* nativeInstance);
 
 		static void internal_destroy(ScriptGUIFixedSpace* nativeInstance);
 		static void internal_setVisible(ScriptGUIFixedSpace* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIFixedSpace* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUIFixedSpace(GUIFixedSpace& fixedSpace, GUILayout* parentLayout);
+		ScriptGUIFixedSpace(MonoObject* instance, GUIFixedSpace& fixedSpace, GUILayout* parentLayout);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIFixedSpace& mFixedSpace;
 		GUILayout* mParentLayout;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIFlexibleSpace.h

@@ -8,21 +8,19 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIFlexibleSpace : public ScriptObject<ScriptGUIFlexibleSpace>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIFlexibleSpace")
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* parentLayout);
-		static void internal_destroyInstance(ScriptGUIFlexibleSpace* nativeInstance);
 
 		static void internal_destroy(ScriptGUIFlexibleSpace* nativeInstance);
 		static void internal_setVisible(ScriptGUIFlexibleSpace* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIFlexibleSpace* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUIFlexibleSpace(GUIFlexibleSpace& flexibleSpace, GUILayout* parentLayout);
+		ScriptGUIFlexibleSpace(MonoObject* instance, GUIFlexibleSpace& flexibleSpace, GUILayout* parentLayout);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIFlexibleSpace& mFlexibleSpace;
 		GUILayout* mParentLayout;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIInputBox.h

@@ -9,14 +9,13 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIInputBox : public ScriptObject<ScriptGUIInputBox>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIInputBox")
 
 		GUIInputBox* getInternalValue() const { return mInputBox; }
 		void* getNativeRaw() const { return mInputBox; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, bool multiline, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIInputBox* nativeInstance);
 
 		static void internal_setText(ScriptGUIInputBox* nativeInstance, MonoString* text);
 		static void internal_getText(ScriptGUIInputBox* nativeInstance, MonoString** text);
@@ -25,11 +24,10 @@ namespace BansheeEngine
 		static void internal_setVisible(ScriptGUIInputBox* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIInputBox* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUIInputBox(GUIInputBox* inputBox);
+		ScriptGUIInputBox(MonoObject* instance, GUIInputBox* inputBox);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIInputBox* mInputBox;
 		bool mIsDestroyed;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUILabel.h

@@ -8,25 +8,23 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUILabel : public ScriptObject<ScriptGUILabel>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUILabel")
 
 		GUILabel* getInternalValue() const { return mLabel; }
 		void* getNativeRaw() const { return mLabel; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUILabel* nativeInstance);
 		static void internal_setContent(ScriptGUILabel* nativeInstance, MonoObject* content);
 
 		static void internal_destroy(ScriptGUILabel* nativeInstance);
 		static void internal_setVisible(ScriptGUILabel* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUILabel* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUILabel(GUILabel* label);
+		ScriptGUILabel(MonoObject* instance, GUILabel* label);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUILabel* mLabel;
 		bool mIsDestroyed;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUILayout.h

@@ -8,7 +8,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUILayout : public ScriptObject<ScriptGUILayout>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUILayout")
 
 		GUILayout* getInternalValue() const { return mLayout; }
 		void* getNativeRaw() const { return mLayout; }
@@ -18,17 +18,15 @@ namespace BansheeEngine
 		static void internal_createInstanceXFromLayout(MonoObject* instance, MonoObject* parentLayout);
 		static void internal_createInstanceYFromLayout(MonoObject* instance, MonoObject* parentLayout);
 		static void internal_createInstanceYFromScrollArea(MonoObject* instance, MonoObject* parentScrollArea);
-		static void internal_destroyInstance(ScriptGUILayout* nativeInstance);
 
 		static void internal_destroy(ScriptGUILayout* nativeInstance);
 		static void internal_setVisible(ScriptGUILayout* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUILayout* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUILayout(GUILayout* layout, GUILayout* parentLayout);
+		ScriptGUILayout(MonoObject* instance, GUILayout* layout, GUILayout* parentLayout);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUILayout* mLayout;
 		GUILayout* mParentLayout;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIListBox.h

@@ -9,27 +9,25 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIListBox : public ScriptObject<ScriptGUIListBox>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIListBox")
 
 		GUIListBox* getInternalValue() const { return mListBox; }
 		void* getNativeRaw() const { return mListBox; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoArray* elements, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIListBox* nativeInstance);
 		static void internal_setElements(ScriptGUIListBox* nativeInstance, MonoArray* elements);
 
 		static void internal_destroy(ScriptGUIListBox* nativeInstance);
 		static void internal_setVisible(ScriptGUIListBox* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIListBox* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
 		static void onSelectionChanged(MonoObject* instance, UINT32 index);
 
-		ScriptGUIListBox(GUIListBox* listBox);
+		ScriptGUIListBox(MonoObject* instance, GUIListBox* listBox);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIListBox* mListBox;
 		bool mIsDestroyed;

+ 2 - 5
SBansheeEngine/Include/BsScriptGUIPanel.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIPanel : public ScriptObject<ScriptGUIPanel>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIPanel")
 
 		GUIWidget& getWidget() const { return *mParentWidget; }
 		const RectI& getClippedArea() const { return mClippedArea; }
@@ -21,12 +21,9 @@ namespace BansheeEngine
 		void unregisterArea(ScriptGUIArea* area);
 
 	protected:
-		ScriptGUIPanel();
-
-		static void initRuntimeData();
+		ScriptGUIPanel(MonoObject* instance);
 
 		static void internal_createInstance(MonoObject* instance);
-		static void internal_destroyInstance(ScriptGUIPanel* thisPtr);
 		static void internal_setArea(ScriptGUIPanel* thisPtr, INT32 x, INT32 y, 
 			UINT32 width, UINT32 height, UINT16 depth);
 

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIScrollArea.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIScrollArea : public ScriptObject<ScriptGUIScrollArea>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIScrollArea")
 
 		GUIScrollArea* getInternalValue() const { return mScrollArea; }
 		void* getNativeRaw() const { return mScrollArea; }
@@ -17,17 +17,15 @@ namespace BansheeEngine
 	private:
 		static void internal_createInstance(MonoObject* instance, ScrollBarType vertBarType, ScrollBarType horzBarType, 
 			MonoString* scrollBarStyle, MonoString* scrollAreaStyle, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIScrollArea* nativeInstance);
 
 		static void internal_destroy(ScriptGUIScrollArea* nativeInstance);
 		static void internal_setVisible(ScriptGUIScrollArea* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIScrollArea* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUIScrollArea(GUIScrollArea* scrollArea);
+		ScriptGUIScrollArea(MonoObject* instance, GUIScrollArea* scrollArea);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIScrollArea* mScrollArea;
 		bool mIsDestroyed;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUITexture.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUITexture : public ScriptObject<ScriptGUITexture>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUITexture")
 
 		GUITexture* getInternalValue() const { return mTexture; }
 		void* getNativeRaw() const { return mTexture; }
@@ -17,18 +17,16 @@ namespace BansheeEngine
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* texture, 
 			GUIImageScaleMode scale, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUITexture* nativeInstance);
 		static void internal_setTexture(ScriptGUITexture* nativeInstance, MonoObject* texture);
 
 		static void internal_destroy(ScriptGUITexture* nativeInstance);
 		static void internal_setVisible(ScriptGUITexture* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUITexture* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
-		ScriptGUITexture(GUITexture* texture);
+		ScriptGUITexture(MonoObject* instance, GUITexture* texture);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUITexture* mTexture;
 		bool mIsDestroyed;

+ 3 - 5
SBansheeEngine/Include/BsScriptGUIToggle.h

@@ -8,7 +8,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIToggle : public ScriptObject<ScriptGUIToggle>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIToggle")
 
 		GUIToggle* getInternalValue() const { return mToggle; }
 		void* getNativeRaw() const { return mToggle; }
@@ -16,7 +16,6 @@ namespace BansheeEngine
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoObject* content, 
 			MonoObject* toggleGroup, MonoString* style, MonoArray* guiOptions);
-		static void internal_destroyInstance(ScriptGUIToggle* nativeInstance);
 		static void internal_setContent(ScriptGUIToggle* nativeInstance, MonoObject* content);
 		static void internal_toggleOn(ScriptGUIToggle* nativeInstance);
 		static void internal_toggleOff(ScriptGUIToggle* nativeInstance);
@@ -25,16 +24,15 @@ namespace BansheeEngine
 		static void internal_setVisible(ScriptGUIToggle* nativeInstance, bool visible);
 		static void internal_setParent(ScriptGUIToggle* nativeInstance, MonoObject* parentLayout);
 
-		static void initRuntimeData();
-
 		static void onClick(MonoObject* instance);
 		static void onHover(MonoObject* instance);
 		static void onOut(MonoObject* instance);
 		static void onToggled(MonoObject* instance, bool toggled);
 
-		ScriptGUIToggle(GUIToggle* toggle);
+		ScriptGUIToggle(MonoObject* instance, GUIToggle* toggle);
 
 		void destroy();
+		void _onManagedInstanceDeleted();
 
 		GUIToggle* mToggle;
 		bool mIsDestroyed;

+ 2 - 5
SBansheeEngine/Include/BsScriptGUIToggleGroup.h

@@ -8,18 +8,15 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptGUIToggleGroup : public ScriptObject<ScriptGUIToggleGroup>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "GUIToggleGroup")
 
 		std::shared_ptr<GUIToggleGroup> getInternalValue() const { return mToggleGroup; }
 		void* getNativeRaw() const { return mToggleGroup.get(); }
 
 	private:
 		static void internal_createInstance(MonoObject* instance);
-		static void internal_destroyInstance(ScriptGUIToggleGroup* nativeInstance);
 
-		static void initRuntimeData();
-
-		ScriptGUIToggleGroup(const std::shared_ptr<GUIToggleGroup>& toggleGroup);
+		ScriptGUIToggleGroup(MonoObject* instance, const std::shared_ptr<GUIToggleGroup>& toggleGroup);
 
 		std::shared_ptr<GUIToggleGroup> mToggleGroup;
 	};

+ 2 - 5
SBansheeEngine/Include/BsScriptHString.h

@@ -9,20 +9,17 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptHString : public ScriptObject<ScriptHString>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "LocString")
 
 		const HString& getInternalValue() const { return mString; }
 		void* getNativeRaw() const { return (void*)&mString; }
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoString* identifier);
-		static void internal_destroyInstance(ScriptHString* nativeInstance);
 		static void internal_setParameter(HString* nativeInstance, UINT32 idx, MonoString* value);
 		static void internal_getValue(HString* nativeInstance, MonoString** value);
 
-		static void initRuntimeData();
-
-		ScriptHString(const HString& string);
+		ScriptHString(MonoObject* instance, const HString& string);
 
 		GUIArea* mArea;
 		HString mString;

+ 36 - 29
SBansheeEngine/Include/BsScriptObject.h

@@ -2,7 +2,6 @@
 
 #include "BsScriptEnginePrerequisites.h"
 #include "BsScriptMeta.h"
-#include "BsMonoField.h"
 #include "CmException.h"
 #include <mono/jit/jit.h>
 
@@ -14,21 +13,42 @@ namespace BansheeEngine
 	public:
 		InitScriptObjectOnStart()
 		{
-			Type::initMetaData();
+			ScriptObject<Type>::_initMetaData();
 		}
 
 		void makeSureIAmInstantiated() { }
 	};
 
+	class BS_SCR_BE_EXPORT ScriptObjectBase
+	{
+	public:
+		ScriptObjectBase(MonoObject* instance);
+		virtual ~ScriptObjectBase();
+
+		static const ScriptMeta* getMetaData() { return &metaData; }
+
+		MonoObject* getManagedInstance() const { return mManagedInstance; }
+		virtual void* getNativeRaw() const { return nullptr; }
+
+		virtual void _onManagedInstanceDeleted();
+
+	protected:
+		static ScriptMeta metaData;
+		MonoObject* mManagedInstance;
+
+		static void registerTypeWithManager();
+		static void* getNativeInstance(MonoObject* managedInstance);
+	};
+
 	/**
 	 * @brief	 Base class for objects that can be extended using Mono scripting
 	 */
 	template <class Type>
-	class ScriptObject
+	class ScriptObject : public ScriptObjectBase
 	{
 	public:
-		ScriptObject()
-			:mManagedInstance(nullptr)
+		ScriptObject(MonoObject* instance)
+			:ScriptObjectBase(instance)
 		{	
 			// Compiler will only generate code for stuff that is directly used, including static data members,
 			// so we fool it here like we're using the class directly. Otherwise compiler won't generate the code for the member
@@ -37,37 +57,21 @@ namespace BansheeEngine
 		}
 
 		virtual ~ScriptObject() 
-		{
-			if(mManagedInstance != nullptr)
-				CM_EXCEPT(InvalidStateException, "Script object is being destroyed without its instance previously being released.");
-		}
-
-		MonoObject* getManagedInstance() const { return mManagedInstance; }
-		virtual void* getNativeRaw() const { return nullptr; }
+		{ }
 
 		static Type* toNative(MonoObject* managedInstance)
 		{
-			Type* nativeInstance = nullptr;
-			metaData.thisPtrField->getValue(managedInstance, &nativeInstance);
-
-			return nativeInstance;
+			return reinterpret_cast<Type*>(getNativeInstance(managedInstance));
 		}
 
-		static const ScriptMeta* getMetaData() { return &metaData; }
-
-	protected:
-		static ScriptMeta metaData;
-
-		MonoObject* mManagedInstance;
-
-		void createInstance(MonoObject* instance)
+		static void _initMetaData()
 		{
-			if(mManagedInstance != nullptr)
-				CM_EXCEPT(InvalidStateException, "Trying to instantiate an already instantiated script object.");
+			metaData = ScriptMeta(Type::getAssemblyName(), Type::getNamespace(), Type::getTypeName(), &Type::initRuntimeData);
 
-			mManagedInstance = instance;
+			registerTypeWithManager();
 		}
 
+	protected:
 		template <class Type2>
 		static void throwIfInstancesDontMatch(ScriptObject<Type2>* lhs, void* rhs)
 		{
@@ -87,6 +91,9 @@ namespace BansheeEngine
 	template <typename Type>
 	InitScriptObjectOnStart<Type> ScriptObject<Type>::initOnStart;
 
-	template <typename Type>
-	ScriptMeta ScriptObject<Type>::metaData;
+#define SCRIPT_OBJ(assembly, namespace, name)		\
+	static String getAssemblyName() { return assembly; }	\
+	static String getNamespace() { return namespace; }		\
+	static String getTypeName() { return name; }			\
+	static void initRuntimeData();
 }

+ 19 - 0
SBansheeEngine/Include/BsScriptObjectImpl.h

@@ -0,0 +1,19 @@
+#pragma once
+
+#include "BsScriptEnginePrerequisites.h"
+#include "BsScriptObject.h"
+#include "CmRectI.h"
+
+namespace BansheeEngine
+{
+	class BS_SCR_BE_EXPORT ScriptObjectImpl : public ScriptObject<ScriptObjectImpl>
+	{
+	public:
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "ScriptObject")
+
+	private:
+		ScriptObjectImpl(MonoObject* instance);
+
+		static void internal_managedInstanceDeleted(ScriptObjectBase* instance);
+	};
+}

+ 3 - 5
SBansheeEngine/Include/BsScriptSceneObject.h

@@ -10,7 +10,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSceneObject : public ScriptGameObject, public ScriptObject<ScriptSceneObject>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SceneObject")
 
 		virtual HGameObject getNativeHandle() const { return mSceneObject; }
 		virtual void setNativeHandle(const HGameObject& gameObject);
@@ -19,7 +19,6 @@ namespace BansheeEngine
 		friend class ScriptGameObjectManager;
 
 		static void internal_createInstance(MonoObject* instance, MonoString* name);
-		static void internal_destroyInstance(ScriptSceneObject* nativeInstance);
 
 		static void internal_setParent(ScriptSceneObject* nativeInstance, MonoObject* parent);
 		static MonoObject* internal_getParent(ScriptSceneObject* nativeInstance);
@@ -27,10 +26,9 @@ namespace BansheeEngine
 		static UINT32 internal_getNumChildren(ScriptSceneObject* nativeInstance);
 		static MonoObject* internal_getChild(ScriptSceneObject* nativeInstance, UINT32 idx);
 
-		static void initRuntimeData();
+		ScriptSceneObject(MonoObject* instance, const HSceneObject& sceneObject);
 
-		ScriptSceneObject(const HSceneObject& sceneObject);
-		~ScriptSceneObject() {}
+		void _onManagedInstanceDeleted();
 
 		HSceneObject mSceneObject;
 	};

+ 2 - 6
SBansheeEngine/Include/BsScriptSerializableArray.h

@@ -8,18 +8,14 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSerializableArray : public ScriptObject<ScriptSerializableArray>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SerializableArray")
 
 		static ScriptSerializableArray* create(const ManagedSerializableTypeInfoArrayPtr& typeInfo, MonoObject* object);
 
 	private:
-		static void internal_destroyInstance(ScriptSerializableArray* nativeInstance);
 		static MonoObject* internal_createProperty(ScriptSerializableArray* nativeInstance);
 
-		static void initRuntimeData();
-
-		ScriptSerializableArray(const ManagedSerializableTypeInfoArrayPtr& typeInfo);
-		~ScriptSerializableArray() {}
+		ScriptSerializableArray(MonoObject* instance, const ManagedSerializableTypeInfoArrayPtr& typeInfo);
 
 		ManagedSerializableTypeInfoArrayPtr mTypeInfo;
 	};

+ 2 - 7
SBansheeEngine/Include/BsScriptSerializableField.h

@@ -8,23 +8,18 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSerializableField : public ScriptObject<ScriptSerializableField>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SerializableField")
 
 		static ScriptSerializableField* create(MonoObject* parentObject, const ManagedSerializableFieldInfoPtr& fieldInfo);
 
 	private:
-		static void internal_destroyInstance(ScriptSerializableField* nativeInstance);
-
 		static MonoObject* internal_createProperty(ScriptSerializableField* nativeInstance);
 		static MonoObject* internal_getValue(ScriptSerializableField* nativeInstance, MonoObject* instance);
 		static void internal_setValue(ScriptSerializableField* nativeInstance, MonoObject* instance, MonoObject* value);
 
-		static void initRuntimeData();
-
 		static UINT32 nativeToManagedFieldType(const ManagedSerializableTypeInfoPtr& typeInfo);
 
-		ScriptSerializableField(const ManagedSerializableFieldInfoPtr& fieldInfo);
-		~ScriptSerializableField() {}
+		ScriptSerializableField(MonoObject* instance, const ManagedSerializableFieldInfoPtr& fieldInfo);
 
 		ManagedSerializableFieldInfoPtr mFieldInfo;
 	};

+ 2 - 6
SBansheeEngine/Include/BsScriptSerializableObject.h

@@ -8,20 +8,16 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSerializableObject : public ScriptObject<ScriptSerializableObject>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SerializableObject")
 
 		static ScriptSerializableObject* create(const ManagedSerializableTypeInfoPtr& typeInfo, MonoObject* object);
 
 	private:
 		static void internal_createInstance(MonoObject* instance, MonoReflectionType* type, MonoObject* object);
-		static void internal_destroyInstance(ScriptSerializableObject* nativeInstance);
-
-		static void initRuntimeData();
 
 		static ScriptSerializableObject* createInternal(MonoObject* instance, const ManagedSerializableObjectInfoPtr& objInfo);
 
-		ScriptSerializableObject(const ManagedSerializableTypeInfoPtr& typeInfo);
-		~ScriptSerializableObject() {}
+		ScriptSerializableObject(MonoObject* instance, const ManagedSerializableTypeInfoPtr& typeInfo);
 
 		ManagedSerializableTypeInfoPtr mTypeInfo;
 

+ 4 - 6
SBansheeEngine/Include/BsScriptSerializableProperty.h

@@ -8,19 +8,17 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSerializableProperty : public ScriptObject<ScriptSerializableProperty>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SerializableProperty")
 
 		static ScriptSerializableProperty* create(const ManagedSerializableTypeInfoPtr& typeInfo);
 
+		~ScriptSerializableProperty() {}
+
 	private:
-		static void internal_destroyInstance(ScriptSerializableProperty* nativeInstance);
 		static MonoObject* internal_createObject(ScriptSerializableProperty* nativeInstance, MonoObject* object);
 		static MonoObject* internal_createArray(ScriptSerializableProperty* nativeInstance, MonoObject* object);
 
-		static void initRuntimeData();
-
-		ScriptSerializableProperty(const ManagedSerializableTypeInfoPtr& typeInfo);
-		~ScriptSerializableProperty() {}
+		ScriptSerializableProperty(MonoObject* instance, const ManagedSerializableTypeInfoPtr& typeInfo);
 
 		ManagedSerializableTypeInfoPtr mTypeInfo;
 	};

+ 3 - 5
SBansheeEngine/Include/BsScriptSpriteTexture.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptSpriteTexture : public ScriptResource, public ScriptObject<ScriptSpriteTexture>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "SpriteTexture")
 
 		const HSpriteTexture& getInternalValue() const { return mTexture; }
 
@@ -20,12 +20,10 @@ namespace BansheeEngine
 		friend class ScriptResourceManager;
 
 		static void internal_createInstance(MonoObject* instance);
-		static void internal_destroyInstance(ScriptSpriteTexture* nativeInstance);
 
-		static void initRuntimeData();
+		ScriptSpriteTexture(MonoObject* instance, const HSpriteTexture& texture);
 
-		ScriptSpriteTexture(const HSpriteTexture& texture);
-		~ScriptSpriteTexture() {}
+		void _onManagedInstanceDeleted();
 
 		HSpriteTexture mTexture;
 	};

+ 2 - 4
SBansheeEngine/Include/BsScriptStringTable.h

@@ -9,7 +9,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptStringTable : public ScriptObject<ScriptStringTable>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "StringTable")
 
 	private:
 		static void internal_GetActiveLanguage(Language* value);
@@ -19,8 +19,6 @@ namespace BansheeEngine
 		static void internal_RemoveString(MonoString* identifier);
 		static void internal_GetLocalizedString(MonoString* identifier, MonoString** value);
 
-		static void initRuntimeData();
-
-		ScriptStringTable() { }
+		ScriptStringTable(MonoObject* instance);
 	};
 }

+ 3 - 5
SBansheeEngine/Include/BsScriptTexture2D.h

@@ -10,7 +10,7 @@ namespace BansheeEngine
 	class BS_SCR_BE_EXPORT ScriptTexture2D : public ScriptResource, public ScriptObject<ScriptTexture2D>
 	{
 	public:
-		static void initMetaData();
+		SCRIPT_OBJ(BansheeEngineAssemblyName, "BansheeEngine", "Texture2D")
 
 		void* getNativeRaw() const { return mTexture.get(); }
 
@@ -20,12 +20,10 @@ namespace BansheeEngine
 		friend class ScriptResourceManager;
 
 		static void internal_createInstance(MonoObject* instance, UINT32 format, UINT32 width, UINT32 height, bool hasMipmaps, bool gammaCorrection);
-		static void internal_destroyInstance(ScriptTexture2D* nativeInstance);
 
-		static void initRuntimeData();
+		ScriptTexture2D(MonoObject* instance, const HTexture& texture);
 
-		ScriptTexture2D(const HTexture& texture);
-		~ScriptTexture2D() {}
+		void _onManagedInstanceDeleted();
 
 		HTexture mTexture;
 	};

+ 3 - 0
SBansheeEngine/SBansheeEngine.vcxproj

@@ -262,6 +262,7 @@
     <ClInclude Include="Include\BsScriptHString.h" />
     <ClInclude Include="Include\BsScriptMacros.h" />
     <ClInclude Include="Include\BsScriptObject.h" />
+    <ClInclude Include="Include\BsScriptObjectImpl.h" />
     <ClInclude Include="Include\BsScriptResource.h" />
     <ClInclude Include="Include\BsScriptResourceManager.h" />
     <ClInclude Include="Include\BsScriptSceneObject.h" />
@@ -301,6 +302,8 @@
     <ClCompile Include="Source\BsScriptGUIToggleGroup.cpp" />
     <ClCompile Include="Source\BsScriptHString.cpp" />
     <ClCompile Include="Source\BsScriptGUIInputBox.cpp" />
+    <ClCompile Include="Source\BsScriptObject.cpp" />
+    <ClCompile Include="Source\BsScriptObjectImpl.cpp" />
     <ClCompile Include="Source\BsScriptResourceManager.cpp" />
     <ClCompile Include="Source\BsScriptSceneObject.cpp" />
     <ClCompile Include="Source\BsManagedSerializableArray.cpp" />

+ 9 - 0
SBansheeEngine/SBansheeEngine.vcxproj.filters

@@ -180,6 +180,9 @@
     <ClInclude Include="Include\BsScriptSerializableProperty.h">
       <Filter>Header Files</Filter>
     </ClInclude>
+    <ClInclude Include="Include\BsScriptObjectImpl.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="Source\BsScriptTexture2D.cpp">
@@ -299,5 +302,11 @@
     <ClCompile Include="Source\BsScriptSerializableProperty.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
+    <ClCompile Include="Source\BsScriptObjectImpl.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="Source\BsScriptObject.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
   </ItemGroup>
 </Project>

+ 5 - 15
SBansheeEngine/Source/BsScriptComponent.cpp

@@ -11,18 +11,9 @@
 
 namespace BansheeEngine
 {
-	ScriptComponent::ScriptComponent(const GameObjectHandle<ManagedComponent>& managedComponent)
-		:mManagedComponent(managedComponent)
-	{
-
-	}
-
-	void ScriptComponent::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "Component", &ScriptComponent::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
+	ScriptComponent::ScriptComponent(MonoObject* instance, const GameObjectHandle<ManagedComponent>& managedComponent)
+		:ScriptObject(instance), mManagedComponent(managedComponent)
+	{ }
 
 	void ScriptComponent::initRuntimeData()
 	{
@@ -30,7 +21,6 @@ namespace BansheeEngine
 		metaData.scriptClass->addInternalCall("Internal_GetComponent", &ScriptComponent::internal_getComponent);
 		metaData.scriptClass->addInternalCall("Internal_GetComponents", &ScriptComponent::internal_getComponents);
 		metaData.scriptClass->addInternalCall("Internal_RemoveComponent", &ScriptComponent::internal_removeComponent);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptComponent::internal_destroyInstance);
 	}
 
 	MonoObject* ScriptComponent::internal_addComponent(MonoObject* parentSceneObject, MonoReflectionType* type)
@@ -136,9 +126,9 @@ namespace BansheeEngine
 		LOGWRN("Attempting to remove a component that doesn't exists on SceneObject \"" + so->getName() + "\"");
 	}
 
-	void ScriptComponent::internal_destroyInstance(ScriptComponent* nativeInstance)
+	void ScriptComponent::_onManagedInstanceDeleted()
 	{
-		ScriptGameObjectManager::instance().destroyScriptGameObject(nativeInstance);
+		ScriptGameObjectManager::instance().destroyScriptGameObject(this);
 	}
 
 	void ScriptComponent::setNativeHandle(const HGameObject& gameObject)

+ 3 - 6
SBansheeEngine/Source/BsScriptDebug.cpp

@@ -6,12 +6,9 @@
 
 namespace BansheeEngine
 {
-	void ScriptDebug::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "Debug", &ScriptDebug::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
+	ScriptDebug::ScriptDebug(MonoObject* instance)
+		:ScriptObject(instance)
+	{ }
 
 	void ScriptDebug::initRuntimeData()
 	{

+ 4 - 19
SBansheeEngine/Source/BsScriptFont.cpp

@@ -7,19 +7,12 @@
 
 namespace BansheeEngine
 {
-	ScriptFont::ScriptFont(const HFont& font)
-		:mFont(font)
+	ScriptFont::ScriptFont(MonoObject* instance, const HFont& font)
+		:ScriptObject(instance), mFont(font)
 	{
 
 	}
 
-	void ScriptFont::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "Font", &ScriptFont::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void* ScriptFont::getNativeRaw() const
 	{
 		return (void*)mFont.get();
@@ -27,19 +20,11 @@ namespace BansheeEngine
 
 	void ScriptFont::initRuntimeData()
 	{
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptFont::internal_destroyInstance);
-	}
 
-	void ScriptFont::internal_createInstanceExternal(MonoObject* instance, const HFont& font)
-	{
-		ScriptFont* nativeInstance = new (cm_alloc<ScriptFont>()) ScriptFont(font);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
 	}
 
-	void ScriptFont::internal_destroyInstance(ScriptFont* nativeInstance)
+	void ScriptFont::internal_createInstanceExternal(MonoObject* instance, const HFont& font)
 	{
-		cm_delete(nativeInstance);
+		ScriptFont* nativeInstance = new (cm_alloc<ScriptFont>()) ScriptFont(instance, font);
 	}
 }

+ 10 - 21
SBansheeEngine/Source/BsScriptGUIArea.cpp

@@ -10,24 +10,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIArea::ScriptGUIArea(GUIArea* area, ScriptGUIPanel* parentGUI)
-		:mGUIArea(area), mParentPanel(parentGUI), mIsDestroyed(false)
+	ScriptGUIArea::ScriptGUIArea(MonoObject* instance, GUIArea* area, ScriptGUIPanel* parentGUI)
+		:ScriptObject(instance), mGUIArea(area), mParentPanel(parentGUI), mIsDestroyed(false)
 	{
 		mParentPanel->registerArea(this);
 	}
-
-	void ScriptGUIArea::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIArea", &ScriptGUIArea::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIArea::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIArea::internal_createInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetArea", &ScriptGUIArea::internal_setArea);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIArea::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIArea::internal_destroy);
 		metaData.scriptClass->addInternalCall("Internal_SetVisible", &ScriptGUIArea::internal_setVisible);
 	}
@@ -45,21 +36,19 @@ namespace BansheeEngine
 		}
 	}
 
-	void ScriptGUIArea::internal_createInstance(MonoObject* instance, MonoObject* panel, INT32 x, INT32 y, UINT32 width, UINT32 height, UINT16 depth)
+	void ScriptGUIArea::_onManagedInstanceDeleted()
 	{
-		ScriptGUIPanel* scriptGUIPanel = ScriptGUIPanel::toNative(panel);
-		GUIArea* nativeArea = GUIArea::create(scriptGUIPanel->getWidget(), x, y, width, height, depth);
-
-		ScriptGUIArea* nativeInstance = new (cm_alloc<ScriptGUIArea>()) ScriptGUIArea(nativeArea, scriptGUIPanel);
-		nativeInstance->createInstance(instance);
+		destroy();
 
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptObject::_onManagedInstanceDeleted();
 	}
 
-	void ScriptGUIArea::internal_destroyInstance(ScriptGUIArea* thisPtr)
+	void ScriptGUIArea::internal_createInstance(MonoObject* instance, MonoObject* panel, INT32 x, INT32 y, UINT32 width, UINT32 height, UINT16 depth)
 	{
-		thisPtr->destroy();
-		cm_delete(thisPtr);
+		ScriptGUIPanel* scriptGUIPanel = ScriptGUIPanel::toNative(panel);
+		GUIArea* nativeArea = GUIArea::create(scriptGUIPanel->getWidget(), x, y, width, height, depth);
+
+		ScriptGUIArea* nativeInstance = new (cm_alloc<ScriptGUIArea>()) ScriptGUIArea(instance, nativeArea, scriptGUIPanel);
 	}
 
 	void ScriptGUIArea::internal_destroy(ScriptGUIArea* thisPtr)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIButton.cpp

@@ -21,23 +21,15 @@ namespace BansheeEngine
 	ScriptGUIButton::OnHoverThunkDef ScriptGUIButton::onHoverThunk;
 	ScriptGUIButton::OnOutThunkDef ScriptGUIButton::onOutThunk;
 
-	ScriptGUIButton::ScriptGUIButton(GUIButton* button)
-		:mButton(button), mIsDestroyed(false)
+	ScriptGUIButton::ScriptGUIButton(MonoObject* instance, GUIButton* button)
+		:ScriptObject(instance), mButton(button), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIButton::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIButton", &ScriptGUIButton::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIButton::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIButton::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIButton::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetContent", &ScriptGUIButton::internal_setContent);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIButton::internal_destroy);
@@ -60,6 +52,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIButton::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIButton::internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions)
 	{
 		GUIOptions options;
@@ -75,10 +74,7 @@ namespace BansheeEngine
 		guiButton->onHover.connect(std::bind(&ScriptGUIButton::onHover, instance));
 		guiButton->onOut.connect(std::bind(&ScriptGUIButton::onOut, instance));
 
-		ScriptGUIButton* nativeInstance = new (cm_alloc<ScriptGUIButton>()) ScriptGUIButton(guiButton);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIButton* nativeInstance = new (cm_alloc<ScriptGUIButton>()) ScriptGUIButton(instance, guiButton);
 	}
 
 	void ScriptGUIButton::internal_setContent(ScriptGUIButton* nativeInstance, MonoObject* content)
@@ -92,12 +88,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUIButton::internal_destroyInstance(ScriptGUIButton* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUIButton::internal_setVisible(ScriptGUIButton* nativeInstance, bool visible)
 	{
 		if(visible)

+ 3 - 7
SBansheeEngine/Source/BsScriptGUIContent.cpp

@@ -5,7 +5,6 @@
 #include "BsMonoManager.h"
 #include "BsMonoUtil.h"
 #include "BsScriptHString.h"
-#include "BsScriptGUIContent.h"
 #include "BsScriptSpriteTexture.h"
 #include "BsSpriteTexture.h"
 
@@ -15,12 +14,9 @@ namespace BansheeEngine
 	MonoField* ScriptGUIContent::mTooltipField;
 	MonoField* ScriptGUIContent::mImageField;
 
-	void ScriptGUIContent::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIContent", &ScriptGUIContent::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
+	ScriptGUIContent::ScriptGUIContent(MonoObject* instance)
+		:ScriptObject(instance)
+	{ }
 
 	void ScriptGUIContent::initRuntimeData()
 	{

+ 6 - 25
SBansheeEngine/Source/BsScriptGUIElementStateStyle.cpp

@@ -9,14 +9,14 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIElementStateStyle::ScriptGUIElementStateStyle()
-		:mElementStateStyle(cm_new<GUIElementStyle::GUIElementStateStyle>()), mSpriteTexture(nullptr), mOwnsStyle(true)
+	ScriptGUIElementStateStyle::ScriptGUIElementStateStyle(MonoObject* instance)
+		:ScriptObject(instance), mElementStateStyle(cm_new<GUIElementStyle::GUIElementStateStyle>()), mSpriteTexture(nullptr), mOwnsStyle(true)
 	{
 
 	}
 
-	ScriptGUIElementStateStyle::ScriptGUIElementStateStyle(GUIElementStyle::GUIElementStateStyle* externalStyle)
-		: mElementStateStyle(externalStyle), mSpriteTexture(nullptr), mOwnsStyle(false)
+	ScriptGUIElementStateStyle::ScriptGUIElementStateStyle(MonoObject* instance, GUIElementStyle::GUIElementStateStyle* externalStyle)
+		:ScriptObject(instance), mElementStateStyle(externalStyle), mSpriteTexture(nullptr), mOwnsStyle(false)
 	{
 
 	}
@@ -27,17 +27,9 @@ namespace BansheeEngine
 			cm_delete(mElementStateStyle);
 	}
 
-	void ScriptGUIElementStateStyle::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIElementStateStyle", &ScriptGUIElementStateStyle::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIElementStateStyle::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIElementStateStyle::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIElementStateStyle::internal_destroyInstance);
 
 		CM_SCRIPT_SETGET_META(ScriptGUIElementStateStyle, Texture);
 		CM_SCRIPT_SETGET_META(ScriptGUIElementStateStyle, TextColor);
@@ -45,22 +37,11 @@ namespace BansheeEngine
 
 	void ScriptGUIElementStateStyle::internal_createInstance(MonoObject* instance)
 	{
-		ScriptGUIElementStateStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStateStyle>()) ScriptGUIElementStateStyle();
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIElementStateStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStateStyle>()) ScriptGUIElementStateStyle(instance);
 	}
 
 	void ScriptGUIElementStateStyle::internal_createInstanceExternal(MonoObject* instance, GUIElementStyle::GUIElementStateStyle* externalStyle)
 	{
-		ScriptGUIElementStateStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStateStyle>()) ScriptGUIElementStateStyle(externalStyle);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIElementStateStyle::internal_destroyInstance(ScriptGUIElementStateStyle* nativeInstance)
-	{
-		cm_delete(nativeInstance);
+		ScriptGUIElementStateStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStateStyle>()) ScriptGUIElementStateStyle(instance, externalStyle);
 	}
 }

+ 38 - 20
SBansheeEngine/Source/BsScriptGUIElementStyle.cpp

@@ -10,15 +10,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIElementStyle::ScriptGUIElementStyle(const String& name)
-		:mName(name), mElementStyle(cm_new<GUIElementStyle>()), mFont(nullptr), mOwnsStyle(true), mNormal(nullptr), mHover(nullptr),
+	ScriptGUIElementStyle::ScriptGUIElementStyle(MonoObject* instance, const String& name)
+		:ScriptObject(instance), mName(name), mElementStyle(cm_new<GUIElementStyle>()), mFont(nullptr), mOwnsStyle(true), mNormal(nullptr), mHover(nullptr),
 		mActive(nullptr), mFocused(nullptr), mNormalOn(nullptr), mHoverOn(nullptr), mActiveOn(nullptr), mFocusedOn(nullptr)
 	{
 
 	}
 
-	ScriptGUIElementStyle::ScriptGUIElementStyle(const String& name, GUIElementStyle* externalStyle)
-		:mName(name), mElementStyle(externalStyle), mFont(nullptr), mOwnsStyle(false), mNormal(nullptr), mHover(nullptr),
+	ScriptGUIElementStyle::ScriptGUIElementStyle(MonoObject* instance, const String& name, GUIElementStyle* externalStyle)
+		:ScriptObject(instance), mName(name), mElementStyle(externalStyle), mFont(nullptr), mOwnsStyle(false), mNormal(nullptr), mHover(nullptr),
 		mActive(nullptr), mFocused(nullptr), mNormalOn(nullptr), mHoverOn(nullptr), mActiveOn(nullptr), mFocusedOn(nullptr)
 	{
 
@@ -30,11 +30,40 @@ namespace BansheeEngine
 			cm_delete(mElementStyle);
 	}
 
-	void ScriptGUIElementStyle::initMetaData()
+	void ScriptGUIElementStyle::initRuntimeData()
 	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIElementStyle", &ScriptGUIElementStyle::initRuntimeData);
+		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIElementStyle::internal_createInstance);
 
-		MonoManager::registerScriptType(&metaData);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Font);
+
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FontSize);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, TextHorzAlign);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, TextVertAlign);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ImagePosition);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, WordWrap);
+
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Normal);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Hover);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Active);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Focused);
+
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, NormalOn);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, HoverOn);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ActiveOn);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FocusedOn);
+
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Border);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Margins);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, ContentOffset);
+
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Width);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, Height);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MinWidth);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MaxWidth);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MinHeight);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, MaxHeight);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FixedWidth);
+		CM_SCRIPT_SETGET_META(ScriptGUIElementStyle, FixedHeight);
 	}
 
 	void ScriptGUIElementStyle::internal_createInstance(MonoObject* instance, MonoString* name)
@@ -43,10 +72,7 @@ namespace BansheeEngine
 		String styleName(nativeName);
 		free(nativeName);
 
-		ScriptGUIElementStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStyle>()) ScriptGUIElementStyle(styleName);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIElementStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStyle>()) ScriptGUIElementStyle(instance, styleName);
 	}
 
 	void ScriptGUIElementStyle::internal_createInstanceExternal(MonoObject* instance, MonoString* name, GUIElementStyle* externalStyle)
@@ -55,14 +81,6 @@ namespace BansheeEngine
 		String styleName(nativeName);
 		free(nativeName);
 
-		ScriptGUIElementStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStyle>()) ScriptGUIElementStyle(styleName, externalStyle);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIElementStyle::internal_destroyInstance(ScriptGUIElementStyle* nativeInstance)
-	{
-		cm_delete(nativeInstance);
+		ScriptGUIElementStyle* nativeInstance = new (cm_alloc<ScriptGUIElementStyle>()) ScriptGUIElementStyle(instance, styleName, externalStyle);
 	}
 }

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIFixedSpace.cpp

@@ -11,23 +11,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIFixedSpace::ScriptGUIFixedSpace(GUIFixedSpace& fixedSpace, GUILayout* parentLayout)
-		:mFixedSpace(fixedSpace), mParentLayout(parentLayout), mIsDestroyed(false)
+	ScriptGUIFixedSpace::ScriptGUIFixedSpace(MonoObject* instance, GUIFixedSpace& fixedSpace, GUILayout* parentLayout)
+		:ScriptObject(instance), mFixedSpace(fixedSpace), mParentLayout(parentLayout), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIFixedSpace::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIFixedSpace", &ScriptGUIFixedSpace::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIFixedSpace::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIFixedSpace::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIFixedSpace::internal_destroyInstance);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIFixedSpace::internal_destroy);
 		metaData.scriptClass->addInternalCall("Internal_SetVisible", &ScriptGUIFixedSpace::internal_setVisible);
@@ -45,22 +37,20 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIFixedSpace::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIFixedSpace::internal_createInstance(MonoObject* instance, MonoObject* parentLayout, UINT32 size)
 	{
 		ScriptGUILayout* scriptLayout = ScriptGUILayout::toNative(parentLayout);
 		GUILayout* nativeLayout = scriptLayout->getInternalValue();
 		GUIFixedSpace& space = nativeLayout->addSpace(size);
 
-		ScriptGUIFixedSpace* nativeInstance = new (cm_alloc<ScriptGUIFixedSpace>()) ScriptGUIFixedSpace(space, nativeLayout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIFixedSpace::internal_destroyInstance(ScriptGUIFixedSpace* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
+		ScriptGUIFixedSpace* nativeInstance = new (cm_alloc<ScriptGUIFixedSpace>()) ScriptGUIFixedSpace(instance, space, nativeLayout);
 	}
 
 	void ScriptGUIFixedSpace::internal_destroy(ScriptGUIFixedSpace* nativeInstance)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIFlexibleSpace.cpp

@@ -11,23 +11,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIFlexibleSpace::ScriptGUIFlexibleSpace(GUIFlexibleSpace& flexibleSpace, GUILayout* parentLayout)
-		:mFlexibleSpace(flexibleSpace), mParentLayout(parentLayout), mIsDestroyed(false)
+	ScriptGUIFlexibleSpace::ScriptGUIFlexibleSpace(MonoObject* instance, GUIFlexibleSpace& flexibleSpace, GUILayout* parentLayout)
+		:ScriptObject(instance), mFlexibleSpace(flexibleSpace), mParentLayout(parentLayout), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIFlexibleSpace::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIFlexibleSpace", &ScriptGUIFlexibleSpace::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIFlexibleSpace::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIFlexibleSpace::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIFlexibleSpace::internal_destroyInstance);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIFlexibleSpace::internal_destroy);
 		metaData.scriptClass->addInternalCall("Internal_SetVisible", &ScriptGUIFlexibleSpace::internal_setVisible);
@@ -45,22 +37,20 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIFlexibleSpace::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIFlexibleSpace::internal_createInstance(MonoObject* instance, MonoObject* parentLayout)
 	{
 		ScriptGUILayout* scriptLayout = ScriptGUILayout::toNative(parentLayout);
 		GUILayout* nativeLayout = scriptLayout->getInternalValue();
 		GUIFlexibleSpace& space = nativeLayout->addFlexibleSpace();
 
-		ScriptGUIFlexibleSpace* nativeInstance = new (cm_alloc<ScriptGUIFlexibleSpace>()) ScriptGUIFlexibleSpace(space, nativeLayout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIFlexibleSpace::internal_destroyInstance(ScriptGUIFlexibleSpace* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
+		ScriptGUIFlexibleSpace* nativeInstance = new (cm_alloc<ScriptGUIFlexibleSpace>()) ScriptGUIFlexibleSpace(instance, space, nativeLayout);
 	}
 
 	void ScriptGUIFlexibleSpace::internal_destroy(ScriptGUIFlexibleSpace* nativeInstance)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIInputBox.cpp

@@ -17,23 +17,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIInputBox::ScriptGUIInputBox(GUIInputBox* inputBox)
-		:mInputBox(inputBox), mIsDestroyed(false)
+	ScriptGUIInputBox::ScriptGUIInputBox(MonoObject* instance, GUIInputBox* inputBox)
+		:ScriptObject(instance), mInputBox(inputBox), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIInputBox::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUITextBox", &ScriptGUIInputBox::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIInputBox::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIInputBox::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIInputBox::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_GetText", &ScriptGUIInputBox::internal_getText);
 		metaData.scriptClass->addInternalCall("Internal_SetText", &ScriptGUIInputBox::internal_setText);
 
@@ -53,6 +45,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIInputBox::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIInputBox::internal_createInstance(MonoObject* instance, bool multiline, MonoString* style, MonoArray* guiOptions)
 	{
 		GUIOptions options;
@@ -63,10 +62,7 @@ namespace BansheeEngine
 
 		GUIInputBox* guiInputBox = GUIInputBox::create(multiline, options, toString(MonoUtil::monoToWString(style)));
 
-		ScriptGUIInputBox* nativeInstance = new (cm_alloc<ScriptGUIInputBox>()) ScriptGUIInputBox(guiInputBox);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIInputBox* nativeInstance = new (cm_alloc<ScriptGUIInputBox>()) ScriptGUIInputBox(instance, guiInputBox);
 	}
 
 	void ScriptGUIInputBox::internal_getText(ScriptGUIInputBox* nativeInstance, MonoString** text)
@@ -84,12 +80,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUIInputBox::internal_destroyInstance(ScriptGUIInputBox* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUIInputBox::internal_setVisible(ScriptGUIInputBox* nativeInstance, bool visible)
 	{
 		if(visible)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUILabel.cpp

@@ -16,23 +16,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUILabel::ScriptGUILabel(GUILabel* label)
-		:mLabel(label), mIsDestroyed(false)
+	ScriptGUILabel::ScriptGUILabel(MonoObject* instance, GUILabel* label)
+		:ScriptObject(instance), mLabel(label), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUILabel::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUILabel", &ScriptGUILabel::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUILabel::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUILabel::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUILabel::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetContent", &ScriptGUILabel::internal_setContent);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUILabel::internal_destroy);
@@ -51,6 +43,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUILabel::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUILabel::internal_createInstance(MonoObject* instance, MonoObject* content, MonoString* style, MonoArray* guiOptions)
 	{
 		GUIOptions options;
@@ -62,10 +61,7 @@ namespace BansheeEngine
 		GUIContent nativeContent(ScriptGUIContent::getText(content), ScriptGUIContent::getImage(content), ScriptGUIContent::getTooltip(content));
 		GUILabel* guiLabel = GUILabel::create(nativeContent, options, toString(MonoUtil::monoToWString(style)));
 
-		ScriptGUILabel* nativeInstance = new (cm_alloc<ScriptGUILabel>()) ScriptGUILabel(guiLabel);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUILabel* nativeInstance = new (cm_alloc<ScriptGUILabel>()) ScriptGUILabel(instance, guiLabel);
 	}
 
 	void ScriptGUILabel::internal_setContent(ScriptGUILabel* nativeInstance, MonoObject* content)
@@ -79,12 +75,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUILabel::internal_destroyInstance(ScriptGUILabel* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUILabel::internal_setVisible(ScriptGUILabel* nativeInstance, bool visible)
 	{
 		if(visible)

+ 13 - 32
SBansheeEngine/Source/BsScriptGUILayout.cpp

@@ -11,26 +11,18 @@
 
 namespace BansheeEngine
 {
-	ScriptGUILayout::ScriptGUILayout(GUILayout* layout, GUILayout* parentLayout)
-		:mLayout(layout), mParentLayout(parentLayout), mIsDestroyed(false)
+	ScriptGUILayout::ScriptGUILayout(MonoObject* instance, GUILayout* layout, GUILayout* parentLayout)
+		:ScriptObject(instance), mLayout(layout), mParentLayout(parentLayout), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUILayout::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUILayout", &ScriptGUILayout::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUILayout::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstanceXFromArea", &ScriptGUILayout::internal_createInstanceXFromArea);
 		metaData.scriptClass->addInternalCall("Internal_CreateInstanceXFromLayout", &ScriptGUILayout::internal_createInstanceXFromLayout);
 		metaData.scriptClass->addInternalCall("Internal_CreateInstanceYFromLayout", &ScriptGUILayout::internal_createInstanceYFromLayout);
 		metaData.scriptClass->addInternalCall("Internal_CreateInstanceYFromScrollArea", &ScriptGUILayout::internal_createInstanceYFromScrollArea);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUILayout::internal_destroyInstance);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUILayout::internal_destroy);
 		metaData.scriptClass->addInternalCall("Internal_SetVisible", &ScriptGUILayout::internal_setVisible);
@@ -51,16 +43,20 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUILayout::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUILayout::internal_createInstanceXFromArea(MonoObject* instance, MonoObject* parentArea)
 	{
 		ScriptGUIArea* scriptArea = ScriptGUIArea::toNative(parentArea);
 		GUIArea* nativeArea = scriptArea->getInternalValue();
 
 		ScriptGUILayout* nativeInstance = new (cm_alloc<ScriptGUILayout>()) 
-			ScriptGUILayout(&nativeArea->getLayout(), nullptr);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+			ScriptGUILayout(instance, &nativeArea->getLayout(), nullptr);
 	}
 
 	void ScriptGUILayout::internal_createInstanceXFromLayout(MonoObject* instance, MonoObject* parentLayout)
@@ -70,10 +66,7 @@ namespace BansheeEngine
 		GUILayout& layout = nativeLayout->addLayoutX();
 
 		ScriptGUILayout* nativeInstance = new (cm_alloc<ScriptGUILayout>()) 
-			ScriptGUILayout(&layout, nativeLayout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+			ScriptGUILayout(instance, &layout, nativeLayout);
 	}
 
 	void ScriptGUILayout::internal_createInstanceYFromLayout(MonoObject* instance, MonoObject* parentLayout)
@@ -83,10 +76,7 @@ namespace BansheeEngine
 		GUILayout& layout = nativeLayout->addLayoutY();
 
 		ScriptGUILayout* nativeInstance = new (cm_alloc<ScriptGUILayout>()) 
-			ScriptGUILayout(&layout, nativeLayout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+			ScriptGUILayout(instance, &layout, nativeLayout);
 	}
 
 	void ScriptGUILayout::internal_createInstanceYFromScrollArea(MonoObject* instance, MonoObject* parentScrollArea)
@@ -95,16 +85,7 @@ namespace BansheeEngine
 		GUILayout* nativeLayout = &scriptScrollArea->getInternalValue()->getLayout();
 
 		ScriptGUILayout* nativeInstance = new (cm_alloc<ScriptGUILayout>()) 
-			ScriptGUILayout(nativeLayout, nativeLayout);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUILayout::internal_destroyInstance(ScriptGUILayout* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
+			ScriptGUILayout(instance, nativeLayout, nativeLayout);
 	}
 
 	void ScriptGUILayout::internal_destroy(ScriptGUILayout* nativeInstance)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIListBox.cpp

@@ -20,23 +20,15 @@ namespace BansheeEngine
 {
 	ScriptGUIListBox::OnSelectionChangedThunkDef ScriptGUIListBox::onSelectionChangedThunk;
 
-	ScriptGUIListBox::ScriptGUIListBox(GUIListBox* listBox)
-		:mListBox(listBox), mIsDestroyed(false)
+	ScriptGUIListBox::ScriptGUIListBox(MonoObject* instance, GUIListBox* listBox)
+		:ScriptObject(instance), mListBox(listBox), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIListBox::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIListBox", &ScriptGUIListBox::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIListBox::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIListBox::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIListBox::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetElements", &ScriptGUIListBox::internal_setElements);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIListBox::internal_destroy);
@@ -57,6 +49,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIListBox::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIListBox::internal_createInstance(MonoObject* instance, MonoArray* elements, MonoString* style, MonoArray* guiOptions)
 	{
 		GUIOptions options;
@@ -83,10 +82,7 @@ namespace BansheeEngine
 		GUIListBox* guiListBox = GUIListBox::create(nativeElements, options, toString(MonoUtil::monoToWString(style)));
 		guiListBox->onSelectionChanged.connect(std::bind(&ScriptGUIListBox::onSelectionChanged, instance, std::placeholders::_1));
 
-		ScriptGUIListBox* nativeInstance = new (cm_alloc<ScriptGUIListBox>()) ScriptGUIListBox(guiListBox);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIListBox* nativeInstance = new (cm_alloc<ScriptGUIListBox>()) ScriptGUIListBox(instance, guiListBox);
 	}
 
 	void ScriptGUIListBox::internal_setElements(ScriptGUIListBox* nativeInstance, MonoArray* elements)
@@ -114,12 +110,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUIListBox::internal_destroyInstance(ScriptGUIListBox* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUIListBox::internal_setVisible(ScriptGUIListBox* nativeInstance, bool visible)
 	{
 		if(visible)

+ 3 - 18
SBansheeEngine/Source/BsScriptGUIPanel.cpp

@@ -9,36 +9,21 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIPanel::ScriptGUIPanel()
+	ScriptGUIPanel::ScriptGUIPanel(MonoObject* instance)
+		:ScriptObject(instance)
 	{
 
 	}
 
-	void ScriptGUIPanel::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIPanel", &ScriptGUIPanel::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIPanel::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIPanel::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIPanel::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetArea", &ScriptGUIPanel::internal_setArea);
 	}
 
 	void ScriptGUIPanel::internal_createInstance(MonoObject* instance)
 	{
-		ScriptGUIPanel* nativeInstance = new (cm_alloc<ScriptGUIPanel>()) ScriptGUIPanel();
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIPanel::internal_destroyInstance(ScriptGUIPanel* thisPtr)
-	{
-		cm_delete(thisPtr);
+		ScriptGUIPanel* nativeInstance = new (cm_alloc<ScriptGUIPanel>()) ScriptGUIPanel(instance);
 	}
 
 	void ScriptGUIPanel::internal_setArea(ScriptGUIPanel* thisPtr, INT32 x, INT32 y, UINT32 width, UINT32 height, UINT16 depth)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIScrollArea.cpp

@@ -17,23 +17,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIScrollArea::ScriptGUIScrollArea(GUIScrollArea* scrollArea)
-		:mScrollArea(scrollArea), mIsDestroyed(false)
+	ScriptGUIScrollArea::ScriptGUIScrollArea(MonoObject* instance, GUIScrollArea* scrollArea)
+		:ScriptObject(instance), mScrollArea(scrollArea), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIScrollArea::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIScrollArea", &ScriptGUIScrollArea::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIScrollArea::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIScrollArea::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIScrollArea::internal_destroyInstance);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUIScrollArea::internal_destroy);
 		metaData.scriptClass->addInternalCall("Internal_SetVisible", &ScriptGUIScrollArea::internal_setVisible);
@@ -51,6 +43,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIScrollArea::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIScrollArea::internal_createInstance(MonoObject* instance, ScrollBarType vertBarType, ScrollBarType horzBarType, 
 		MonoString* scrollBarStyle, MonoString* scrollAreaStyle, MonoArray* guiOptions)
 	{
@@ -63,16 +62,7 @@ namespace BansheeEngine
 		GUIScrollArea* guiScrollArea = GUIScrollArea::create(vertBarType, horzBarType, options, 
 			toString(MonoUtil::monoToWString(scrollBarStyle)), toString(MonoUtil::monoToWString(scrollAreaStyle)));
 
-		ScriptGUIScrollArea* nativeInstance = new (cm_alloc<ScriptGUIScrollArea>()) ScriptGUIScrollArea(guiScrollArea);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIScrollArea::internal_destroyInstance(ScriptGUIScrollArea* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
+		ScriptGUIScrollArea* nativeInstance = new (cm_alloc<ScriptGUIScrollArea>()) ScriptGUIScrollArea(instance, guiScrollArea);
 	}
 
 	void ScriptGUIScrollArea::internal_destroy(ScriptGUIScrollArea* nativeInstance)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUITexture.cpp

@@ -17,23 +17,15 @@
 
 namespace BansheeEngine
 {
-	ScriptGUITexture::ScriptGUITexture(GUITexture* texture)
-		:mTexture(texture), mIsDestroyed(false)
+	ScriptGUITexture::ScriptGUITexture(MonoObject* instance, GUITexture* texture)
+		:ScriptObject(instance), mTexture(texture), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUITexture::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUITexture", &ScriptGUITexture::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUITexture::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUITexture::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUITexture::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetTexture", &ScriptGUITexture::internal_setTexture);
 
 		metaData.scriptClass->addInternalCall("Internal_Destroy", &ScriptGUITexture::internal_destroy);
@@ -52,6 +44,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUITexture::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUITexture::internal_createInstance(MonoObject* instance, MonoObject* texture, 
 		GUIImageScaleMode scale, MonoString* style, MonoArray* guiOptions)
 	{
@@ -67,10 +66,7 @@ namespace BansheeEngine
 
 		GUITexture* guiTexture = GUITexture::create(nativeTexture, scale, options, toString(MonoUtil::monoToWString(style)));
 
-		ScriptGUITexture* nativeInstance = new (cm_alloc<ScriptGUITexture>()) ScriptGUITexture(guiTexture);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUITexture* nativeInstance = new (cm_alloc<ScriptGUITexture>()) ScriptGUITexture(instance, guiTexture);
 	}
 
 	void ScriptGUITexture::internal_setTexture(ScriptGUITexture* nativeInstance, MonoObject* texture)
@@ -87,12 +83,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUITexture::internal_destroyInstance(ScriptGUITexture* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUITexture::internal_setVisible(ScriptGUITexture* nativeInstance, bool visible)
 	{
 		if(visible)

+ 10 - 20
SBansheeEngine/Source/BsScriptGUIToggle.cpp

@@ -26,23 +26,15 @@ namespace BansheeEngine
 	ScriptGUIToggle::OnOutThunkDef ScriptGUIToggle::onOutThunk;
 	ScriptGUIToggle::OnToggledThunkDef ScriptGUIToggle::onToggledThunk;
 
-	ScriptGUIToggle::ScriptGUIToggle(GUIToggle* toggle)
-		:mToggle(toggle), mIsDestroyed(false)
+	ScriptGUIToggle::ScriptGUIToggle(MonoObject* instance, GUIToggle* toggle)
+		:ScriptObject(instance), mToggle(toggle), mIsDestroyed(false)
 	{
 
 	}
 
-	void ScriptGUIToggle::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIToggle", &ScriptGUIToggle::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIToggle::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIToggle::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIToggle::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetContent", &ScriptGUIToggle::internal_setContent);
 		metaData.scriptClass->addInternalCall("Internal_ToggleOn", &ScriptGUIToggle::internal_toggleOn);
 		metaData.scriptClass->addInternalCall("Internal_ToggleOff", &ScriptGUIToggle::internal_toggleOff);
@@ -68,6 +60,13 @@ namespace BansheeEngine
 		}
 	}
 
+	void ScriptGUIToggle::_onManagedInstanceDeleted()
+	{
+		destroy();
+
+		ScriptObject::_onManagedInstanceDeleted();
+	}
+
 	void ScriptGUIToggle::internal_createInstance(MonoObject* instance, MonoObject* content, 
 		MonoObject* toggleGroup, MonoString* style, MonoArray* guiOptions)
 	{
@@ -89,10 +88,7 @@ namespace BansheeEngine
 		guiToggle->onOut.connect(std::bind(&ScriptGUIToggle::onOut, instance));
 		guiToggle->onToggled.connect(std::bind(&ScriptGUIToggle::onToggled, instance, std::placeholders::_1));
 
-		ScriptGUIToggle* nativeInstance = new (cm_alloc<ScriptGUIToggle>()) ScriptGUIToggle(guiToggle);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptGUIToggle* nativeInstance = new (cm_alloc<ScriptGUIToggle>()) ScriptGUIToggle(instance, guiToggle);
 	}
 
 	void ScriptGUIToggle::internal_setContent(ScriptGUIToggle* nativeInstance, MonoObject* content)
@@ -116,12 +112,6 @@ namespace BansheeEngine
 		nativeInstance->destroy();
 	}
 
-	void ScriptGUIToggle::internal_destroyInstance(ScriptGUIToggle* nativeInstance)
-	{
-		nativeInstance->destroy();
-		cm_delete(nativeInstance);
-	}
-
 	void ScriptGUIToggle::internal_setVisible(ScriptGUIToggle* nativeInstance, bool visible)
 	{
 		if(visible)

+ 3 - 19
SBansheeEngine/Source/BsScriptGUIToggleGroup.cpp

@@ -9,37 +9,21 @@
 
 namespace BansheeEngine
 {
-	ScriptGUIToggleGroup::ScriptGUIToggleGroup(const std::shared_ptr<GUIToggleGroup>& toggleGroup)
-		:mToggleGroup(toggleGroup)
+	ScriptGUIToggleGroup::ScriptGUIToggleGroup(MonoObject* instance, const std::shared_ptr<GUIToggleGroup>& toggleGroup)
+		:ScriptObject(instance), mToggleGroup(toggleGroup)
 	{
 
 	}
 
-	void ScriptGUIToggleGroup::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "GUIToggleGroup", &ScriptGUIToggleGroup::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptGUIToggleGroup::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptGUIToggleGroup::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptGUIToggleGroup::internal_destroyInstance);
 	}
 
 	void ScriptGUIToggleGroup::internal_createInstance(MonoObject* instance)
 	{
 		std::shared_ptr<GUIToggleGroup> toggleGroup = GUIToggle::createToggleGroup();
 
-		ScriptGUIToggleGroup* nativeInstance = new (cm_alloc<ScriptGUIToggleGroup>()) ScriptGUIToggleGroup(toggleGroup);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptGUIToggleGroup::internal_destroyInstance(ScriptGUIToggleGroup* nativeInstance)
-	{
-		cm_delete(nativeInstance);
+		ScriptGUIToggleGroup* nativeInstance = new (cm_alloc<ScriptGUIToggleGroup>()) ScriptGUIToggleGroup(instance, toggleGroup);
 	}
 }

+ 2 - 10
SBansheeEngine/Source/BsScriptGameObjectManager.cpp

@@ -31,11 +31,7 @@ namespace BansheeEngine
 		if(findIter != mScriptGameObjects.end())
 			CM_EXCEPT(InvalidStateException, "Script component for this Component already exists.");
 
-		ScriptComponent* nativeInstance = new (cm_alloc<ScriptComponent>()) ScriptComponent(component);
-
-		nativeInstance->createInstance(component->getManagedInstance());
-		nativeInstance->metaData.thisPtrField->setValue(component->getManagedInstance(), &nativeInstance);
-
+		ScriptComponent* nativeInstance = new (cm_alloc<ScriptComponent>()) ScriptComponent(component->getManagedInstance(), component);
 		mScriptGameObjects[component->getInstanceId()] = nativeInstance;
 
 		return nativeInstance;
@@ -54,11 +50,7 @@ namespace BansheeEngine
 		if(findIter != mScriptGameObjects.end())
 			CM_EXCEPT(InvalidStateException, "Script SceneObject for this SceneObject already exists.");
 
-		ScriptSceneObject* nativeInstance = new (cm_alloc<ScriptSceneObject>()) ScriptSceneObject(sceneObject);
-
-		nativeInstance->createInstance(existingInstance);
-		nativeInstance->metaData.thisPtrField->setValue(existingInstance, &nativeInstance);
-
+		ScriptSceneObject* nativeInstance = new (cm_alloc<ScriptSceneObject>()) ScriptSceneObject(existingInstance, sceneObject);
 		mScriptGameObjects[sceneObject->getInstanceId()] = nativeInstance;
 
 		return nativeInstance;

+ 3 - 19
SBansheeEngine/Source/BsScriptHString.cpp

@@ -7,21 +7,13 @@
 
 namespace BansheeEngine
 {
-	ScriptHString::ScriptHString(const HString& string)
-		:mString(string)
+	ScriptHString::ScriptHString(MonoObject* instance, const HString& string)
+		:ScriptObject(instance), mString(string)
 	{ }
 
-	void ScriptHString::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "LocString", &ScriptHString::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptHString::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptHString::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptHString::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_SetParameter", &ScriptHString::internal_setParameter);
 		metaData.scriptClass->addInternalCall("Internal_GetValue", &ScriptHString::internal_getValue);
 	}
@@ -30,15 +22,7 @@ namespace BansheeEngine
 	{
 		HString string(MonoUtil::monoToWString(identifier));
 		
-		ScriptHString* nativeInstance = new (cm_alloc<ScriptHString>()) ScriptHString(string);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
-	}
-
-	void ScriptHString::internal_destroyInstance(ScriptHString* nativeInstance)
-	{
-		cm_delete(nativeInstance);
+		ScriptHString* nativeInstance = new (cm_alloc<ScriptHString>()) ScriptHString(instance, string);
 	}
 
 	void ScriptHString::internal_setParameter(HString* nativeInstance, UINT32 idx, MonoString* value)

+ 43 - 0
SBansheeEngine/Source/BsScriptObject.cpp

@@ -0,0 +1,43 @@
+#include "BsScriptObject.h"
+#include "BsMonoManager.h"
+#include "BsMonoField.h"
+
+namespace BansheeEngine
+{
+	ScriptMeta ScriptObjectBase::metaData;
+
+	ScriptObjectBase::ScriptObjectBase(MonoObject* instance)
+		:mManagedInstance(instance)
+	{	
+		ScriptObjectBase* param = this;
+
+		if(metaData.thisPtrField != nullptr)
+			metaData.thisPtrField->setValue(instance, &param);
+	}
+
+	ScriptObjectBase::~ScriptObjectBase() 
+	{
+		if(mManagedInstance != nullptr)
+			CM_EXCEPT(InvalidStateException, "Script object is being destroyed without its instance previously being released.");
+	}
+
+	void ScriptObjectBase::_onManagedInstanceDeleted()
+	{
+		cm_delete(this);
+	}
+
+	void ScriptObjectBase::registerTypeWithManager()
+	{
+		MonoManager::registerScriptType(&metaData);
+	}
+
+	void* ScriptObjectBase::getNativeInstance(MonoObject* managedInstance)
+	{
+		void* nativeInstance = nullptr;
+
+		if(metaData.thisPtrField != nullptr)
+			metaData.thisPtrField->getValue(managedInstance, &nativeInstance);
+
+		return nativeInstance;
+	}
+}

+ 21 - 0
SBansheeEngine/Source/BsScriptObjectImpl.cpp

@@ -0,0 +1,21 @@
+#include "BsScriptObjectImpl.h"
+#include "BsMonoManager.h"
+#include "BsMonoClass.h"
+#include "BsMonoUtil.h"
+
+namespace BansheeEngine
+{
+	ScriptObjectImpl::ScriptObjectImpl(MonoObject* instance)
+		:ScriptObject(instance)
+	{ }
+
+	void ScriptObjectImpl::initRuntimeData()
+	{
+		metaData.scriptClass->addInternalCall("Internal_ManagedInstanceDeleted", &ScriptObjectImpl::internal_managedInstanceDeleted);
+	}
+
+	void ScriptObjectImpl::internal_managedInstanceDeleted(ScriptObjectBase* instance)
+	{
+		instance->_onManagedInstanceDeleted();
+	}
+}

+ 2 - 8
SBansheeEngine/Source/BsScriptResourceManager.cpp

@@ -36,12 +36,9 @@ namespace BansheeEngine
 		const String& uuid = resourceHandle.getUUID();
 		throwExceptionIfInvalidOrDuplicate(uuid);
 
-		ScriptTexture2D* scriptResource = new (cm_alloc<ScriptTexture2D>()) ScriptTexture2D(resourceHandle);
+		ScriptTexture2D* scriptResource = new (cm_alloc<ScriptTexture2D>()) ScriptTexture2D(instance, resourceHandle);
 		mScriptResources[uuid] = scriptResource;
 
-		scriptResource->createInstance(instance);
-		scriptResource->metaData.thisPtrField->setValue(instance, &scriptResource);
-
 		return scriptResource;
 	}
 
@@ -57,12 +54,9 @@ namespace BansheeEngine
 		const String& uuid = resourceHandle.getUUID();
 		throwExceptionIfInvalidOrDuplicate(uuid);
 
-		ScriptSpriteTexture* scriptResource = new (cm_alloc<ScriptSpriteTexture>()) ScriptSpriteTexture(resourceHandle);
+		ScriptSpriteTexture* scriptResource = new (cm_alloc<ScriptSpriteTexture>()) ScriptSpriteTexture(instance, resourceHandle);
 		mScriptResources[uuid] = scriptResource;
 
-		scriptResource->createInstance(instance);
-		scriptResource->metaData.thisPtrField->setValue(instance, &scriptResource);
-
 		return scriptResource;
 	}
 

+ 7 - 15
SBansheeEngine/Source/BsScriptSceneObject.cpp

@@ -9,23 +9,15 @@
 
 namespace BansheeEngine
 {
-	ScriptSceneObject::ScriptSceneObject(const HSceneObject& sceneObject)
-		:mSceneObject(sceneObject)
+	ScriptSceneObject::ScriptSceneObject(MonoObject* instance, const HSceneObject& sceneObject)
+		:ScriptObject(instance), mSceneObject(sceneObject)
 	{
 
 	}
 
-	void ScriptSceneObject::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SceneObject", &ScriptSceneObject::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSceneObject::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptSceneObject::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSceneObject::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_GetParent", &ScriptSceneObject::internal_getParent);
 		metaData.scriptClass->addInternalCall("Internal_SetParent", &ScriptSceneObject::internal_setParent);
 		metaData.scriptClass->addInternalCall("Internal_GetNumChildren", &ScriptSceneObject::internal_getNumChildren);
@@ -39,11 +31,6 @@ namespace BansheeEngine
 		ScriptGameObjectManager::instance().createScriptSceneObject(instance, sceneObject);
 	}
 
-	void ScriptSceneObject::internal_destroyInstance(ScriptSceneObject* nativeInstance)
-	{
-		ScriptGameObjectManager::instance().destroyScriptGameObject(nativeInstance);
-	}
-
 	void ScriptSceneObject::internal_setParent(ScriptSceneObject* nativeInstance, MonoObject* parent)
 	{
 		ScriptSceneObject* parentScriptSO = ScriptSceneObject::toNative(parent);
@@ -85,6 +72,11 @@ namespace BansheeEngine
 		return childScriptSO->getManagedInstance();
 	}
 
+	void ScriptSceneObject::_onManagedInstanceDeleted()
+	{
+		ScriptGameObjectManager::instance().destroyScriptGameObject(this);
+	}
+
 	void ScriptSceneObject::setNativeHandle(const HGameObject& gameObject)
 	{
 		mSceneObject = static_object_cast<SceneObject>(gameObject);

+ 3 - 21
SBansheeEngine/Source/BsScriptSerializableArray.cpp

@@ -9,38 +9,26 @@
 
 namespace BansheeEngine
 {
-	ScriptSerializableArray::ScriptSerializableArray(const ManagedSerializableTypeInfoArrayPtr& typeInfo)
-		:mTypeInfo(typeInfo)
+	ScriptSerializableArray::ScriptSerializableArray(MonoObject* instance, const ManagedSerializableTypeInfoArrayPtr& typeInfo)
+		:ScriptObject(instance), mTypeInfo(typeInfo)
 	{
 
 	}
 
-	void ScriptSerializableArray::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SerializableArray", &ScriptSerializableArray::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSerializableArray::initRuntimeData()
 	{
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSerializableArray::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_CreateProperty", &ScriptSerializableArray::internal_createProperty);
 	}
 
 	ScriptSerializableArray* ScriptSerializableArray::create(const ManagedSerializableTypeInfoArrayPtr& typeInfo, MonoObject* object)
 	{
-		ScriptSerializableArray* nativeInstance = new (cm_alloc<ScriptSerializableArray>()) ScriptSerializableArray(typeInfo);
-
 		MonoType* monoInternalElementType = mono_class_get_type(typeInfo->mElementType->getMonoClass());
 		MonoReflectionType* internalElementType = mono_type_get_object(MonoManager::instance().getDomain(), monoInternalElementType);
 
 		void* params[2] = { object, internalElementType };
 		MonoObject* managedInstance = metaData.scriptClass->createInstance(params, 2);
 
-		nativeInstance->createInstance(managedInstance);
-
-		metaData.thisPtrField->setValue(managedInstance, &nativeInstance);
+		ScriptSerializableArray* nativeInstance = new (cm_alloc<ScriptSerializableArray>()) ScriptSerializableArray(managedInstance, typeInfo);
 
 		return nativeInstance;
 	}
@@ -51,10 +39,4 @@ namespace BansheeEngine
 
 		return newProperty->getManagedInstance();
 	}
-
-	void ScriptSerializableArray::internal_destroyInstance(ScriptSerializableArray* nativeInstance)
-	{
-		nativeInstance->~ScriptSerializableArray();
-		cm_free(nativeInstance);
-	}
 }

+ 3 - 20
SBansheeEngine/Source/BsScriptSerializableField.cpp

@@ -9,22 +9,14 @@
 
 namespace BansheeEngine
 {
-	ScriptSerializableField::ScriptSerializableField(const ManagedSerializableFieldInfoPtr& fieldInfo)
-		:mFieldInfo(fieldInfo)
+	ScriptSerializableField::ScriptSerializableField(MonoObject* instance, const ManagedSerializableFieldInfoPtr& fieldInfo)
+		:ScriptObject(instance), mFieldInfo(fieldInfo)
 	{
 
 	}
 
-	void ScriptSerializableField::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SerializableField", &ScriptSerializableField::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSerializableField::initRuntimeData()
 	{
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSerializableField::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_CreateProperty", &ScriptSerializableField::internal_createProperty);
 		metaData.scriptClass->addInternalCall("Internal_GetValue", &ScriptSerializableField::internal_getValue);
 		metaData.scriptClass->addInternalCall("Internal_SetValue", &ScriptSerializableField::internal_setValue);
@@ -40,20 +32,11 @@ namespace BansheeEngine
 		void* params[4] = { parentObject, monoStrName, &fieldFlags, internalType };
 		MonoObject* managedInstance = metaData.scriptClass->createInstance(params, 4);
 
-		ScriptSerializableField* nativeInstance = new (cm_alloc<ScriptSerializableField>()) ScriptSerializableField(fieldInfo);
-		nativeInstance->createInstance(managedInstance);
-
-		metaData.thisPtrField->setValue(managedInstance, &nativeInstance);
+		ScriptSerializableField* nativeInstance = new (cm_alloc<ScriptSerializableField>()) ScriptSerializableField(managedInstance, fieldInfo);
 
 		return nativeInstance;
 	}
 
-	void ScriptSerializableField::internal_destroyInstance(ScriptSerializableField* nativeInstance)
-	{
-		nativeInstance->~ScriptSerializableField();
-		cm_free(nativeInstance);
-	}
-
 	MonoObject* ScriptSerializableField::internal_createProperty(ScriptSerializableField* nativeInstance)
 	{
 		ScriptSerializableProperty* newProperty = ScriptSerializableProperty::create(nativeInstance->mFieldInfo->mTypeInfo);

+ 3 - 20
SBansheeEngine/Source/BsScriptSerializableObject.cpp

@@ -10,23 +10,15 @@ namespace BansheeEngine
 {
 	MonoField* ScriptSerializableObject::FieldsField = nullptr;
 
-	ScriptSerializableObject::ScriptSerializableObject(const ManagedSerializableTypeInfoPtr& typeInfo)
-		:mTypeInfo(typeInfo)
+	ScriptSerializableObject::ScriptSerializableObject(MonoObject* instance, const ManagedSerializableTypeInfoPtr& typeInfo)
+		:ScriptObject(instance), mTypeInfo(typeInfo)
 	{
 
 	}
 
-	void ScriptSerializableObject::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SerializableObject", &ScriptSerializableObject::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSerializableObject::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptSerializableObject::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSerializableObject::internal_destroyInstance);
 
 		FieldsField = metaData.scriptClass->getField("_fields");
 	}
@@ -62,10 +54,7 @@ namespace BansheeEngine
 		if(objInfo != nullptr)
 			typeInfo = objInfo->mTypeInfo;
 
-		ScriptSerializableObject* nativeInstance = new (cm_alloc<ScriptSerializableObject>()) ScriptSerializableObject(typeInfo);
-		nativeInstance->createInstance(instance);
-
-		metaData.thisPtrField->setValue(instance, &nativeInstance);
+		ScriptSerializableObject* nativeInstance = new (cm_alloc<ScriptSerializableObject>()) ScriptSerializableObject(instance, typeInfo);
 
 		if(objInfo != nullptr)
 		{
@@ -91,10 +80,4 @@ namespace BansheeEngine
 
 		return nativeInstance;
 	}
-
-	void ScriptSerializableObject::internal_destroyInstance(ScriptSerializableObject* nativeInstance)
-	{
-		nativeInstance->~ScriptSerializableObject();
-		cm_free(nativeInstance);
-	}
 }

+ 3 - 20
SBansheeEngine/Source/BsScriptSerializableProperty.cpp

@@ -10,22 +10,14 @@
 
 namespace BansheeEngine
 {
-	ScriptSerializableProperty::ScriptSerializableProperty(const ManagedSerializableTypeInfoPtr& typeInfo)
-		:mTypeInfo(typeInfo)
+	ScriptSerializableProperty::ScriptSerializableProperty(MonoObject* instance, const ManagedSerializableTypeInfoPtr& typeInfo)
+		:ScriptObject(instance), mTypeInfo(typeInfo)
 	{
 
 	}
 
-	void ScriptSerializableProperty::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SerializableProperty", &ScriptSerializableProperty::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSerializableProperty::initRuntimeData()
 	{
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSerializableProperty::internal_destroyInstance);
 		metaData.scriptClass->addInternalCall("Internal_CreateObject", &ScriptSerializableProperty::internal_createObject);
 		metaData.scriptClass->addInternalCall("Internal_CreateArray", &ScriptSerializableProperty::internal_createArray);
 	}
@@ -34,10 +26,7 @@ namespace BansheeEngine
 	{
 		MonoObject* managedInstance = metaData.scriptClass->createInstance();
 
-		ScriptSerializableProperty* nativeInstance = new (cm_alloc<ScriptSerializableProperty>()) ScriptSerializableProperty(typeInfo);
-		nativeInstance->createInstance(managedInstance);
-
-		metaData.thisPtrField->setValue(managedInstance, &nativeInstance);
+		ScriptSerializableProperty* nativeInstance = new (cm_alloc<ScriptSerializableProperty>()) ScriptSerializableProperty(managedInstance, typeInfo);
 
 		return nativeInstance;
 	}
@@ -56,10 +45,4 @@ namespace BansheeEngine
 
 		return newObject->getManagedInstance();
 	}
-
-	void ScriptSerializableProperty::internal_destroyInstance(ScriptSerializableProperty* nativeInstance)
-	{
-		nativeInstance->~ScriptSerializableProperty();
-		cm_free(nativeInstance);
-	}
 }

+ 4 - 12
SBansheeEngine/Source/BsScriptSpriteTexture.cpp

@@ -8,23 +8,15 @@
 
 namespace BansheeEngine
 {
-	ScriptSpriteTexture::ScriptSpriteTexture(const HSpriteTexture& texture)
-		:mTexture(texture)
+	ScriptSpriteTexture::ScriptSpriteTexture(MonoObject* instance,const HSpriteTexture& texture)
+		:ScriptObject(instance), mTexture(texture)
 	{
 
 	}
 
-	void ScriptSpriteTexture::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "SpriteTexture", &ScriptSpriteTexture::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptSpriteTexture::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptSpriteTexture::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptSpriteTexture::internal_destroyInstance);
 	}
 
 	void ScriptSpriteTexture::internal_createInstance(MonoObject* instance)
@@ -32,9 +24,9 @@ namespace BansheeEngine
 		ScriptResourceManager::instance().createScriptSpriteTexture(instance, SpriteTexture::dummy()); // TODO - DUMMY CODE!
 	}
 
-	void ScriptSpriteTexture::internal_destroyInstance(ScriptSpriteTexture* nativeInstance)
+	void ScriptSpriteTexture::_onManagedInstanceDeleted()
 	{
-		ScriptResourceManager::instance().destroyScriptResource(nativeInstance);
+		ScriptResourceManager::instance().destroyScriptResource(this);
 	}
 
 	void ScriptSpriteTexture::setNativeHandle(const HResource& resource) 

+ 3 - 5
SBansheeEngine/Source/BsScriptStringTable.cpp

@@ -7,12 +7,10 @@
 
 namespace BansheeEngine
 {
-	void ScriptStringTable::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "StringTable", &ScriptStringTable::initRuntimeData);
+	ScriptStringTable::ScriptStringTable(MonoObject* instance)
+		:ScriptObject(instance)
+	{ }
 
-		MonoManager::registerScriptType(&metaData);
-	}
 	void ScriptStringTable::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_GetActiveLanguage", &ScriptStringTable::internal_GetActiveLanguage);

+ 4 - 12
SBansheeEngine/Source/BsScriptTexture2D.cpp

@@ -10,23 +10,15 @@
 
 namespace BansheeEngine
 {
-	ScriptTexture2D::ScriptTexture2D(const HTexture& texture)
-		:mTexture(texture)
+	ScriptTexture2D::ScriptTexture2D(MonoObject* instance, const HTexture& texture)
+		:ScriptObject(instance), mTexture(texture)
 	{
 
 	}
 
-	void ScriptTexture2D::initMetaData()
-	{
-		metaData = ScriptMeta(BansheeEngineAssemblyName, "BansheeEngine", "Texture2D", &ScriptTexture2D::initRuntimeData);
-
-		MonoManager::registerScriptType(&metaData);
-	}
-
 	void ScriptTexture2D::initRuntimeData()
 	{
 		metaData.scriptClass->addInternalCall("Internal_CreateInstance", &ScriptTexture2D::internal_createInstance);
-		metaData.scriptClass->addInternalCall("Internal_DestroyInstance", &ScriptTexture2D::internal_destroyInstance);
 	}
 
 	void ScriptTexture2D::internal_createInstance(MonoObject* instance, UINT32 format, UINT32 width, UINT32 height, bool hasMipmaps, bool gammaCorrection)
@@ -53,9 +45,9 @@ namespace BansheeEngine
 		ScriptResourceManager::instance().createScriptTexture(instance, texture);
 	}
 
-	void ScriptTexture2D::internal_destroyInstance(ScriptTexture2D* nativeInstance)
+	void ScriptTexture2D::_onManagedInstanceDeleted()
 	{
-		ScriptResourceManager::instance().destroyScriptResource(nativeInstance);
+		ScriptResourceManager::instance().destroyScriptResource(this);
 	}
 
 	void ScriptTexture2D::setNativeHandle(const HResource& resource)