فهرست منبع

Inspector will not try to display multi-rank arrays as it doesn't support them yet
Text fields can now be multiline

Marko Pintera 11 سال پیش
والد
کامیت
c0b00d66fb

+ 43 - 3
BansheeEditor/Include/BsGUITextField.h

@@ -1,19 +1,55 @@
 #pragma once
 
 #include "BsEditorPrerequisites.h"
-#include "BsGUIFieldBase.h"
+#include "BsGUIElementContainer.h"
 
 namespace BansheeEngine
 {
-	class BS_ED_EXPORT GUITextField : public TGUIField<GUITextField>
+	class BS_ED_EXPORT GUITextField : public GUIElementContainer
 	{
+		struct PrivatelyConstruct {};
+
 	public:
+		static const String& getLabelStyleType();
 		static const String& getGUITypeName();
 		static const String& getInputStyleType();
 
-		GUITextField(const PrivatelyConstruct& dummy, const GUIContent& labelContent, UINT32 labelWidth,
+		static GUITextField* create(bool multiline, const GUIContent& labelContent, UINT32 labelWidth, const GUIOptions& layoutOptions,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const GUIContent& labelContent, const GUIOptions& layoutOptions,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const HString& labelText, UINT32 labelWidth, const GUIOptions& layoutOptions,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const HString& labelText, const GUIOptions& layoutOptions,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const GUIOptions& layoutOptions, const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const GUIContent& labelContent, UINT32 labelWidth,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const GUIContent& labelContent,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const HString& labelText, UINT32 labelWidth,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const HString& labelText,
+			const String& style = StringUtil::BLANK);
+
+		static GUITextField* create(bool multiline, const String& style = StringUtil::BLANK);
+
+		GUITextField(const PrivatelyConstruct& dummy, bool multiline, const GUIContent& labelContent, UINT32 labelWidth,
 			const String& style, const GUILayoutOptions& layoutOptions, bool withLabel);
 
+		void _updateLayoutInternal(INT32 x, INT32 y, UINT32 width, UINT32 height,
+			RectI clipRect, UINT8 widgetDepth, UINT16 areaDepth);
+
+		Vector2I _getOptimalSize() const;
+
 		WString getValue() const { return mValue; }
 		void setValue(const WString& value);
 
@@ -21,6 +57,8 @@ namespace BansheeEngine
 
 		Event<void(const WString&)> onValueChanged;
 	protected:
+		static const UINT32 DEFAULT_LABEL_WIDTH;
+
 		virtual ~GUITextField();
 
 		void styleUpdated();
@@ -30,6 +68,8 @@ namespace BansheeEngine
 		void focusLost();
 
 		GUIInputBox* mInputBox;
+		GUILayout* mLayout;
+		GUILabel* mLabel;
 		bool mHasInputFocus;
 		WString mValue;
 	};

+ 140 - 5
BansheeEditor/Source/BsGUITextField.cpp

@@ -13,12 +13,22 @@ using namespace std::placeholders;
 
 namespace BansheeEngine
 {
-	GUITextField::GUITextField(const PrivatelyConstruct& dummy, const GUIContent& labelContent, UINT32 labelWidth, 
-		const String& style, const GUILayoutOptions& layoutOptions, bool withLabel)
-		:TGUIField(dummy, labelContent, labelWidth, style, layoutOptions, withLabel), 
-		mInputBox(nullptr), mValue(L""), mHasInputFocus(false)
+	const UINT32 GUITextField::DEFAULT_LABEL_WIDTH = 100;
+
+	GUITextField::GUITextField(const PrivatelyConstruct& dummy, bool multiline, const GUIContent& labelContent, 
+		UINT32 labelWidth, const String& style, const GUILayoutOptions& layoutOptions, bool withLabel)
+		:GUIElementContainer(layoutOptions, style),
+		mInputBox(nullptr), mValue(L""), mHasInputFocus(false), mLayout(nullptr), mLabel(nullptr)
 	{
-		mInputBox = GUIInputBox::create(false, getSubStyleName(getInputStyleType()));
+		mLayout = &addLayoutXInternal(this);
+
+		if (withLabel)
+		{
+			mLabel = GUILabel::create(labelContent, GUIOptions(GUIOption::fixedWidth(labelWidth)), getSubStyleName(getLabelStyleType()));
+			mLayout->addElement(mLabel);
+		}
+
+		mInputBox = GUIInputBox::create(multiline, getSubStyleName(getInputStyleType()));
 		mLayout->addElement(mInputBox);
 
 		mInputBox->onValueChanged.connect(std::bind(&GUITextField::valueChanged, this, _1));
@@ -31,12 +41,131 @@ namespace BansheeEngine
 
 	}
 
+	GUITextField* GUITextField::create(bool multiline, const GUIContent& labelContent, UINT32 labelWidth, const GUIOptions& layoutOptions,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, labelContent, labelWidth, *curStyle,
+			GUILayoutOptions::create(layoutOptions), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const GUIContent& labelContent, const GUIOptions& layoutOptions,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, labelContent, DEFAULT_LABEL_WIDTH, *curStyle,
+			GUILayoutOptions::create(layoutOptions), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const HString& labelText, UINT32 labelWidth, const GUIOptions& layoutOptions,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(labelText), labelWidth, *curStyle,
+			GUILayoutOptions::create(layoutOptions), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const HString& labelText, const GUIOptions& layoutOptions,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(labelText), DEFAULT_LABEL_WIDTH, *curStyle,
+			GUILayoutOptions::create(layoutOptions), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const GUIOptions& layoutOptions, const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(), 0, *curStyle,
+			GUILayoutOptions::create(layoutOptions), false);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const GUIContent& labelContent, UINT32 labelWidth,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, labelContent, labelWidth, *curStyle,
+			GUILayoutOptions::create(), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const GUIContent& labelContent,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, labelContent, DEFAULT_LABEL_WIDTH, *curStyle,
+			GUILayoutOptions::create(), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const HString& labelText, UINT32 labelWidth,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(labelText), labelWidth, *curStyle,
+			GUILayoutOptions::create(), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const HString& labelText,
+		const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(labelText), DEFAULT_LABEL_WIDTH, *curStyle,
+			GUILayoutOptions::create(), true);
+	}
+
+	GUITextField* GUITextField::create(bool multiline, const String& style)
+	{
+		const String* curStyle = &style;
+		if (*curStyle == StringUtil::BLANK)
+			curStyle = &GUITextField::getGUITypeName();
+
+		return bs_new<GUITextField>(PrivatelyConstruct(), multiline, GUIContent(), 0, *curStyle,
+			GUILayoutOptions::create(), false);
+	}
+
 	void GUITextField::setValue(const WString& value)
 	{
 		mValue = value;
 		mInputBox->setText(value);
 	}
 
+	void GUITextField::_updateLayoutInternal(INT32 x, INT32 y, UINT32 width, UINT32 height,
+		RectI clipRect, UINT8 widgetDepth, UINT16 areaDepth)
+	{
+		mLayout->_updateLayoutInternal(x, y, width, height, clipRect, widgetDepth, areaDepth);
+	}
+
+	Vector2I GUITextField::_getOptimalSize() const
+	{
+		return mLayout->_getOptimalSize();
+	}
+
 	void GUITextField::styleUpdated()
 	{
 		if (mLabel != nullptr)
@@ -76,4 +205,10 @@ namespace BansheeEngine
 		static String LABEL_STYLE_TYPE = "EditorFieldInput";
 		return LABEL_STYLE_TYPE;
 	}
+
+	const String& GUITextField::getLabelStyleType()
+	{
+		static String LABEL_STYLE_TYPE = "EditorFieldLabel";
+		return LABEL_STYLE_TYPE;
+	}
 }

