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

C#: Added GUIButton and GUITexture

Marko Pintera 12 лет назад
Родитель
Сommit
5f3e72c502

+ 2 - 0
BansheeEngine/Include/BsGUIInputBox.h

@@ -14,6 +14,8 @@ namespace BansheeEngine
 
 		static GUIInputBox* create(GUIWidget& parent, bool multiline = false, const GUIElementStyle* style = nullptr);
 		static GUIInputBox* create(GUIWidget& parent, const GUIOptions& layoutOptions, bool multiline = false, const GUIElementStyle* style = nullptr);
+
+		const CM::WString& getText() const { return mText; }
 	protected:
 		~GUIInputBox();
 

+ 7 - 3
BansheeEngine/Include/BsGUITexture.h

@@ -21,10 +21,14 @@ namespace BansheeEngine
 
 		static GUITexture* create(GUIWidget& parent, const HSpriteTexture& texture, GUIImageScaleMode scale = GUIImageScaleMode::StretchToFit, 
 			const GUIElementStyle* style = nullptr);
-		static GUITexture* create(GUIWidget& parent, const GUIOptions& layoutOptions, const HSpriteTexture& texture, 
-			GUIImageScaleMode scale = GUIImageScaleMode::StretchToFit, const GUIElementStyle* style = nullptr);
+		static GUITexture* create(GUIWidget& parent, const HSpriteTexture& texture, GUIImageScaleMode scale, 
+			const GUIOptions& layoutOptions, const GUIElementStyle* style = nullptr);
+		static GUITexture* create(GUIWidget& parent, const HSpriteTexture& texture, 
+			const GUIOptions& layoutOptions, const GUIElementStyle* style = nullptr);
+
 		static GUITexture* create(GUIWidget& parent, GUIImageScaleMode scale = GUIImageScaleMode::StretchToFit, const GUIElementStyle* style = nullptr);
-		static GUITexture* create(GUIWidget& parent, const GUIOptions& layoutOptions, GUIImageScaleMode scale = GUIImageScaleMode::StretchToFit, const GUIElementStyle* style = nullptr);
+		static GUITexture* create(GUIWidget& parent, GUIImageScaleMode scale, const GUIOptions& layoutOptions, const GUIElementStyle* style = nullptr);
+		static GUITexture* create(GUIWidget& parent, const GUIOptions& layoutOptions, const GUIElementStyle* style = nullptr);
 
 		void setTexture(const HSpriteTexture& texture);
 	protected:

+ 26 - 3
BansheeEngine/Source/BsGUITexture.cpp

@@ -50,8 +50,8 @@ namespace BansheeEngine
 		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, texture, scale, GUILayoutOptions::create(style));
 	}
 
-	GUITexture* GUITexture::create(GUIWidget& parent, const GUIOptions& layoutOptions, const HSpriteTexture& texture, 
-		GUIImageScaleMode scale, const GUIElementStyle* style)
+	GUITexture* GUITexture::create(GUIWidget& parent, const HSpriteTexture& texture, 
+		GUIImageScaleMode scale, const GUIOptions& layoutOptions, const GUIElementStyle* style)
 	{
 		if(style == nullptr)
 		{
@@ -62,6 +62,18 @@ namespace BansheeEngine
 		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, texture, scale, GUILayoutOptions::create(layoutOptions, style));
 	}
 
+	GUITexture* GUITexture::create(GUIWidget& parent, const HSpriteTexture& texture, 
+		const GUIOptions& layoutOptions, const GUIElementStyle* style)
+	{
+		if(style == nullptr)
+		{
+			const GUISkin& skin = parent.getSkin();
+			style = skin.getStyle(getGUITypeName());
+		}
+
+		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, texture, GUIImageScaleMode::StretchToFit, GUILayoutOptions::create(layoutOptions, style));
+	}
+
 	GUITexture* GUITexture::create(GUIWidget& parent, GUIImageScaleMode scale, const GUIElementStyle* style)
 	{
 		if(style == nullptr)
@@ -73,7 +85,7 @@ namespace BansheeEngine
 		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, HSpriteTexture(), scale, GUILayoutOptions::create(style));
 	}
 
