Browse Source

addComponent accepts a variable number of parameters instead of needing to call initialize() after

Marko Pintera 12 years ago
parent
commit
08b94f84b0

+ 2 - 3
BansheeEngine/Include/BsGUIDropDownBox.h

@@ -101,11 +101,10 @@ namespace BansheeEngine
 	class BS_EXPORT GUIDropDownBox : public GUIWidget
 	class BS_EXPORT GUIDropDownBox : public GUIWidget
 	{
 	{
 	public:
 	public:
-		GUIDropDownBox(const CM::HSceneObject& parent);
+		GUIDropDownBox(const CM::HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* window, const GUIDropDownAreaPlacement& placement,
+			const CM::Vector<GUIDropDownData>::type& elements, const GUISkin& skin, GUIDropDownType type);
 		~GUIDropDownBox();
 		~GUIDropDownBox();
 
 
-		void initialize(CM::Viewport* target, CM::RenderWindow* window, const GUIDropDownAreaPlacement& placement,
-			const CM::Vector<GUIDropDownData>::type& elements, const GUISkin& skin, GUIDropDownType type);
 	private:
 	private:
 		struct DropDownSubMenu
 		struct DropDownSubMenu
 		{
 		{

+ 4 - 0
BansheeEngine/Include/BsGUISkin.h

@@ -8,6 +8,8 @@ namespace BansheeEngine
 	class BS_EXPORT GUISkin
 	class BS_EXPORT GUISkin
 	{
 	{
 	public:
 	public:
+		GUISkin() {}
+
 		const GUIElementStyle* getStyle(const CM::String& guiElemType) const;
 		const GUIElementStyle* getStyle(const CM::String& guiElemType) const;
 		void setStyle(const CM::String& guiElemType, const GUIElementStyle& style);
 		void setStyle(const CM::String& guiElemType, const GUIElementStyle& style);
 
 
@@ -15,5 +17,7 @@ namespace BansheeEngine
 		static GUIElementStyle DefaultStyle;
 		static GUIElementStyle DefaultStyle;
 
 
 		CM::UnorderedMap<CM::String, GUIElementStyle>::type mStyles;
 		CM::UnorderedMap<CM::String, GUIElementStyle>::type mStyles;
+
+		GUISkin(const GUISkin& skin) {} // Disable copying
 	};
 	};
 }
 }

+ 1 - 10
BansheeEngine/Include/BsGUIWidget.h

@@ -14,15 +14,6 @@ namespace BansheeEngine
 	public:
 	public:
 		virtual ~GUIWidget();
 		virtual ~GUIWidget();
 
 
-		/**
-		 * @brief	Initializes the GUIWidget. Must be called in order for GUIWidget to start rendering.
-		 *
-		 * @param 	target			Target onto which we want to render the widget.
-		 * @param	ownerWindow   	Window that contains the widget. This will be the source of all input
-		 * 							for the widget. "target" and "ownerWindow" may be the same object.
-		 */
-		virtual void initialize(CM::Viewport* target, CM::RenderWindow* ownerWindow);
-
 		void setSkin(const GUISkin& skin);
 		void setSkin(const GUISkin& skin);
 		const GUISkin& getSkin() const;
 		const GUISkin& getSkin() const;
 
 
@@ -65,7 +56,7 @@ namespace BansheeEngine
 		friend class GUIArea;
 		friend class GUIArea;
 		friend class GUIManager;
 		friend class GUIManager;
 
 
-		GUIWidget(const CM::HSceneObject& parent);
+		GUIWidget(const CM::HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow);
 
 
 		void registerElement(GUIElement* elem);
 		void registerElement(GUIElement* elem);
 		void unregisterElement(GUIElement* elem);
 		void unregisterElement(GUIElement* elem);

+ 1 - 8
BansheeEngine/Include/BsOverlay.h

@@ -17,13 +17,6 @@ namespace BansheeEngine
 	public:
 	public:
 		virtual ~Overlay();
 		virtual ~Overlay();
 
 
-		/**
-		 * @brief	Initializes the GUIWidget. Must be called in order for GUIWidget to start rendering.
-		 *
-		 * @param 	target			Target onto which we want to render the widget.
-		 */
-		void initialize(CM::Viewport* target);
-
 		virtual void render(CM::RenderQueue& renderQueue) const = 0;
 		virtual void render(CM::RenderQueue& renderQueue) const = 0;
 		virtual void update() {}
 		virtual void update() {}
 
 
@@ -47,6 +40,6 @@ namespace BansheeEngine
 		CM::Viewport* mRenderTarget;
 		CM::Viewport* mRenderTarget;
 		CM::INT32 mDepth;
 		CM::INT32 mDepth;
 
 
-		Overlay(const CM::HSceneObject& parent);
+		Overlay(const CM::HSceneObject& parent, CM::Viewport* target);
 	};
 	};
 }
 }