+ 1 - 1
BansheeEditor/Source/DbgEditorWidget2.cpp

@@ -51,7 +51,7 @@ namespace BansheeEngine
 
 		GUIIntField* intField = GUIIntField::create(GUIContent(HString(L"Int Field")), 100, GUIOptions(GUIOption::fixedWidth(200)));
 		GUIFloatField* floatField = GUIFloatField::create(HString(L"Float Field"), GUIOptions(GUIOption::fixedWidth(200)));
-		GUITextField* textField = GUITextField::create(HString(L"Text Field"), GUIOptions(GUIOption::fixedWidth(200)));
+		GUITextField* textField = GUITextField::create(false, HString(L"Text Field"), GUIOptions(GUIOption::fixedWidth(200)));
 		GUIVector4Field* vec4Field = GUIVector4Field::create(HString(L"Vec4 Field"), GUIOptions(GUIOption::fixedWidth(200)));
 		GUIVector3Field* vec3Field = GUIVector3Field::create(HString(L"Vec3 Field"), GUIOptions(GUIOption::fixedWidth(200)));
 		GUIVector2Field* vec2Field = GUIVector2Field::create(HString(L"Vec2 Field"), GUIOptions(GUIOption::fixedWidth(200)));

+ 4 - 4
Inspector.txt

@@ -7,21 +7,21 @@ Test custom resources:
 
 ARRAY TODO:
  - Need a GUIFoldout that doesn't have BG and is just a single button.
- - Don't render inspector if array is multi-rank
 
 TODO:
  - Ensure fields aren't updated from the app when in focus
  - Entire foldout should be clickable, not just the toggle button
  - Extend text field so it can be multi-line
  - Properly hook up UndoRedo, for both in-field and object-wide changes