-	GUITexture* GUITexture::create(GUIWidget& parent, const GUIOptions& layoutOptions, GUIImageScaleMode scale, const GUIElementStyle* style)
+	GUITexture* GUITexture::create(GUIWidget& parent, GUIImageScaleMode scale, const GUIOptions& layoutOptions, const GUIElementStyle* style)
 	{
 		if(style == nullptr)
 		{
@@ -84,6 +96,17 @@ namespace BansheeEngine
 		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, HTexture(), scale, GUILayoutOptions::create(layoutOptions, style));
 	}
 
+	GUITexture* GUITexture::create(GUIWidget& parent, const GUIOptions& layoutOptions, const GUIElementStyle* style)
+	{
+		if(style == nullptr)
+		{
+			const GUISkin& skin = parent.getSkin();
+			style = skin.getStyle(getGUITypeName());
+		}
+
+		return new (cm_alloc<GUITexture, PoolAlloc>()) GUITexture(parent, style, HTexture(), GUIImageScaleMode::StretchToFit, GUILayoutOptions::create(layoutOptions, style));
+	}
+
 	void GUITexture::setTexture(const HSpriteTexture& texture)
 	{
 		mActiveTexture = texture;

+ 5 - 0
BansheeMono/Include/BsMonoUtil.h

@@ -39,6 +39,11 @@ namespace BansheeEngine
 			return monoString;
 		}
 
+		static void throwIfException(MonoException* exception)
+		{
+			throwIfException(reinterpret_cast<MonoObject*>(exception));
+		}
+
 		static void throwIfException(MonoObject* exception)
 		{
 			if(exception != nullptr)

+ 15 - 10
CSharpWrap.txt

@@ -92,17 +92,20 @@ Eventually make all math classes templates that work on both doubles and floats.
 ----------------------------
 
 Implement:
- - Button
- - Texture
- - RenderTexture
- - Toggle
- - TextField
- - ListBox
- - DropDownBox
- - ScrollArea
+ - GUIInputBox
+  - getText
+
+ - GUIListBox
+  - onSelectionChanged
+
+ - GUIScrollArea
 
- - Space
- - FlexibleSpace
+ - GUIRenderTexture
+  - RenderTexture (?)
+
+ - GUIToggle
+  - onToggled
+  - ToggleGroup (?)
 
  - Destroy()
  - GUISkin
@@ -114,6 +117,8 @@ Implement:
  - Implement C# Font
  - Implement C# SpriteTexture
 
+ - Need a way to update Listbox after it has been created (C++ and C#)
+
 When loading resources I need to be able to load both project resources and engine ones. 
  - BuiltinResources can be used for accessing default resources like GUI skin textures and similar
  - They're all loaded from a special folder that is set in EditorApplication

+ 2 - 2
CamelotClient/Source/BsGUIMenuBar.cpp

@@ -26,8 +26,8 @@ namespace BansheeEditor
 		mBackgroundArea = GUIArea::create(*parent, 0, 0, 1, 13, 9900);
 		mMainArea = GUIArea::create(*parent, 0, 0, 1, 13, 9899);
 
-		mBgTexture = GUITexture::create(*parent, GUIOptions(GUIOption::flexibleWidth(), GUIOption::flexibleHeight()), 
-			GUIImageScaleMode::StretchToFit, EngineGUI::instance().getSkin().getStyle("MenuBarBg"));
+		mBgTexture = GUITexture::create(*parent, GUIImageScaleMode::StretchToFit, GUIOptions(GUIOption::flexibleWidth(), GUIOption::flexibleHeight()),
+			EngineGUI::instance().getSkin().getStyle("MenuBarBg"));
 		mBackgroundArea->getLayout().addElement(mBgTexture);
 
 		mLogoTexture = GUITexture::create(*parent, GUIImageScaleMode::StretchToFit, EngineGUI::instance().getSkin().getStyle("MenuBarBansheeLogo"));

+ 2 - 2
CamelotClient/Source/BsGUIWindowFrameWidget.cpp

@@ -22,8 +22,8 @@ namespace BansheeEditor
 		setSkin(skin);
 
 		GUIArea* backgroundArea = GUIArea::createStretchedXY(*this, 0, 0, 0, 0, 500);
-		backgroundArea->getLayout().addElement(GUITexture::create(*this, GUIOptions(GUIOption::flexibleWidth(), GUIOption::flexibleHeight()), 
-			GUIImageScaleMode::RepeatToFit, getSkin().getStyle("WindowBackground")));
+		backgroundArea->getLayout().addElement(GUITexture::create(*this, GUIImageScaleMode::RepeatToFit, 
+			GUIOptions(GUIOption::flexibleWidth(), GUIOption::flexibleHeight()), getSkin().getStyle("WindowBackground")));
 
 		mWindowFrameArea = GUIArea::createStretchedXY(*this, 0, 0, 0, 0, 499);
 

+ 8 - 0
MBansheeEditor/ProjectSelectWindow.cs

@@ -14,6 +14,14 @@ namespace BansheeEditor
         {
             GUILabel label = GUI.main.AddLabel("Test test");
             label.SetContent("Test2");
+
+            GUIButton button = GUI.main.AddButton("CLICK ME");
+            button.OnClick += button_OnClick;
+        }
+
+        void button_OnClick()
+        {
+            throw new NotImplementedException();
         }
     }
 }

