Browse Source

Basic window docking working

Marko Pintera 13 years ago
parent
commit
55b0a53bd7

+ 2 - 0
CamelotEditor/Include/CmEditorApplication.h

@@ -27,6 +27,8 @@ namespace CamelotEditor
 		bool projectExists(const QString& absProjPath) const;
 		bool projectExists(const QString& absProjPath) const;
 
 
 		QString getEditorRootPath() const;
 		QString getEditorRootPath() const;
+
+		QtEditor* getMainWindow() const;
 		
 		
 	private:
 	private:
 		static const QString PROJECT_PREFS_FILE_NAME;
 		static const QString PROJECT_PREFS_FILE_NAME;

+ 2 - 0
CamelotEditor/Include/CmEditorPrerequisites.h

@@ -10,7 +10,9 @@ namespace CamelotEditor
 	class EditorPrefs;
 	class EditorPrefs;
 	class EditorApplication;
 	class EditorApplication;
 	class ProjectPrefs;
 	class ProjectPrefs;
+	class QtEditor;
 	class QtDockOverlayWidget;
 	class QtDockOverlayWidget;
+	class EditorWindowFactory;
 	class QtEditorWindow;
 	class QtEditorWindow;
 }
 }
 
 

+ 1 - 1
CamelotEditor/Include/CmEditorWindowFactory.h

@@ -8,7 +8,7 @@ namespace CamelotEditor
 	class EditorWindowFactory
 	class EditorWindowFactory
 	{
 	{
 	public:
 	public:
-		virtual QtEditorWindow* create(QWidget* parent) const = 0;
+		virtual QtEditorWindow* create(QWidget* parent) = 0;
 
 
 		virtual const QString& getWindowName() const = 0;
 		virtual const QString& getWindowName() const = 0;
 		virtual const QString& getMenuCategory() const = 0;
 		virtual const QString& getMenuCategory() const = 0;

+ 11 - 3
CamelotEditor/Include/CmEditorWindowManager.h

@@ -2,7 +2,8 @@
 
 
 #include "CmEditorPrerequisites.h"
 #include "CmEditorPrerequisites.h"
 #include "CmModule.h"
 #include "CmModule.h"
-#include "CmEditorWindowFactory.h"
+#include <boost/function.hpp>
+#include <QtCore/QString>
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
@@ -11,9 +12,16 @@ namespace CamelotEditor
 	public:
 	public:
 		void registerWindowFactory(EditorWindowFactory* factory);
 		void registerWindowFactory(EditorWindowFactory* factory);
 
 
-		QtEditorWindow* create(const QString& name) const;
+		void openWindow(const QString& name);
+		boost::function<void()> getOpenCallback(const QString& name);
+
+		vector<QString>::type getAvailableWindowTypes() const;
 
 
 	private:
 	private:
-		std::map<QString, EditorWindowFactory*> mFactories;
+		map<QString, EditorWindowFactory*>::type mFactories;
+
+		EditorWindowFactory* getFactory(const QString& name) const;
 	};
 	};
+
+	EditorWindowManager& gEditorWindowManager();
 }
 }

+ 3 - 2
CamelotEditor/Include/CmHierarchyWindowFactory.h

@@ -1,14 +1,15 @@
 #pragma once
 #pragma once
 
 
 #include "CmEditorPrerequisites.h"
 #include "CmEditorPrerequisites.h"