+   - How do I track Ctrl+Z and Ctrl+Y keys? And in general how do I distinguish when I send
+     input to the game and when to the editor.
  - GUIColor needs to be hooked up to a window that actually changes its value.
  - Inspector scrolling
+ - Editor fields don't have a minimum width value?
+ - When editor field is small enough the label can overlap the input field
 
 KEEP IN MIND:
  - Clicking on an object/resource in inspector should ping it in their window
- - Inspector needs to be organized in such a way that scroll areas work. That should be possible with GUIPanelContainer.
-
-
 
 
 

+ 5 - 5
MBansheeEditor/GUI/GUITextField.cs

@@ -22,14 +22,14 @@ namespace BansheeEditor
             set { Internal_SetValue(mCachedPtr, value); }
         }
 
-        public GUITextField(GUIContent title, int titleWidth = 100, string style = "", params GUIOption[] options)
+        public GUITextField(GUIContent title, int titleWidth = 100, bool multiline = false, string style = "", params GUIOption[] options)
         {
-            Internal_CreateInstance(this, title, titleWidth, style, options, true);
+            Internal_CreateInstance(this, multiline, title, titleWidth, style, options, true);
         }
 
-        public GUITextField(string style = "", params GUIOption[] options)
+        public GUITextField(bool multiline = false, string style = "", params GUIOption[] options)
         {
-            Internal_CreateInstance(this, null, 0, style, options, false);
+            Internal_CreateInstance(this, multiline, null, 0, style, options, false);
         }
 
         public bool HasInputFocus()
@@ -46,7 +46,7 @@ namespace BansheeEditor
         }
 
         [MethodImpl(MethodImplOptions.InternalCall)]
-        private static extern void Internal_CreateInstance(GUITextField instance, GUIContent title, int titleWidth,
+        private static extern void Internal_CreateInstance(GUITextField instance, bool multiline, GUIContent title, int titleWidth,
             string style, GUIOption[] options, bool withTitle);
 
         [MethodImpl(MethodImplOptions.InternalCall)]

+ 1 - 1
MBansheeEditor/Inspector/InspectableArray.cs

@@ -89,7 +89,7 @@ namespace BansheeEditor
             base.Update(layoutIndex);
             isInitialized = true;
 
-            if (property.Type != SerializableProperty.FieldType.Array)
+            if (property.Type != SerializableProperty.FieldType.Array || property.InternalType.GetArrayRank() != 1) // We don't support multirank arrays
                 return;
 
             foreach (var row in rows)

+ 1 - 1
SBansheeEditor/Include/BsScriptGUITextField.h

@@ -11,7 +11,7 @@ namespace BansheeEngine
 		SCRIPT_OBJ(BansheeEditorAssemblyName, "BansheeEditor", "GUITextField")
 
 	private:
-		static void internal_createInstance(MonoObject* instance, MonoObject* title, UINT32 titleWidth,
+		static void internal_createInstance(MonoObject* instance, bool multiline, MonoObject* title, UINT32 titleWidth,
 			MonoString* style, MonoArray* guiOptions, bool withTitle);
 
 		static void internal_getValue(ScriptGUITextField* nativeInstance, MonoString** output);

+ 3 - 3
SBansheeEditor/Source/BsScriptGUITextField.cpp

@@ -38,7 +38,7 @@ namespace BansheeEngine
 		onChangedThunk = (OnChangedThunkDef)metaData.scriptClass->getMethod("DoOnChanged", 1).getThunk();
 	}
 
-	void ScriptGUITextField::internal_createInstance(MonoObject* instance, MonoObject* title, UINT32 titleWidth,
+	void ScriptGUITextField::internal_createInstance(MonoObject* instance, bool multiline, MonoObject* title, UINT32 titleWidth,
 		MonoString* style, MonoArray* guiOptions, bool withTitle)
 	{
 		GUIOptions options;
@@ -53,11 +53,11 @@ namespace BansheeEngine
 		if (withTitle)
 		{
 			GUIContent nativeContent(ScriptGUIContent::getText(title), ScriptGUIContent::getImage(title), ScriptGUIContent::getTooltip(title));
-			guiField = GUITextField::create(nativeContent, titleWidth, options, styleName);
+			guiField = GUITextField::create(multiline, nativeContent, titleWidth, options, styleName);
 		}
 		else
 		{
-			guiField = GUITextField::create(options, styleName);
+			guiField = GUITextField::create(multiline, options, styleName);
 		}
 
 		guiField->onValueChanged.connect(std::bind(&ScriptGUITextField::onChanged, instance, _1));