+ 8 - 15
BansheeEngine/Source/BsGUIDropDownBox.cpp

@@ -71,24 +71,12 @@ namespace BansheeEngine
 		return instance;
 		return instance;
 	}
 	}
 
 
-	GUIDropDownBox::GUIDropDownBox(const HSceneObject& parent)
-		:GUIWidget(parent), mScrollUpStyle(nullptr),
+	GUIDropDownBox::GUIDropDownBox(const HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* window, const GUIDropDownAreaPlacement& placement,
+		const CM::Vector<GUIDropDownData>::type& elements, const GUISkin& skin, GUIDropDownType type)
+		:GUIWidget(parent, target, window), mScrollUpStyle(nullptr),
 		mScrollDownStyle(nullptr), mEntryBtnStyle(nullptr), mEntryExpBtnStyle(nullptr), 
 		mScrollDownStyle(nullptr), mEntryBtnStyle(nullptr), mEntryExpBtnStyle(nullptr), 
 		mSeparatorStyle(nullptr), mBackgroundStyle(nullptr)
 		mSeparatorStyle(nullptr), mBackgroundStyle(nullptr)
 	{
 	{
-
-	}
-
-	GUIDropDownBox::~GUIDropDownBox()
-	{
-		cm_delete(mRootMenu);
-	}
-
-	void GUIDropDownBox::initialize(Viewport* target, RenderWindow* window, const GUIDropDownAreaPlacement& placement, 
-		const CM::Vector<GUIDropDownData>::type& elements, const GUISkin& skin, GUIDropDownType type)
-	{
-		GUIWidget::initialize(target, window);
-
 		String stylePrefix = "";
 		String stylePrefix = "";
 		switch(type)
 		switch(type)
 		{
 		{
@@ -120,6 +108,11 @@ namespace BansheeEngine
 		mRootMenu = cm_new<DropDownSubMenu>(this, placement, availableBounds, elements, type);
 		mRootMenu = cm_new<DropDownSubMenu>(this, placement, availableBounds, elements, type);
 	}
 	}
 
 
+	GUIDropDownBox::~GUIDropDownBox()
+	{
+		cm_delete(mRootMenu);
+	}
+
 	GUIDropDownBox::DropDownSubMenu::DropDownSubMenu(GUIDropDownBox* owner, const GUIDropDownAreaPlacement& placement, 
 	GUIDropDownBox::DropDownSubMenu::DropDownSubMenu(GUIDropDownBox* owner, const GUIDropDownAreaPlacement& placement, 
 		const Rect& availableBounds, const CM::Vector<GUIDropDownData>::type& elements, GUIDropDownType type)
 		const Rect& availableBounds, const CM::Vector<GUIDropDownData>::type& elements, GUIDropDownType type)
 		:mOwner(owner), mPage(0), mBackgroundFrame(nullptr), mBackgroundArea(nullptr), mContentArea(nullptr), 
 		:mOwner(owner), mPage(0), mBackgroundFrame(nullptr), mBackgroundArea(nullptr), mContentArea(nullptr), 

+ 1 - 3
BansheeEngine/Source/BsGUIDropDownBoxManager.cpp

@@ -16,11 +16,9 @@ namespace BansheeEngine
 		closeDropDownBox();
 		closeDropDownBox();
 
 
 		mDropDownSO = SceneObject::create("DropDownBox");
 		mDropDownSO = SceneObject::create("DropDownBox");
-		mDropDownBox = mDropDownSO->addComponent<GUIDropDownBox>();
+		mDropDownBox = mDropDownSO->addComponent<GUIDropDownBox>(target, window, placement, elements, skin, type);
 		mOnClosedCallback = onClosedCallback;
 		mOnClosedCallback = onClosedCallback;
 
 
-		mDropDownBox->initialize(target, window, placement, elements, skin, type);
-
 		return mDropDownBox;
 		return mDropDownBox;
 	}
 	}
 
 

