From 1ee64c7087d062e57b8e4821c4f2c2301e699725 Mon Sep 17 00:00:00 2001 From: cc9cii Date: Sat, 1 Nov 2014 19:12:22 +1100 Subject: [PATCH] Add missing files for multi-document support. --- apps/opencs/view/world/physicsmanager.cpp | 87 +++++++++++++++++++++++ apps/opencs/view/world/physicsmanager.hpp | 58 +++++++++++++++ 2 files changed, 145 insertions(+) create mode 100644 apps/opencs/view/world/physicsmanager.cpp create mode 100644 apps/opencs/view/world/physicsmanager.hpp diff --git a/apps/opencs/view/world/physicsmanager.cpp b/apps/opencs/view/world/physicsmanager.cpp new file mode 100644 index 0000000000..ce71ac3150 --- /dev/null +++ b/apps/opencs/view/world/physicsmanager.cpp @@ -0,0 +1,87 @@ +#include "physicsmanager.hpp" + +#include + +#include "../render/worldspacewidget.hpp" +#include "physicssystem.hpp" + +namespace CSVWorld +{ + PhysicsManager *PhysicsManager::mPhysicsManagerInstance = 0; + + PhysicsManager::PhysicsManager() + { + assert(!mPhysicsManagerInstance); + mPhysicsManagerInstance = this; + } + + PhysicsManager::~PhysicsManager() + { + std::map::iterator iter = mPhysics.begin(); + for(; iter != mPhysics.end(); ++iter) + delete iter->second; // shouldn't be any left but just in case + } + + PhysicsManager *PhysicsManager::instance() + { + assert(mPhysicsManagerInstance); + return mPhysicsManagerInstance; + } + + // create a physics instance per document, called from CSVDoc::View() to get Document* + void PhysicsManager::setupPhysics(CSMDoc::Document *doc) + { + std::map >::iterator iter = mSceneWidgets.find(doc); + if(iter == mSceneWidgets.end()) + { + mSceneWidgets[doc] = std::list {}; // zero elements + mPhysics[doc] = new PhysicsSystem(); + } + } + + // called from CSVRender::WorldspaceWidget() to get widgets' association with Document& + PhysicsSystem *PhysicsManager::addSceneWidget(CSMDoc::Document &doc, CSVRender::WorldspaceWidget *widget) + { + CSVRender::SceneWidget *sceneWidget = static_cast(widget); + + std::map >::iterator iter = mSceneWidgets.begin(); + for(; iter != mSceneWidgets.end(); ++iter) + { + if((*iter).first == &doc) + { + (*iter).second.push_back(sceneWidget); + return mPhysics[(*iter).first]; // TODO: consider using shared_ptr instead + } + } + + throw std::runtime_error("No physics system found for the given document."); + } + + // delete physics when the last scene widget for the document is closed + void PhysicsManager::removeSceneWidget(CSVRender::WorldspaceWidget *widget) + { + CSVRender::SceneWidget *sceneWidget = static_cast(widget); + + std::map >::iterator iter = mSceneWidgets.begin(); + for(; iter != mSceneWidgets.end(); ++iter) + { + std::list::iterator itWidget = (*iter).second.begin(); + for(; itWidget != (*iter).second.end(); ++itWidget) + { + if((*itWidget) == sceneWidget) + { + (*iter).second.erase(itWidget); + + if((*iter).second.empty()) // last one for the document + { + delete mPhysics[(*iter).first]; + mPhysics.erase((*iter).first); + mSceneWidgets.erase(iter); + } + + break; + } + } + } + } +} diff --git a/apps/opencs/view/world/physicsmanager.hpp b/apps/opencs/view/world/physicsmanager.hpp new file mode 100644 index 0000000000..7bcd5d39de --- /dev/null +++ b/apps/opencs/view/world/physicsmanager.hpp @@ -0,0 +1,58 @@ +#ifndef CSV_WORLD_PHYSICSMANAGER_H +#define CSV_WORLD_PHYSICSMANAGER_H + +#include +#include + +namespace Ogre +{ + class SceneManager; +} + +namespace CSMDoc +{ + class Document; +} + +namespace CSVRender +{ + class WorldspaceWidget; + class SceneWidget; +} + +namespace CSVWorld +{ + class PhysicsSystem; +} + +namespace CSVWorld +{ + class PhysicsManager + { + static PhysicsManager *mPhysicsManagerInstance; + + //std::map mSceneManagers; + std::map > mSceneWidgets; + std::map mPhysics; + + public: + + PhysicsManager(); + ~PhysicsManager(); + + static PhysicsManager *instance(); + + void setupPhysics(CSMDoc::Document *); +#if 0 + void addSceneManager(CSVRender::SceneWidget *sceneWidget, Ogre::SceneManager *sceneMgr); + + void removeSceneManager(CSVRender::SceneWidget *sceneWidget); +#endif + + PhysicsSystem *addSceneWidget(CSMDoc::Document &doc, CSVRender::WorldspaceWidget *widget); + + void removeSceneWidget(CSVRender::WorldspaceWidget *widget); + }; +} + +#endif // CSV_WORLD_PHYSICSMANAGER_H