Browse Source

Much better way of dealing with GUIElement children in GUIElementContainers

Marko Pintera 12 năm trước cách đây
mục cha
commit
9556d2c33b

+ 3 - 0
BansheeEngine/Include/BsGUIElementBase.h

@@ -61,6 +61,9 @@ namespace BansheeEngine
 
 		virtual void _changeParentWidget(GUIWidget* widget);
 
+		void _registerChildElement(GUIElement* element);
+		void _unregisterChildElement(GUIElement* element);
+
 	protected:
 		/**
 		 * @brief	Marks the elements contents as dirty, which causes the sprite meshes to be recreated from scratch.

+ 0 - 4
BansheeEngine/Include/BsGUIElementContainer.h

@@ -38,9 +38,5 @@ namespace BansheeEngine
 		virtual void updateClippedBounds();
 
 		virtual CM::Vector2I _getOptimalSize() const;
-		virtual void _changeParentWidget(BS::GUIWidget* widget);
-
-		virtual CM::UINT32 getNumChildElements() const = 0;
-		virtual GUIElement* getChildElement(CM::UINT32 idx) const = 0;
 	};
 }

+ 0 - 3
BansheeEngine/Include/BsGUIScrollArea.h

@@ -61,8 +61,5 @@ namespace BansheeEngine
 		void horzScrollUpdate(float pct);
 		void _updateLayoutInternal(CM::INT32 x, CM::INT32 y, CM::UINT32 width, CM::UINT32 height,
 			CM::RectI clipRect, CM::UINT8 widgetDepth, CM::UINT16 areaDepth);
-
-		CM::UINT32 getNumChildElements() const;
-		GUIElement* getChildElement(CM::UINT32 idx) const;
 	};
 }

+ 2 - 5
BansheeEngine/Source/BsGUIElement.cpp

@@ -18,11 +18,8 @@ namespace BansheeEngine
 
 	GUIElement::~GUIElement()
 	{
-		if(mParentElement != nullptr && mParentElement->_getType() == GUIElementBase::Type::Layout)
-		{
-			GUILayout* layoutParent = static_cast<GUILayout*>(mParentElement);
-			layoutParent->removeElement(this);
-		}
+		if(mParentElement != nullptr)
+			mParentElement->_unregisterChildElement(this);
 	}
 
 	void GUIElement::updateRenderElements()

+ 36 - 0
BansheeEngine/Source/BsGUIElementBase.cpp

@@ -182,6 +182,42 @@ namespace BansheeEngine
 		return *entry;
 	}
 
+	void GUIElementBase::_registerChildElement(GUIElement* element)
+	{
+		GUIElementBase* parentElement = element->_getParent();
+		if(parentElement != nullptr)
+		{
+			parentElement->_unregisterChildElement(element);
+		}
+
+		element->_setParent(this);
+		mChildren.push_back(element);
+
+		markContentAsDirty();
+	}
+
+	void GUIElementBase::_unregisterChildElement(GUIElement* element)
+	{
+		bool foundElem = false;
+		for(auto iter = mChildren.begin(); iter != mChildren.end(); ++iter)
+		{
+			GUIElementBase* child = *iter;
+
+			if(child->_getType() == GUIElementBase::Type::Element && child == element)
+			{
+				mChildren.erase(iter);
+				element->_setParent(nullptr);
+				foundElem = true;
+
+				markContentAsDirty();
+				break;
+			}
+		}
+
+		if(!foundElem)
+			CM_EXCEPT(InvalidParametersException, "Provided element is not a part of this element.");
+	}
+
 	void GUIElementBase::_changeParentWidget(GUIWidget* widget)
 	{
 		for(auto& child : mChildren)

+ 0 - 13
BansheeEngine/Source/BsGUIElementContainer.cpp

@@ -41,17 +41,4 @@ namespace BansheeEngine
 	{
 		return Vector2I();
 	}
-
-	void GUIElementContainer::_changeParentWidget(GUIWidget* widget)
-	{
-		GUIElement::_changeParentWidget(widget);
-
-		for(UINT32 i = 0; i < getNumChildElements(); i++)
-		{
-			GUIElement* child = getChildElement(i);
-
-			if(child != nullptr)
-				child->_changeParentWidget(widget);
-		}
-	}
 }

+ 4 - 32
BansheeEngine/Source/BsGUILayout.cpp

@@ -22,39 +22,12 @@ namespace BansheeEngine
 
 	void GUILayout::addElement(GUIElement* element)
 	{
-		GUIElementBase* parentElement = element->_getParent();
-		if(parentElement != nullptr && parentElement->_getType() == GUIElementBase::Type::Layout)
-		{
-			GUILayout* layoutParent = static_cast<GUILayout*>(parentElement);
-			layoutParent->removeElement(element);
-		}
-
-		element->_setParent(this);
-		mChildren.push_back(element);
-
-		markContentAsDirty();
+		_registerChildElement(element);
 	}
 
 	void GUILayout::removeElement(GUIElement* element)
 	{
-		bool foundElem = false;
-		for(auto iter = mChildren.begin(); iter != mChildren.end(); ++iter)
-		{
-			GUIElementBase* child = *iter;
-
-			if(child->_getType() == GUIElementBase::Type::Element && child == element)
-			{
-				mChildren.erase(iter);
-				element->_setParent(nullptr);
-				foundElem = true;
-				
-				markContentAsDirty();
-				break;
-			}
-		}
-
-		if(!foundElem)
-			CM_EXCEPT(InvalidParametersException, "Provided element is not a part of this layout.");
+		_unregisterChildElement(element);
 	}
 
 	void GUILayout::insertElement(UINT32 idx, GUIElement* element)
@@ -63,10 +36,9 @@ namespace BansheeEngine
 			CM_EXCEPT(InvalidParametersException, "Index out of range: " + toString(idx) + ". Valid range: 0 .. " + toString((UINT32)mChildren.size()));
 
 		GUIElementBase* parentElement = element->_getParent();
-		if(parentElement != nullptr && parentElement->_getType() == GUIElementBase::Type::Layout)
+		if(parentElement != nullptr)
 		{
-			GUILayout* layoutParent = static_cast<GUILayout*>(parentElement);
-			layoutParent->removeElement(element);
+			parentElement->_unregisterChildElement(element);
 		}
 
 		element->_setParent(this);

+ 4 - 18
BansheeEngine/Source/BsGUIScrollArea.cpp

@@ -116,6 +116,8 @@ namespace BansheeEngine
 				else
 					mVertScroll = GUIScrollBarVert::create(_getParentWidget());
 
+				_registerChildElement(mVertScroll);
+
 				mVertScroll->onScrollPositionChanged.connect(boost::bind(&GUIScrollArea::vertScrollUpdate, this, _1));
 				mVertScroll->_setAcceptsKeyboardFocus(false);
 			}
@@ -175,6 +177,8 @@ namespace BansheeEngine
 				else
 					mHorzScroll = GUIScrollBarHorz::create(_getParentWidget());
 
+				_registerChildElement(mHorzScroll);
+
 				mHorzScroll->onScrollPositionChanged.connect(boost::bind(&GUIScrollArea::horzScrollUpdate, this, _1));
 				mHorzScroll->_setAcceptsKeyboardFocus(false);
 			}
@@ -261,24 +265,6 @@ namespace BansheeEngine
 		return false;
 	}
 
-	UINT32 GUIScrollArea::getNumChildElements() const
-	{
-		return 2;
-	}
-
-	GUIElement* GUIScrollArea::getChildElement(UINT32 idx) const
-	{
-		switch(idx)
-		{
-		case 0:
-			return mVertScroll;
-		case 1:
-			return mHorzScroll;
-		}
-
-		return nullptr;
-	}
-
 	GUIScrollArea* GUIScrollArea::create(GUIWidget& parent, ScrollBarType vertBarType, ScrollBarType horzBarType, 
 		const GUIElementStyle* scrollBarStyle, const GUIElementStyle* scrollAreaStyle)
 	{

+ 0 - 3
CamelotClient/Include/BsDockManager.h

@@ -107,8 +107,5 @@ namespace BansheeEditor
 
 		bool mouseEvent(const BS::GUIMouseEvent& event);
 		bool insidePolygon(CM::Vector2* polyPoints, CM::UINT32 numPoints, CM::Vector2 point) const;
-
-		virtual CM::UINT32 getNumChildElements() const;
-		virtual BS::GUIElement* getChildElement(CM::UINT32 idx) const;
 	};
 }

+ 0 - 2
CamelotClient/Include/BsGUITabbedTitleBar.h

@@ -68,8 +68,6 @@ namespace BansheeEditor
 			BS::GUIElementStyle* minBtnStyle, BS::GUIElementStyle* closeBtnStyle, const BS::GUILayoutOptions& layoutOptions);
 
 		virtual bool mouseEvent(const BS::GUIMouseEvent& ev);
-		virtual CM::UINT32 getNumChildElements() const;
-		virtual GUIElement* getChildElement(CM::UINT32 idx) const;
 
 		void tabToggled(CM::UINT32 tabIdx);
 		void tabClosed();

+ 0 - 10
CamelotClient/Source/BsDockManager.cpp

@@ -634,16 +634,6 @@ namespace BansheeEditor
 		return false;
 	}
 
-	UINT32 DockManager::getNumChildElements() const
-	{
-		return 0;
-	}
-
-	GUIElement* DockManager::getChildElement(UINT32 idx) const
-	{
-		return nullptr;
-	}
-
 	// TODO - Move to a separate Polygon class?
 	bool DockManager::insidePolygon(CM::Vector2* polyPoints, CM::UINT32 numPoints, CM::Vector2 point) const
 	{

+ 7 - 26
CamelotClient/Source/BsGUITabbedTitleBar.cpp

@@ -43,8 +43,13 @@ namespace BansheeEditor
 			mTabBtnStyle = parent.getSkin().getStyle("TabbedBarBtn");
 
 		mBackgroundImage = GUITexture::create(parent, mBackgroundStyle);
+		_registerChildElement(mBackgroundImage);
+
 		mMinBtn = GUIButton::create(parent, HString(L""), mMinimizeBtnStyle);
+		_registerChildElement(mMinBtn);
+
 		mCloseBtn = GUIButton::create(parent, HString(L""), mCloseBtnStyle);
+		_registerChildElement(mCloseBtn);
 
 		mCloseBtn->onClick.connect(boost::bind(&GUITabbedTitleBar::tabClosed, this));
 
@@ -53,8 +58,7 @@ namespace BansheeEditor
 
 	GUITabbedTitleBar::~GUITabbedTitleBar()
 	{
-		for(UINT32 i = 0; i < getNumChildElements(); i++)
-			GUIElement::destroy(getChildElement(i));
+
 	}
 
 	GUITabbedTitleBar* GUITabbedTitleBar::create(GUIWidget& parent, RenderWindow* parentWindow, GUIElementStyle* backgroundStyle, 
@@ -85,6 +89,7 @@ namespace BansheeEditor
 	void GUITabbedTitleBar::insertTab(UINT32 idx, const CM::HString& name)
 	{
 		GUITabButton* newTabToggle = GUITabButton::create(*mParent, mTabToggleGroup, mUniqueTabIdx, name, mTabBtnStyle);
+		_registerChildElement(newTabToggle);
 
 		idx = Math::clamp(idx, 0U, (UINT32)mTabButtons.size());
 
@@ -95,8 +100,6 @@ namespace BansheeEditor
 		mTabButtons.insert(mTabButtons.begin() + idx, newTabToggle);
 
 		mUniqueTabIdx++;
-
-		markContentAsDirty();
 	}
 
 	void GUITabbedTitleBar::removeTab(UINT32 idx)
@@ -109,8 +112,6 @@ namespace BansheeEditor
 		GUIElement::destroy(mTabButtons[idx]);
 
 		mTabButtons.erase(mTabButtons.begin() + idx);
-
-		markContentAsDirty();
 	}
 
 	bool GUITabbedTitleBar::mouseEvent(const GUIMouseEvent& event)
@@ -211,26 +212,6 @@ namespace BansheeEditor
 		return false;
 	}
 
-	UINT32 GUITabbedTitleBar::getNumChildElements() const
-	{
-		return 3 + (UINT32)mTabButtons.size();
-	}
-
-	GUIElement* GUITabbedTitleBar::getChildElement(CM::UINT32 idx) const
-	{
-		switch (idx)
-		{
-		case 0:
-			return mBackgroundImage;
-		case 1:
-			return mMinBtn;
-		case 2:
-			return mCloseBtn;
-		}
-
-		return mTabButtons[idx - 3];
-	}
-
 	void GUITabbedTitleBar::updateClippedBounds()
 	{
 		Vector2I offset = _getOffset();