+ 50 - 0
MBansheeEngine/GUIButton.cs

@@ -0,0 +1,50 @@
+using System;
+using System.Runtime.CompilerServices;
+
+namespace BansheeEngine
+{
+    public sealed class GUIButton : ScriptObject
+    {
+        public delegate void OnClickDelegate();
+        public delegate void OnHoverDelegate();
+        public delegate void OnOutDelegate();
+
+        public event OnClickDelegate OnClick;
+        public event OnHoverDelegate OnHover;
+        public event OnOutDelegate OnOut;
+
+        internal GUIButton(GUILayout parentLayout, GUIContent content, GUIElementStyle style, params GUIOption[] options)
+        {
+            Internal_CreateInstance(this, parentLayout, content, style, options);
+        }
+
+        public void SetContent(GUIContent content)
+        {
+            Internal_SetContent(mCachedPtr, content);
+        }
+
+        private void DoOnClick()
+        {
+            if (OnClick != null)
+                OnClick();
+        }
+
+        private void DoOnHover()
+        {
+            if (OnHover != null)
+                OnHover();
+        }
+
+        private void DoOnOut()
+        {
+            if (OnOut != null)
+                OnOut();
+        }
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern void Internal_CreateInstance(GUIButton instance, GUILayout layout, GUIContent content, GUIElementStyle style, GUIOption[] options);
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern void Internal_SetContent(IntPtr nativeInstance, GUIContent content);
+    }
+}

+ 44 - 4
MBansheeEngine/GUILayout.cs

@@ -10,14 +10,54 @@ namespace BansheeEngine
             return new GUILabel(this, content, style, options);
         }
 
-        public GUILabel AddLabel(GUIContent content, GUIElementStyle style)
+        public GUILabel AddLabel(GUIContent content, params GUIOption[] options)
         {
-            return new GUILabel(this, content, style, new GUIOption[0]);
+            return new GUILabel(this, content, null, options);
         }
 