+#include "CmEditorWindowFactory.h"
 #include <QtCore/QString>
 #include <QtCore/QString>
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
-	class HierarchyWindowFactory
+	class HierarchyWindowFactory : public EditorWindowFactory
 	{
 	{
 	public:
 	public:
-		QtEditorWindow* create(QWidget* parent) const;
+		QtEditorWindow* create(QWidget* parent);
 
 
 		const QString& getWindowName() const;
 		const QString& getWindowName() const;
 		const QString& getMenuCategory() const;
 		const QString& getMenuCategory() const;

+ 12 - 2
CamelotEditor/Include/CmQtEditor.h

@@ -2,6 +2,7 @@
 
 
 #include "CmEditorPrerequisites.h"
 #include "CmEditorPrerequisites.h"
 #include <QtWidgets/QMainWindow>
 #include <QtWidgets/QMainWindow>
+#include <boost/function.hpp>
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
@@ -16,6 +17,10 @@ namespace CamelotEditor
 		QtDockOverlayWidget* getDockOverlayWidget() const { return mDockOverlayWidget; }
 		QtDockOverlayWidget* getDockOverlayWidget() const { return mDockOverlayWidget; }
 		QWidget* getCentralWidget() const { return mCentralWidget; }
 		QWidget* getCentralWidget() const { return mCentralWidget; }
 
 
+		void setProjectName(const QString& name);
+		QAction* addMenuItemCallback(const QString& menuCategory, const QString& itemName, boost::function<void()> callback);
+		void addMenuItemSeparator(const QString& menuCategory);
+
 	private:
 	private:
 		QMenuBar* mMenuBar;
 		QMenuBar* mMenuBar;
 		QToolBar* mMainToolBar;
 		QToolBar* mMainToolBar;
@@ -23,10 +28,15 @@ namespace CamelotEditor
 		QStatusBar* mStatusBar;
 		QStatusBar* mStatusBar;
 		QtDockOverlayWidget* mDockOverlayWidget;
 		QtDockOverlayWidget* mDockOverlayWidget;
 
 
-		QMenu* mFileMenu;
-		QMenu* mWindowMenu;
+		map<QString, QMenu*>::type mMenus;
 
 
 		void setupUi();
 		void setupUi();
 		void retranslateUi();
 		void retranslateUi();
+
+		QMenu* findOrCreateMenu(const QString& name);
+
+		void openProject();
+		void saveProject();
+		void exitEditor();
 	};
 	};
 }
 }

+ 3 - 2
CamelotEditor/Include/CmSceneWindowFactory.h

@@ -1,14 +1,15 @@
 #pragma once
 #pragma once
 
 
 #include "CmEditorPrerequisites.h"
 #include "CmEditorPrerequisites.h"
+#include "CmEditorWindowFactory.h"
 #include <QtCore/QString>
 #include <QtCore/QString>
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
-	class SceneWindowFactory
+	class SceneWindowFactory : public EditorWindowFactory
 	{
 	{
 	public:
 	public:
-		QtEditorWindow* create(QWidget* parent) const;
+		QtEditorWindow* create(QWidget* parent);
 
 
 		const QString& getWindowName() const;
 		const QString& getWindowName() const;
 		const QString& getMenuCategory() const;
 		const QString& getMenuCategory() const;

+ 17 - 0
CamelotEditor/Source/CmEditorApplication.cpp

@@ -5,6 +5,8 @@
 #include "CmQtProjectSelection.h"
 #include "CmQtProjectSelection.h"
 #include "CmEditorWindowManager.h"
 #include "CmEditorWindowManager.h"
 #include "CmWindowDockManager.h"
 #include "CmWindowDockManager.h"
+#include "CmSceneWindowFactory.h"
+#include "CmHierarchyWindowFactory.h"
 #include "CmFileSystem.h"
 #include "CmFileSystem.h"
 #include "CmException.h"
 #include "CmException.h"
 #include <QtWidgets/QApplication>
 #include <QtWidgets/QApplication>
@@ -48,6 +50,15 @@ namespace CamelotEditor
 
 
 		EditorWindowManager::startUp(new EditorWindowManager());
 		EditorWindowManager::startUp(new EditorWindowManager());
 		WindowDockManager::startUp(new WindowDockManager(p->mEditor->getCentralWidget(), p->mEditor->getDockOverlayWidget()));
 		WindowDockManager::startUp(new WindowDockManager(p->mEditor->getCentralWidget(), p->mEditor->getDockOverlayWidget()));
+
+		gEditorWindowManager().registerWindowFactory(new SceneWindowFactory());
+		gEditorWindowManager().registerWindowFactory(new HierarchyWindowFactory());
+
+		vector<QString>::type windowTypes = gEditorWindowManager().getAvailableWindowTypes();
+		for(auto iter = windowTypes.begin(); iter != windowTypes.end(); ++iter)
+		{
+			p->mEditor->addMenuItemCallback("Windows", *iter, gEditorWindowManager().getOpenCallback(*iter));
+		}
 	}
 	}
 
 
 	void EditorApplication::run()
 	void EditorApplication::run()
@@ -58,6 +69,7 @@ namespace CamelotEditor
 		if(projSelection.exec() == QDialog::Rejected)
 		if(projSelection.exec() == QDialog::Rejected)
 			return;
 			return;
 
 