+ 12 - 15
BansheeEngine/Source/BsGUIWidget.cpp

@@ -22,12 +22,23 @@ namespace BansheeEngine
 {
 {
 	GUISkin GUIWidget::DefaultSkin;
 	GUISkin GUIWidget::DefaultSkin;
 
 
-	GUIWidget::GUIWidget(const HSceneObject& parent)
+	GUIWidget::GUIWidget(const HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow)
 		:Component(parent), mSkin(nullptr), mOwnerWindow(nullptr), mWidgetIsDirty(false), mTarget(nullptr), mDepth(0)
 		:Component(parent), mSkin(nullptr), mOwnerWindow(nullptr), mWidgetIsDirty(false), mTarget(nullptr), mDepth(0)
 	{
 	{
 		mLastFramePosition = SO()->getWorldPosition();
 		mLastFramePosition = SO()->getWorldPosition();
 		mLastFrameRotation = SO()->getWorldRotation();
 		mLastFrameRotation = SO()->getWorldRotation();
 		mLastFrameScale = SO()->getWorldScale();
 		mLastFrameScale = SO()->getWorldScale();
+
+		assert(target != nullptr);
+		assert(ownerWindow != nullptr);
+
+		if(mOwnerWindow != nullptr)
+			CM_EXCEPT(InvalidStateException, "Widget has already been initialized.");
+
+		mTarget = target;
+		mOwnerWindow = ownerWindow;
+
+		GUIManager::instance().registerWidget(this);
 	}
 	}
 
 
 	GUIWidget::~GUIWidget()
 	GUIWidget::~GUIWidget()
@@ -51,20 +62,6 @@ namespace BansheeEngine
 		mElements.clear();
 		mElements.clear();
 	}
 	}
 
 