-        public GUILabel AddLabel(GUIContent content, params GUIOption[] options)
+        public GUIButton AddButton(GUIContent content, GUIElementStyle style, params GUIOption[] options)
         {
-            return new GUILabel(this, content, null, options);
+            return new GUIButton(this, content, style, options);
+        }
+
+        public GUIButton AddButton(GUIContent content, GUIElementStyle style)
+        {
+            return new GUIButton(this, content, style, new GUIOption[0]);
+        }
+
+        public GUIButton AddButton(GUIContent content, params GUIOption[] options)
+        {
+            return new GUIButton(this, content, null, options);
+        }
+
+        public GUITexture AddTexture(SpriteTexture texture, GUIImageScaleMode scale, GUIElementStyle style, params GUIOption[] options)
+        {
+            return new GUITexture(this, texture, scale, style, options);
+        }
+
+        public GUITexture AddTexture(SpriteTexture texture, GUIImageScaleMode scale, params GUIOption[] options)
+        {
+            return new GUITexture(this, texture, scale, null, options);
+        }
+
+        public GUITexture AddTexture(SpriteTexture texture, GUIElementStyle style, params GUIOption[] options)
+        {
+            return new GUITexture(this, texture, GUIImageScaleMode.StretchToFit, style, options);
+        }
+
+        public GUITexture AddTexture(SpriteTexture texture, params GUIOption[] options)
+        {
+            return new GUITexture(this, texture, GUIImageScaleMode.StretchToFit, null, options);
+        }
+
+        public GUIFixedSpace AddSpace(int size)
+        {
+            return new GUIFixedSpace(this, size);
+        }
+
+        public GUIFlexibleSpace AddFlexibleSpace()
+        {
+            return new GUIFlexibleSpace(this);
         }
 
         [MethodImpl(MethodImplOptions.InternalCall)]

+ 34 - 0
MBansheeEngine/GUITexture.cs

@@ -0,0 +1,34 @@
+using System;
+using System.Runtime.CompilerServices;
+
+namespace BansheeEngine
+{
+    public enum GUIImageScaleMode
+	{
+		StretchToFit,
+		ScaleToFit,
+		CropToFit,
+		RepeatToFit
+	};
+
+
+    public sealed class GUITexture : ScriptObject
+    {
+        internal GUITexture(GUILayout parentLayout, SpriteTexture texture, GUIImageScaleMode scale, GUIElementStyle style, params GUIOption[] options)
+        {
+            Internal_CreateInstance(this, parentLayout, texture, scale, style, options);
+        }
+
+        public void SetTexture(SpriteTexture texture)
+        {
+            Internal_SetTexture(mCachedPtr, texture);
+        }
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern void Internal_CreateInstance(GUITexture instance, GUILayout layout, SpriteTexture texture, 
+            GUIImageScaleMode scale, GUIElementStyle style, GUIOption[] options);
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern void Internal_SetTexture(IntPtr nativeInstance, SpriteTexture texture);
+    }
+}

+ 2 - 0
MBansheeEngine/MBansheeEngine.csproj

@@ -48,6 +48,7 @@
     <Compile Include="GUI.cs" />
     <Compile Include="GUIArea.cs" />
     <Compile Include="GUIBase.cs" />
+    <Compile Include="GUIButton.cs" />
     <Compile Include="GUIContent.cs" />
     <Compile Include="GUIElementStateStyle.cs" />
     <Compile Include="GUIElementStyle.cs" />
@@ -58,6 +59,7 @@
     <Compile Include="GUIOption.cs" />
     <Compile Include="GUISkin.cs" />
     <Compile Include="GUISpace.cs" />
+    <Compile Include="GUITexture.cs" />
     <Compile Include="GUIWidget.cs" />
     <Compile Include="HString.cs" />
     <Compile Include="MathEx.cs" />

+ 1 - 1
Notes.txt

@@ -65,7 +65,7 @@ Reminders:
     - This would probably come with an overhead of at least one extra function call for each script call, which is currently unacceptable 
 	  considering that most people will definitely won't be writing new script systems.
   - Perhaps add code generation functionality to the engine through Mono? I know Mono has support for it though its Embed interface