+		p->mEditor->setProjectName(gProjectPrefs().getProjectName());
 		p->mEditor->show();
 		p->mEditor->show();
 		p->mApp->exec();
 		p->mApp->exec();
 	}
 	}
@@ -146,6 +158,11 @@ namespace CamelotEditor
 		return QDir::cleanPath(QDir::toNativeSeparators(getEditorRootPath() + QDir::separator() + EDITOR_PREFS_FILE_NAME));
 		return QDir::cleanPath(QDir::toNativeSeparators(getEditorRootPath() + QDir::separator() + EDITOR_PREFS_FILE_NAME));
 	}
 	}
 
 
+	QtEditor* EditorApplication::getMainWindow() const
+	{
+		return p->mEditor;
+	}
+
 	EditorApplication& gEditorApp()
 	EditorApplication& gEditorApp()
 	{
 	{
 		static EditorApplication application;
 		static EditorApplication application;

+ 36 - 3
CamelotEditor/Source/CmEditorWindowManager.cpp

@@ -1,5 +1,10 @@
 #include "CmEditorWindowManager.h"
 #include "CmEditorWindowManager.h"
+#include "CmEditorApplication.h"
+#include "CmQtEditorWindow.h"
+#include "CmEditorWindowFactory.h"
 #include "CmException.h"
 #include "CmException.h"
+#include "CmQtEditor.h"
+#include <boost/bind.hpp>
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
@@ -10,15 +15,43 @@ namespace CamelotEditor
 		mFactories[factory->getWindowName()] = factory;
 		mFactories[factory->getWindowName()] = factory;
 	}
 	}
 
 
-	QtEditorWindow* EditorWindowManager::create(const QString& name) const
+	void EditorWindowManager::openWindow(const QString& name)
+	{
+		EditorWindowFactory* factory = getFactory(name);
+		QtEditorWindow* window = factory->create(gEditorApp().getMainWindow());
+		window->setAttribute(Qt::WA_DeleteOnClose, true);
+
+		window->show();
+	}
+
+	boost::function<void()> EditorWindowManager::getOpenCallback(const QString& name)
+	{
+		return boost::bind(&EditorWindowManager::openWindow, this, name);
+	}
+
+	vector<QString>::type EditorWindowManager::getAvailableWindowTypes() const
+	{
+		vector<QString>::type types;
+		for(auto iter = mFactories.begin(); iter != mFactories.end(); ++iter)
+		{
+			types.push_back(iter->first);
+		}
+
+		return types;
+	}
+
+	EditorWindowFactory* EditorWindowManager::getFactory(const QString& name) const
 	{
 	{
 		auto iterFind = mFactories.find(name);
 		auto iterFind = mFactories.find(name);
 
 
 		if(iterFind == mFactories.end())
 		if(iterFind == mFactories.end())
 			CM_EXCEPT(InvalidParametersException, "Window with the name: \"" + name.toStdString() + "\" doesn't exist.");
 			CM_EXCEPT(InvalidParametersException, "Window with the name: \"" + name.toStdString() + "\" doesn't exist.");
 
 
+		return iterFind->second;
+	}
 
 
-
-		//QtEditorWindow* window = iterFind->second.create(parent);
+	EditorWindowManager& gEditorWindowManager()
+	{
+		return EditorWindowManager::instance();
 	}
 	}
 }
 }

+ 3 - 3
CamelotEditor/Source/CmHierarchyWindowFactory.cpp

@@ -1,11 +1,11 @@
 #include "CmHierarchyWindowFactory.h"
 #include "CmHierarchyWindowFactory.h"
-#include "CmQtSceneWindow.h"
+#include "CmQtHierarchyWindow.h"
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
-	QtEditorWindow* HierarchyWindowFactory::create(QWidget* parent) const
+	QtEditorWindow* HierarchyWindowFactory::create(QWidget* parent)
 	{
 	{
-		return new QtSceneWindow(parent);
+		return new QtHierarchyWindow(parent);
 	}
 	}
 
 
 	const QString& HierarchyWindowFactory::getWindowName() const
 	const QString& HierarchyWindowFactory::getWindowName() const

+ 64 - 12
CamelotEditor/Source/CmQtEditor.cpp

@@ -1,11 +1,12 @@
 #include "CmQtEditor.h"
 #include "CmQtEditor.h"