-	void GUIWidget::initialize(Viewport* target, RenderWindow* ownerWindow)
-	{
-		assert(target != nullptr);
-		assert(ownerWindow != nullptr);
-
-		if(mOwnerWindow != nullptr)
-			CM_EXCEPT(InvalidStateException, "Widget has already been initialized.");
-
-		mTarget = target;
-		mOwnerWindow = ownerWindow;
-
-		GUIManager::instance().registerWidget(this);
-	}
-
 	void GUIWidget::update()
 	void GUIWidget::update()
 	{
 	{
 		// If the widgets parent scene object moved, we need to mark it as dirty
 		// If the widgets parent scene object moved, we need to mark it as dirty

+ 6 - 11
BansheeEngine/Source/BsOverlay.cpp

@@ -5,18 +5,8 @@ using namespace CamelotFramework;
 
 
 namespace BansheeEngine
 namespace BansheeEngine
 {
 {
-	Overlay::Overlay(const HSceneObject& parent)
+	Overlay::Overlay(const HSceneObject& parent, CM::Viewport* target)
 		:Component(parent), mRenderTarget(nullptr), mDepth(0)
 		:Component(parent), mRenderTarget(nullptr), mDepth(0)
-	{
-
-	}
-
-	Overlay::~Overlay()
-	{
-		OverlayManager::instance().detachOverlayFromAll(this);
-	}
-
-	void Overlay::initialize(CM::Viewport* target)
 	{
 	{
 		if(mRenderTarget != nullptr)
 		if(mRenderTarget != nullptr)
 			OverlayManager::instance().detachOverlay(mRenderTarget, this);
 			OverlayManager::instance().detachOverlay(mRenderTarget, this);
@@ -25,4 +15,9 @@ namespace BansheeEngine
 
 
 		OverlayManager::instance().attachOverlay(mRenderTarget, this);	
 		OverlayManager::instance().attachOverlay(mRenderTarget, this);	
 	}
 	}
+
+	Overlay::~Overlay()
+	{
+		OverlayManager::instance().detachOverlayFromAll(this);
+	}
 }
 }

+ 1 - 3
CamelotClient/Include/BsGUIWindowFrameWidget.h

@@ -9,11 +9,9 @@ namespace BansheeEditor
 	class WindowFrameWidget : public BS::GUIWidget
 	class WindowFrameWidget : public BS::GUIWidget
 	{
 	{
 	public:
 	public:
-		WindowFrameWidget(const CM::HSceneObject& parent);
+		WindowFrameWidget(const CM::HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow, const BS::GUISkin& skin);
 		virtual ~WindowFrameWidget();
 		virtual ~WindowFrameWidget();
 
 
-		virtual void initialize(CM::Viewport* target, CM::RenderWindow* ownerWindow);
-
 	protected:
 	protected:
 		static const CM::UINT32 RESIZE_BORDER_WIDTH;
 		static const CM::UINT32 RESIZE_BORDER_WIDTH;
 
 

+ 1 - 1
CamelotClient/Include/CmTestTextSprite.h

@@ -8,7 +8,7 @@ namespace CamelotFramework
 	protected:
 	protected:
 		friend class CM::SceneObject;
 		friend class CM::SceneObject;
 
 
-		TestTextSprite(const HSceneObject& parent);
+		TestTextSprite(const HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow);
 	public:
 	public:
 		~TestTextSprite();
 		~TestTextSprite();
 
 

+ 2 - 5
CamelotClient/Source/BsEditorWindowBase.cpp

@@ -73,15 +73,12 @@ namespace BansheeEditor
 		mCamera->setAspectRatio(1.0f);
 		mCamera->setAspectRatio(1.0f);
 		mCamera->setIgnoreSceneRenderables(true);
 		mCamera->setIgnoreSceneRenderables(true);
 
 
-		mGUI = mSceneObject->addComponent<GUIWidget>();
-		mGUI->initialize(mCamera->getViewport().get(), renderWindow.get());
+		mGUI = mSceneObject->addComponent<GUIWidget>(mCamera->getViewport().get(), renderWindow.get());
 		mGUI->setDepth(128);
 		mGUI->setDepth(128);
 
 
 		mGUI->setSkin(EngineGUI::instance().getSkin());
 		mGUI->setSkin(EngineGUI::instance().getSkin());
 
 
-		mWindowFrame = mSceneObject->addComponent<WindowFrameWidget>();
-		mWindowFrame->setSkin(EngineGUI::instance().getSkin());
-		mWindowFrame->initialize(mCamera->getViewport().get(), renderWindow.get());
+		mWindowFrame = mSceneObject->addComponent<WindowFrameWidget>(mCamera->getViewport().get(), renderWindow.get(), EngineGUI::instance().getSkin());
 		mWindowFrame->setDepth(129);
 		mWindowFrame->setDepth(129);
 
 
 		mMoveOrResizeConn = RenderWindowManager::instance().onMovedOrResized.connect(boost::bind(&EditorWindowBase::movedOrResized, this, _1));
 		mMoveOrResizeConn = RenderWindowManager::instance().onMovedOrResized.connect(boost::bind(&EditorWindowBase::movedOrResized, this, _1));

+ 8 - 13
CamelotClient/Source/BsGUIWindowFrameWidget.cpp

@@ -16,20 +16,10 @@ namespace BansheeEditor
 {
 {
 	const UINT32 WindowFrameWidget::RESIZE_BORDER_WIDTH = 3;
 	const UINT32 WindowFrameWidget::RESIZE_BORDER_WIDTH = 3;
 
 
-	WindowFrameWidget::WindowFrameWidget(const HSceneObject& parent)
-		:GUIWidget(parent), mWindowFrameArea(nullptr)
+	WindowFrameWidget::WindowFrameWidget(const HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow, const GUISkin& skin)
+		:GUIWidget(parent, target, ownerWindow), mWindowFrameArea(nullptr)
 	{
 	{
-
-	}
-
-	WindowFrameWidget::~WindowFrameWidget()
-	{
-
-	}
-
-	void WindowFrameWidget::initialize(CM::Viewport* target, CM::RenderWindow* ownerWindow)
-	{
-		GUIWidget::initialize(target, ownerWindow);
+		setSkin(skin);
 
 
 		GUIArea* backgroundArea = GUIArea::createStretchedXY(*this, 0, 0, 0, 0, 500);
 		GUIArea* backgroundArea = GUIArea::createStretchedXY(*this, 0, 0, 0, 0, 500);
 		backgroundArea->getLayout().addElement(GUITexture::create(*this, GUILayoutOptions::expandableXY(), GUIImageScaleMode::RepeatToFit, getSkin().getStyle("WindowBackground")));
 		backgroundArea->getLayout().addElement(GUITexture::create(*this, GUILayoutOptions::expandableXY(), GUIImageScaleMode::RepeatToFit, getSkin().getStyle("WindowBackground")));
@@ -42,6 +32,11 @@ namespace BansheeEditor
 		refreshNonClientAreas();
 		refreshNonClientAreas();
 	}
 	}
 
 
+	WindowFrameWidget::~WindowFrameWidget()
+	{
+
+	}
+
 	void WindowFrameWidget::update()
 	void WindowFrameWidget::update()
 	{
 	{
 
 

+ 1 - 2
CamelotClient/Source/BsMainEditorWindow.cpp

@@ -48,8 +48,7 @@ namespace BansheeEditor
 
 
 		GameObjectHandle<DebugCamera> debugCamera = sceneCameraGO->addComponent<DebugCamera>();
 		GameObjectHandle<DebugCamera> debugCamera = sceneCameraGO->addComponent<DebugCamera>();
 
 
-		GameObjectHandle<TestTextSprite> textSprite = mSceneObject->addComponent<TestTextSprite>();
-		textSprite->initialize(mCamera->getViewport().get(), renderWindow.get());
+		GameObjectHandle<TestTextSprite> textSprite = mSceneObject->addComponent<TestTextSprite>(mCamera->getViewport().get(), renderWindow.get());
 
 
 		textSprite->init(sceneCamera, "Testing in a new row, does this work?", sceneRenderTarget);
 		textSprite->init(sceneCamera, "Testing in a new row, does this work?", sceneRenderTarget);
 
 

+ 2 - 2
CamelotClient/Source/CmTestTextSprite.cpp

@@ -26,8 +26,8 @@ using namespace BansheeEngine;
 
 
 namespace CamelotFramework
 namespace CamelotFramework
 {
 {
-	TestTextSprite::TestTextSprite(const HSceneObject& parent)
-		:GUIWidget(parent)
+	TestTextSprite::TestTextSprite(const HSceneObject& parent, CM::Viewport* target, CM::RenderWindow* ownerWindow)
+		:GUIWidget(parent, target, ownerWindow)
 	{
 	{
 	}
 	}
 
 

+ 24 - 2
CamelotCore/Include/CmSceneObject.h

@@ -213,8 +213,7 @@ namespace CamelotFramework
 		template <typename T>
 		template <typename T>
 		GameObjectHandle<T> addComponent()
 		GameObjectHandle<T> addComponent()
 		{
 		{
-			BOOST_STATIC_ASSERT_MSG((boost::is_base_of<CamelotFramework::Component, T>::value), 
-				"Specified type is not a valid Component.");
+			BOOST_STATIC_ASSERT_MSG((boost::is_base_of<CamelotFramework::Component, T>::value), "Specified type is not a valid Component.");
 
 
 			GameObjectHandle<T> newComponent = GameObjectHandle<T>(
 			GameObjectHandle<T> newComponent = GameObjectHandle<T>(
 				new (cm_alloc<T, PoolAlloc>()) T(mThisHandle), &cm_delete<PoolAlloc, GameObject>);
 				new (cm_alloc<T, PoolAlloc>()) T(mThisHandle), &cm_delete<PoolAlloc, GameObject>);
@@ -225,6 +224,29 @@ namespace CamelotFramework
 			return newComponent;
 			return newComponent;
 		}
 		}
 
 
+		// addComponent that accepts an arbitrary number of parameters > 0
+#define MAKE_ADD_COMPONENT(z, n, unused)											\
+		template<class Type BOOST_PP_ENUM_TRAILING_PARAMS(n, class T)>				\
+		GameObjectHandle<Type> addComponent(BOOST_PP_ENUM_BINARY_PARAMS(n, T, &&t) )  \
+		{																			\
+			BOOST_STATIC_ASSERT_MSG((boost::is_base_of<CamelotFramework::Component, Type>::value),  \
+				"Specified type is not a valid Component.");										\
+																									\
+			GameObjectHandle<Type> newComponent = GameObjectHandle<Type>(							\
+				new (cm_alloc<Type, PoolAlloc>()) Type(mThisHandle, BOOST_PP_ENUM_PARAMS (n, t)),	\
+				&cm_delete<PoolAlloc, GameObject>);													\
+																									\
+			mComponents.push_back(newComponent);													\
+																									\
+			gSceneManager().notifyComponentAdded(newComponent);										\
+																									\
+			return newComponent;																	\
+		}
+
+		BOOST_PP_REPEAT_FROM_TO(1, 15, MAKE_ADD_COMPONENT, ~)
+
+#undef MAKE_ADD_COMPONENT
+
 		/**
 		/**
 		 * @brief	Searches for a component with the specific type and returns the first one
 		 * @brief	Searches for a component with the specific type and returns the first one
 		 * 			it finds. 
 		 * 			it finds. 

+ 4 - 4
DropDown.txt

@@ -1,13 +1,13 @@
 GUI ignores image in GUIContent for most elements.
 GUI ignores image in GUIContent for most elements.
 
 
 Doesn't belong here but as an additional reminder: Remove Component::initialize and instead make multi paramter addComponent
 Doesn't belong here but as an additional reminder: Remove Component::initialize and instead make multi paramter addComponent
-
-Add min/max/close buttons to GUIMenuBar
-Setup move areas in GUIMenuBar
+ - There's an exception that happens where mStyle of a GUIButtonBase is not initialized
+ - Track down other uses of initialize() and remove them (GUIWidget has one, probably Camera and similar as well)
 
 
 Test context
 Test context
-Test scrollUp/scrollDown
+ - There are issues when dealing with the context menu. Hover doesn't seem to close menus, and hovering for a few seconds seems to cause an exception.
 
 
+Test scrollUp/scrollDown
 
 
 Design improvements:
 Design improvements:
 Attempt to get rid of selective input click callback in GUIManager. It's too specific.
 Attempt to get rid of selective input click callback in GUIManager. It's too specific.