-
+  - Add instancing to engine: All I really need to add are per-instance attributes in VertexData (and MeshData). And then RenderSystem::renderInstance method that also accepts an instance count.
 
 Potential optimizations:
  - bulkPixelConversion is EXTREMELY poorly unoptimized. Each pixel it calls a separate method that does redudant operations every pixel.

+ 39 - 0
SBansheeEngine/Include/BsScriptGUIButton.h

@@ -0,0 +1,39 @@
+#pragma once
+
+#include "BsScriptEnginePrerequisites.h"
+#include "BsScriptObject.h"
+
+namespace BansheeEngine
+{
+	class BS_SCR_BE_EXPORT ScriptGUIButton : public ScriptObject<ScriptGUIButton>
+	{
+	public:
+		static void initMetaData();
+
+		GUIButton* getInternalValue() const { return mButton; }
+		void* getNativeRaw() const { return mButton; }
+
+	private:
+		static void internal_createInstance(MonoObject* instance, MonoObject* parentLayout, MonoObject* content, MonoObject* style, MonoArray* guiOptions);
+		static void internal_destroyInstance(ScriptGUIButton* nativeInstance);
+		static void internal_setContent(ScriptGUIButton* nativeInstance, MonoObject* content);
+
+		static void initRuntimeData();
+
+		static void onClick(MonoObject* instance);
+		static void onHover(MonoObject* instance);
+		static void onOut(MonoObject* instance);
+
+		ScriptGUIButton(GUIButton* button);
+
+		GUIButton* mButton;
+
+		typedef void (__stdcall *OnClickThunkDef) (MonoObject*, MonoException**);
+		typedef void (__stdcall *OnHoverThunkDef) (MonoObject*, MonoException**);
+		typedef void (__stdcall *OnOutThunkDef) (MonoObject*, MonoException**);
+
+		static OnClickThunkDef onClickThunk;
+		static OnHoverThunkDef onHoverThunk;
+		static OnOutThunkDef onOutThunk;
+	};
+}

+ 1 - 1
SBansheeEngine/Include/BsScriptGUIContent.h

@@ -12,7 +12,7 @@ namespace BansheeEngine
 
 		static const CM::HString& getText(MonoObject* instance);
 		static const CM::HString& getTooltip(MonoObject* instance);
-		static const HSpriteTexture& getImage(MonoObject* instance);
+		static HSpriteTexture getImage(MonoObject* instance);
 
 	private:
 		static void initRuntimeData();

+ 29 - 0
SBansheeEngine/Include/BsScriptGUITexture.h

@@ -0,0 +1,29 @@
+#pragma once
+
+#include "BsScriptEnginePrerequisites.h"
+#include "BsScriptObject.h"
+#include "BsGUITexture.h"
+
+namespace BansheeEngine
+{
+	class BS_SCR_BE_EXPORT ScriptGUITexture : public ScriptObject<ScriptGUITexture>
+	{
+	public:
+		static void initMetaData();
+
+		GUITexture* getInternalValue() const { return mTexture; }
+		void* getNativeRaw() const { return mTexture; }
+
+	private:
+		static void internal_createInstance(MonoObject* instance, MonoObject* parentLayout, MonoObject* texture, 
+			GUIImageScaleMode scale, MonoObject* style, MonoArray* guiOptions);
+		static void internal_destroyInstance(ScriptGUITexture* nativeInstance);
+		static void internal_setTexture(ScriptGUITexture* nativeInstance, MonoObject* texture);
+
+		static void initRuntimeData();
+
+		ScriptGUITexture(GUITexture* texture);
+
+		GUITexture* mTexture;
+	};
+}

+ 4 - 0
SBansheeEngine/SBansheeEngine.vcxproj