-#include "CmProjectPrefs.h"
 #include "CmQtDockOverlayWidget.h"
 #include "CmQtDockOverlayWidget.h"
 #include <QtWidgets/QMenuBar>
 #include <QtWidgets/QMenuBar>
 #include <QtWidgets/QToolBar>
 #include <QtWidgets/QToolBar>
 #include <QtWidgets/QStatusBar>
 #include <QtWidgets/QStatusBar>
 #include <QtCore/QLocale>
 #include <QtCore/QLocale>
 #include <QtWidgets/QApplication>
 #include <QtWidgets/QApplication>
+#include <boost/bind.hpp>
+#include "CmException.h"
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
@@ -43,14 +44,10 @@ namespace CamelotEditor
 		mStatusBar->setObjectName(QStringLiteral("statusBar"));
 		mStatusBar->setObjectName(QStringLiteral("statusBar"));
 		setStatusBar(mStatusBar);
 		setStatusBar(mStatusBar);
 		
 		
-		mFileMenu = new QMenu(mMenuBar);
-		mFileMenu->setObjectName(QString::fromUtf8("fileMenu"));
-
-		mWindowMenu = new QMenu(mMenuBar);
-		mWindowMenu->setObjectName(QString::fromUtf8("windowMenu"));
-
-		mMenuBar->addAction(mFileMenu->menuAction());
-		mMenuBar->addAction(mWindowMenu->menuAction());
+		addMenuItemCallback("File", "Open project", boost::bind(&QtEditor::openProject, this));
+		addMenuItemCallback("File", "Save project", boost::bind(&QtEditor::saveProject, this));
+		addMenuItemSeparator("File");
+		addMenuItemCallback("File", "Exit", boost::bind(&QtEditor::exitEditor, this));
 
 
 		mDockOverlayWidget = new QtDockOverlayWidget(this);
 		mDockOverlayWidget = new QtDockOverlayWidget(this);
 
 
@@ -61,11 +58,66 @@ namespace CamelotEditor
 
 
 	void QtEditor::retranslateUi()
 	void QtEditor::retranslateUi()
 	{
 	{
-		QString title = tr("Camelot Editor") + " - " + gProjectPrefs().getProjectName();
+		setProjectName("No project");
+	}
+
+	void QtEditor::setProjectName(const QString& name)
+	{
+		QString title = tr("Camelot Editor") + " - " + name;
 
 
 		setWindowTitle(title);
 		setWindowTitle(title);
-		mFileMenu->setTitle(tr("File"));
-		mWindowMenu->setTitle(tr("Windows"));
+	}
+
+	QAction* QtEditor::addMenuItemCallback(const QString& menuCategory, const QString& itemName, boost::function<void()> callback)
+	{
+		QMenu* menu = findOrCreateMenu(menuCategory);
+
+		QAction* newAction = menu->addAction(itemName);
+		connect(newAction, &QAction::triggered, callback);
+
+		return newAction;
+	}
+
+	void QtEditor::addMenuItemSeparator(const QString& menuCategory)
+	{
+		QMenu* menu = findOrCreateMenu(menuCategory);
+
+		menu->addSeparator();
+	}
+
+	QMenu* QtEditor::findOrCreateMenu(const QString& name)
+	{
+		auto iterFind = mMenus.find(name);
+		QMenu* menu = nullptr;
+
+		if(iterFind == mMenus.end())
+		{
+			menu = new QMenu(mMenuBar);
+			menu->setObjectName(name);
+			menu->setTitle(name);
+			mMenuBar->addAction(menu->menuAction());
+
+			mMenus[name] = menu;
+
+			return menu;
+		}
+		else
+			return iterFind->second;
+	}
+
+	void QtEditor::openProject()
+	{
+		CM_EXCEPT(NotImplementedException, "Not implemented");
+	}
+
+	void QtEditor::saveProject()
+	{
+		CM_EXCEPT(NotImplementedException, "Not implemented");
+	}
+
+	void QtEditor::exitEditor()
+	{
+		exit(1);
 	}
 	}
 }
 }
 
 

+ 2 - 2
CamelotEditor/Source/CmQtNewProject.cpp

@@ -79,8 +79,8 @@ namespace CamelotEditor
 
 
 	void QtNewProject::setupSignals()
 	void QtNewProject::setupSignals()
 	{
 	{
-		connect(mBtnCreate, SIGNAL(clicked()), this, SLOT(createProject()));
-		connect(mBtnBrowse, SIGNAL(clicked()), this, SLOT(browseProjectPath()));
+		connect(mBtnCreate, &QPushButton::clicked, this, &QtNewProject::createProject);
+		connect(mBtnBrowse, &QPushButton::clicked, this, &QtNewProject::browseProjectPath);
 	}
 	}
 
 
 	void QtNewProject::retranslateUi()
 	void QtNewProject::retranslateUi()

+ 3 - 3
CamelotEditor/Source/CmQtProjectSelection.cpp

@@ -63,9 +63,9 @@ namespace CamelotEditor
 
 
 	void QtProjectSelection::setupSignals()
 	void QtProjectSelection::setupSignals()
 	{
 	{
-		connect(mBtnNew, SIGNAL(clicked()), this, SLOT(newProject()));
-		connect(mBtnBrowse, SIGNAL(clicked()), this, SLOT(browseProject()));
-		connect(mBtnOpen, SIGNAL(clicked()), this, SLOT(openSelectedProject()));
+		connect(mBtnNew, &QPushButton::clicked, this, &QtProjectSelection::newProject);
+		connect(mBtnBrowse, &QPushButton::clicked, this, &QtProjectSelection::browseProject);
+		connect(mBtnOpen, &QPushButton::clicked, this, &QtProjectSelection::openSelectedProject);
 	}
 	}
 
 
 	void QtProjectSelection::reloadProjectList()
 	void QtProjectSelection::reloadProjectList()

+ 1 - 1
CamelotEditor/Source/CmSceneWindowFactory.cpp

@@ -3,7 +3,7 @@
 
 
 namespace CamelotEditor
 namespace CamelotEditor
 {
 {
-	QtEditorWindow* SceneWindowFactory::create(QWidget* parent) const
+	QtEditorWindow* SceneWindowFactory::create(QWidget* parent)
 	{
 	{
 		return new QtSceneWindow(parent);
 		return new QtSceneWindow(parent);
 	}
 	}

+ 10 - 0
TODO.txt

@@ -9,6 +9,11 @@
 
 
 -----------------------IMMEDIATE TODO---------------------------------------------------------------
 -----------------------IMMEDIATE TODO---------------------------------------------------------------
 
 
+ Assets manifest
+  - I need to be able to create a list of assets used in the game. Assets referenced from the editor
+    should be easy to account for. But assets loaded from code are special. Maybe be like Unity and allow
+	special Resources folder?
+
 >>>>>>>>>>FINAL SPRINT BEFORE EDITOR WORK
 >>>>>>>>>>FINAL SPRINT BEFORE EDITOR WORK
 Pass
 Pass
  - A way to bind buffers to a Pass, while specifying buffer range
  - A way to bind buffers to a Pass, while specifying buffer range
@@ -98,6 +103,11 @@ So final solution:
   - Sample mask when setting blend state (DX11, check if equivalent exists in GL)
   - Sample mask when setting blend state (DX11, check if equivalent exists in GL)
   - RGBA blend factor when setting blend state(DX11, check if equivalent exists in GL)
   - RGBA blend factor when setting blend state(DX11, check if equivalent exists in GL)
   - HLSL9/HLSL11/GLSL/Cg shaders need preprocessor defines & includes
   - HLSL9/HLSL11/GLSL/Cg shaders need preprocessor defines & includes
+  - One camera -> one task (thread) approach for multithreading
+   - Also make sure to run off a thread pool (WorkQueue class already exists that provides needed interface)
+  - The way I handle rendering currently is to discard simulation results if gpu thread isn't finished.
+     - This reduces input lag but at worst case scenario the effect of multithreading might be completely eliminated as
+	   GPU ends up waiting for GPU, just because it was few milliseconds late. Maybe better to wait for GPU?
 
 
 Command buffer TODO:
 Command buffer TODO:
  - Make CommandQueue not use mutexes and use atomics instead??
  - Make CommandQueue not use mutexes and use atomics instead??

+ 4 - 1
TODOEditor.txt

@@ -29,4 +29,7 @@ TODO for next few days:
 
 
 
 
 Dock overlay widget colors need to be customizable
 Dock overlay widget colors need to be customizable
-QtEditorWindow style needs to be customizable
+QtEditorWindow style needs to be customizable
+
+I want to rethink how the docking system works, and window management in general
+ - those systems should be interconnected somehow