@@ -227,6 +227,7 @@
   </ItemDefinitionGroup>
   <ItemGroup>
     <ClInclude Include="Include\BsScriptEnginePrerequisites.h" />
+    <ClInclude Include="Include\BsScriptGUIButton.h" />
     <ClInclude Include="Include\BsScriptGUIFixedSpace.h" />
     <ClInclude Include="Include\BsScriptGUIFlexibleSpace.h" />
     <ClInclude Include="Include\BsScriptFont.h" />
@@ -236,6 +237,7 @@
     <ClInclude Include="Include\BsScriptGUIElementStyle.h" />
     <ClInclude Include="Include\BsScriptGUILabel.h" />
     <ClInclude Include="Include\BsScriptGUILayout.h" />
+    <ClInclude Include="Include\BsScriptGUITexture.h" />
     <ClInclude Include="Include\BsScriptHString.h" />
     <ClInclude Include="Include\BsScriptMacros.h" />
     <ClInclude Include="Include\BsScriptObject.h" />
@@ -246,6 +248,7 @@
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="Source\BsScriptEnginePlugin.cpp" />
+    <ClCompile Include="Source\BsScriptGUIButton.cpp" />
     <ClCompile Include="Source\BsScriptGUIFixedSpace.cpp" />
     <ClCompile Include="Source\BsScriptGUIFlexibleSpace.cpp" />
     <ClCompile Include="Source\BsScriptFont.cpp" />
@@ -255,6 +258,7 @@
     <ClCompile Include="Source\BsScriptGUIElementStyle.cpp" />
     <ClCompile Include="Source\BsScriptGUILabel.cpp" />
     <ClCompile Include="Source\BsScriptGUILayout.cpp" />
+    <ClCompile Include="Source\BsScriptGUITexture.cpp" />
     <ClCompile Include="Source\BsScriptHString.cpp" />
     <ClCompile Include="Source\BsScriptSpriteTexture.cpp" />
     <ClCompile Include="Source\BsScriptStringTable.cpp" />

+ 12 - 0
SBansheeEngine/SBansheeEngine.vcxproj.filters

@@ -66,6 +66,12 @@
     <ClInclude Include="Include\BsScriptGUIFlexibleSpace.h">
       <Filter>Header Files</Filter>
     </ClInclude>
+    <ClInclude Include="Include\BsScriptGUIButton.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="Include\BsScriptGUITexture.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="Source\BsScriptTexture2D.cpp">
@@ -113,5 +119,11 @@
     <ClCompile Include="Source\BsScriptGUIFlexibleSpace.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
+    <ClCompile Include="Source\BsScriptGUITexture.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="Source\BsScriptGUIButton.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
   </ItemGroup>
 </Project>

+ 115 - 0
SBansheeEngine/Source/BsScriptGUIButton.cpp

@@ -0,0 +1,115 @@
+#include "BsScriptGUIButton.h"
+#include "BsScriptMeta.h"
+#include "BsMonoField.h"
+#include "BsMonoClass.h"
+#include "BsMonoManager.h"
+#include "BsMonoMethod.h"
+#include "BsSpriteTexture.h"
+#include "BsMonoUtil.h"
+#include "BsGUILayout.h"
+#include "BsGUIButton.h"
+#include "BsGUIOptions.h"
+#include "BsScriptGUIElementStyle.h"
+#include "BsScriptGUILayout.h"
+#include "BsScriptGUIArea.h"
+#include "BsScriptHString.h"
+#include "BsScriptGUIContent.h"
+
+using namespace CamelotFramework;
+
+namespace BansheeEngine
+{
+	ScriptGUIButton::OnClickThunkDef ScriptGUIButton::onClickThunk;
+	ScriptGUIButton::OnHoverThunkDef ScriptGUIButton::onHoverThunk;
+	ScriptGUIButton::OnOutThunkDef ScriptGUIButton::onOutThunk;
+
+	ScriptGUIButton::ScriptGUIButton(GUIButton* button)
+		:mButton(button)
+	{
+
+	}
+
+	void ScriptGUIButton::initMetaData()
+	{
+		metaData = ScriptMeta("MBansheeEngine", "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);
+
+		onClickThunk = (OnClickThunkDef)metaData.scriptClass->getMethod("DoOnClick").getThunk();
+		onHoverThunk = (OnHoverThunkDef)metaData.scriptClass->getMethod("DoOnHover").getThunk();
+		onOutThunk = (OnOutThunkDef)metaData.scriptClass->getMethod("DoOnOut").getThunk();
+	}
+
+	void ScriptGUIButton::internal_createInstance(MonoObject* instance, MonoObject* parentLayout, MonoObject* content, MonoObject* style, MonoArray* guiOptions)
+	{
+		ScriptGUILayout* scriptLayout = ScriptGUILayout::toNative(parentLayout);
+		GUIOptions options;
+
+		UINT32 arrayLen = (UINT32)mono_array_length(guiOptions);
+		for(UINT32 i = 0; i < arrayLen; i++)
+			options.addOption(mono_array_get(guiOptions, GUIOption, i));
+
+		GUIElementStyle* elemStyle = nullptr;
+
+		if(style != nullptr)
+			elemStyle = ScriptGUIElementStyle::toNative(style)->getInternalValue();
+
+		GUIContent nativeContent(ScriptGUIContent::getText(content), ScriptGUIContent::getImage(content), ScriptGUIContent::getTooltip(content));
+		GUIButton* guiButton = GUIButton::create(scriptLayout->getParentArea()->getParentWidget(), nativeContent, options, elemStyle);
+
+		guiButton->onClick.connect(std::bind(&ScriptGUIButton::onClick, instance));
+		guiButton->onHover.connect(std::bind(&ScriptGUIButton::onHover, instance));
+		guiButton->onOut.connect(std::bind(&ScriptGUIButton::onOut, instance));
+
+		GUILayout* nativeLayout = scriptLayout->getInternalValue();
+		nativeLayout->addElement(guiButton);
+
+		ScriptGUIButton* nativeInstance = new (cm_alloc<ScriptGUIButton>()) ScriptGUIButton(guiButton);
+		nativeInstance->createInstance(instance);
+
+		metaData.thisPtrField->setValue(instance, nativeInstance);
+	}
+
+	void ScriptGUIButton::internal_destroyInstance(ScriptGUIButton* nativeInstance)
+	{
+		nativeInstance->destroyInstance();
+		cm_delete(nativeInstance);
+	}
+
+	void ScriptGUIButton::internal_setContent(ScriptGUIButton* nativeInstance, MonoObject* content)
+	{
+		GUIContent nativeContent(ScriptGUIContent::getText(content), ScriptGUIContent::getImage(content), ScriptGUIContent::getTooltip(content));
+		nativeInstance->getInternalValue()->setContent(nativeContent);
+	}
+
+	void ScriptGUIButton::onClick(MonoObject* instance)
+	{
+		MonoException* exception = nullptr;
+		onClickThunk(instance, &exception);
+
+		MonoUtil::throwIfException(exception);
+	}
+
+	void ScriptGUIButton::onHover(MonoObject* instance)
+	{
+		MonoException* exception = nullptr;
+		onHoverThunk(instance, &exception);
+
+		MonoUtil::throwIfException(exception);
+	}
+
+	void ScriptGUIButton::onOut(MonoObject* instance)
+	{
+		MonoException* exception = nullptr;
+		onOutThunk(instance, &exception);
+
+		MonoUtil::throwIfException(exception);
+	}
+}

+ 2 - 2
SBansheeEngine/Source/BsScriptGUIContent.cpp

@@ -53,12 +53,12 @@ namespace BansheeEngine
 		return tooltipScript->getInternalValue();
 	}
 
-	const HSpriteTexture& ScriptGUIContent::getImage(MonoObject* instance)
+	HSpriteTexture ScriptGUIContent::getImage(MonoObject* instance)
 	{
 		MonoObject* imageManaged = (MonoObject*)mImageField->getValue(instance);
 
 		if(imageManaged == nullptr)
-			return SpriteTexture::dummy();
+			return HSpriteTexture();
 
 		ScriptSpriteTexture* imageScript = ScriptSpriteTexture::toNative(imageManaged);
 		return imageScript->getInternalValue();

+ 85 - 0
SBansheeEngine/Source/BsScriptGUITexture.cpp

@@ -0,0 +1,85 @@
+#include "BsScriptGUITexture.h"
+#include "BsScriptMeta.h"
+#include "BsMonoField.h"
+#include "BsMonoClass.h"
+#include "BsMonoManager.h"
+#include "BsSpriteTexture.h"
+#include "BsMonoUtil.h"
+#include "BsGUILayout.h"
+#include "BsGUITexture.h"
+#include "BsGUIOptions.h"
+#include "BsScriptSpriteTexture.h"
+#include "BsScriptGUIElementStyle.h"
+#include "BsScriptGUILayout.h"
+#include "BsScriptGUIArea.h"
+#include "BsScriptHString.h"
+#include "BsScriptGUIContent.h"
+
+using namespace CamelotFramework;
+
+namespace BansheeEngine
+{
+	ScriptGUITexture::ScriptGUITexture(GUITexture* texture)
+		:mTexture(texture)
+	{
+
+	}
+
+	void ScriptGUITexture::initMetaData()
+	{
+		metaData = ScriptMeta("MBansheeEngine", "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);
+	}
+
+	void ScriptGUITexture::internal_createInstance(MonoObject* instance, MonoObject* parentLayout, MonoObject* texture, 
+		GUIImageScaleMode scale, MonoObject* style, MonoArray* guiOptions)
+	{
+		ScriptGUILayout* scriptLayout = ScriptGUILayout::toNative(parentLayout);
+		GUIOptions options;
+
+		UINT32 arrayLen = (UINT32)mono_array_length(guiOptions);
+		for(UINT32 i = 0; i < arrayLen; i++)
+			options.addOption(mono_array_get(guiOptions, GUIOption, i));
+
+		GUIElementStyle* elemStyle = nullptr;
+
+		if(style != nullptr)
+			elemStyle = ScriptGUIElementStyle::toNative(style)->getInternalValue();
+
+		HSpriteTexture nativeTexture;
+		if(texture != nullptr)
+			nativeTexture = ScriptSpriteTexture::toNative(texture)->getInternalValue();
+
+		GUITexture* guiTexture = GUITexture::create(scriptLayout->getParentArea()->getParentWidget(), nativeTexture, scale, options, elemStyle);
+		GUILayout* nativeLayout = scriptLayout->getInternalValue();
+		nativeLayout->addElement(guiTexture);
+
+		ScriptGUITexture* nativeInstance = new (cm_alloc<ScriptGUITexture>()) ScriptGUITexture(guiTexture);
+		nativeInstance->createInstance(instance);
+
+		metaData.thisPtrField->setValue(instance, nativeInstance);
+	}
+
+	void ScriptGUITexture::internal_destroyInstance(ScriptGUITexture* nativeInstance)
+	{
+		nativeInstance->destroyInstance();
+		cm_delete(nativeInstance);
+	}
+
+	void ScriptGUITexture::internal_setTexture(ScriptGUITexture* nativeInstance, MonoObject* texture)
+	{
+		HSpriteTexture nativeTexture;
+		if(texture != nullptr)
+			nativeTexture = ScriptSpriteTexture::toNative(texture)->getInternalValue();
+
+		nativeInstance->getInternalValue()->setTexture(nativeTexture);
+	}
+}