mirror of
https://github.com/OpenMW/openmw.git
synced 2025-01-21 06:53:53 +00:00
Fix memory leak when multiple documents in 3D edit. Support multiple physics engine per document.
This commit is contained in:
parent
03abd69b4f
commit
f051fb65ff
7 changed files with 106 additions and 18 deletions
|
@ -2,7 +2,6 @@
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
#include <OgreRoot.h>
|
|
||||||
#include <openengine/bullet/BulletShapeLoader.h>
|
#include <openengine/bullet/BulletShapeLoader.h>
|
||||||
|
|
||||||
#include "../render/worldspacewidget.hpp"
|
#include "../render/worldspacewidget.hpp"
|
||||||
|
@ -58,15 +57,9 @@ namespace CSVWorld
|
||||||
mSceneWidgets.erase(it);
|
mSceneWidgets.erase(it);
|
||||||
}
|
}
|
||||||
|
|
||||||
// cleanup global resources
|
// cleanup global resources used by OEngine
|
||||||
if(mPhysics.empty())
|
if(mPhysics.empty())
|
||||||
{
|
{
|
||||||
// delete the extra resources created in removeDebugDraw
|
|
||||||
if (Ogre::MaterialManager::getSingleton().resourceExists("BtOgre/DebugLines"))
|
|
||||||
Ogre::MaterialManager::getSingleton().remove("BtOgre/DebugLines");
|
|
||||||
if (Ogre::ResourceGroupManager::getSingleton().resourceGroupExists("BtOgre"))
|
|
||||||
Ogre::ResourceGroupManager::getSingleton().destroyResourceGroup("BtOgre");
|
|
||||||
|
|
||||||
delete OEngine::Physic::BulletShapeManager::getSingletonPtr();
|
delete OEngine::Physic::BulletShapeManager::getSingletonPtr();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
#include <OgreCamera.h>
|
#include <OgreCamera.h>
|
||||||
#include <OgreSceneManager.h>
|
#include <OgreSceneManager.h>
|
||||||
|
|
||||||
#include "physicsengine.hpp"
|
#include <openengine/bullet/physic.hpp>
|
||||||
#include <components/nifbullet/bulletnifloader.hpp>
|
#include <components/nifbullet/bulletnifloader.hpp>
|
||||||
#include "../../model/settings/usersettings.hpp"
|
#include "../../model/settings/usersettings.hpp"
|
||||||
#include "../render/elements.hpp"
|
#include "../render/elements.hpp"
|
||||||
|
@ -15,7 +15,9 @@ namespace CSVWorld
|
||||||
{
|
{
|
||||||
PhysicsSystem::PhysicsSystem()
|
PhysicsSystem::PhysicsSystem()
|
||||||
{
|
{
|
||||||
mEngine = new PhysicsEngine();
|
// Create physics. shapeLoader is deleted by the physic engine
|
||||||
|
NifBullet::ManualBulletShapeLoader* shapeLoader = new NifBullet::ManualBulletShapeLoader();
|
||||||
|
mEngine = new OEngine::Physic::PhysicEngine(shapeLoader);
|
||||||
}
|
}
|
||||||
|
|
||||||
PhysicsSystem::~PhysicsSystem()
|
PhysicsSystem::~PhysicsSystem()
|
||||||
|
@ -51,6 +53,8 @@ namespace CSVWorld
|
||||||
{
|
{
|
||||||
mEngine->createAndAdjustRigidBody(mesh,
|
mEngine->createAndAdjustRigidBody(mesh,
|
||||||
referenceId, scale, position, rotation,
|
referenceId, scale, position, rotation,
|
||||||
|
0, // scaledBoxTranslation
|
||||||
|
0, // boxRotation
|
||||||
true, // raycasting
|
true, // raycasting
|
||||||
placeable);
|
placeable);
|
||||||
}
|
}
|
||||||
|
@ -139,7 +143,7 @@ namespace CSVWorld
|
||||||
|
|
||||||
// create a new physics object
|
// create a new physics object
|
||||||
mEngine->createAndAdjustRigidBody(mesh, referenceId, scale, position, rotation,
|
mEngine->createAndAdjustRigidBody(mesh, referenceId, scale, position, rotation,
|
||||||
true, placeable);
|
0, 0, true, placeable);
|
||||||
|
|
||||||
// update other scene managers if they have the referenceId
|
// update other scene managers if they have the referenceId
|
||||||
// FIXME: rotation or scale not updated
|
// FIXME: rotation or scale not updated
|
||||||
|
|
|
@ -12,6 +12,14 @@ namespace Ogre
|
||||||
class Camera;
|
class Camera;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace OEngine
|
||||||
|
{
|
||||||
|
namespace Physic
|
||||||
|
{
|
||||||
|
class PhysicEngine;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
namespace CSVRender
|
namespace CSVRender
|
||||||
{
|
{
|
||||||
class SceneWidget;
|
class SceneWidget;
|
||||||
|
@ -19,15 +27,13 @@ namespace CSVRender
|
||||||
|
|
||||||
namespace CSVWorld
|
namespace CSVWorld
|
||||||
{
|
{
|
||||||
class PhysicsEngine;
|
|
||||||
|
|
||||||
class PhysicsSystem
|
class PhysicsSystem
|
||||||
{
|
{
|
||||||
std::map<std::string, std::string> mSceneNodeToRefId;
|
std::map<std::string, std::string> mSceneNodeToRefId;
|
||||||
std::map<std::string, std::map<Ogre::SceneManager *, std::string> > mRefIdToSceneNode;
|
std::map<std::string, std::map<Ogre::SceneManager *, std::string> > mRefIdToSceneNode;
|
||||||
std::map<std::string, std::string> mSceneNodeToMesh;
|
std::map<std::string, std::string> mSceneNodeToMesh;
|
||||||
std::map<Ogre::SceneManager*, CSVRender::SceneWidget *> mSceneWidgets;
|
std::map<Ogre::SceneManager*, CSVRender::SceneWidget *> mSceneWidgets;
|
||||||
PhysicsEngine* mEngine;
|
OEngine::Physic::PhysicEngine* mEngine;
|
||||||
std::multimap<std::string, Ogre::SceneManager *> mTerrain;
|
std::multimap<std::string, Ogre::SceneManager *> mTerrain;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
|
@ -14,6 +14,7 @@
|
||||||
#include <openengine/bullet/physic.hpp>
|
#include <openengine/bullet/physic.hpp>
|
||||||
#include <openengine/bullet/BtOgreExtras.h>
|
#include <openengine/bullet/BtOgreExtras.h>
|
||||||
#include <openengine/ogre/renderer.hpp>
|
#include <openengine/ogre/renderer.hpp>
|
||||||
|
#include <openengine/bullet/BulletShapeLoader.h>
|
||||||
|
|
||||||
#include <components/nifbullet/bulletnifloader.hpp>
|
#include <components/nifbullet/bulletnifloader.hpp>
|
||||||
|
|
||||||
|
@ -498,6 +499,7 @@ namespace MWWorld
|
||||||
if (mWaterCollisionObject.get())
|
if (mWaterCollisionObject.get())
|
||||||
mEngine->mDynamicsWorld->removeCollisionObject(mWaterCollisionObject.get());
|
mEngine->mDynamicsWorld->removeCollisionObject(mWaterCollisionObject.get());
|
||||||
delete mEngine;
|
delete mEngine;
|
||||||
|
delete OEngine::Physic::BulletShapeManager::getSingletonPtr();
|
||||||
}
|
}
|
||||||
|
|
||||||
OEngine::Physic::PhysicEngine* PhysicsSystem::getEngine()
|
OEngine::Physic::PhysicEngine* PhysicsSystem::getEngine()
|
||||||
|
|
|
@ -212,8 +212,10 @@ public:
|
||||||
|
|
||||||
~DebugDrawer()
|
~DebugDrawer()
|
||||||
{
|
{
|
||||||
Ogre::MaterialManager::getSingleton().remove("BtOgre/DebugLines");
|
if (Ogre::MaterialManager::getSingleton().resourceExists("BtOgre/DebugLines"))
|
||||||
Ogre::ResourceGroupManager::getSingleton().destroyResourceGroup("BtOgre");
|
Ogre::MaterialManager::getSingleton().remove("BtOgre/DebugLines");
|
||||||
|
if (Ogre::ResourceGroupManager::getSingleton().resourceGroupExists("BtOgre"))
|
||||||
|
Ogre::ResourceGroupManager::getSingleton().destroyResourceGroup("BtOgre");
|
||||||
delete mLineDrawer;
|
delete mLineDrawer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -356,7 +356,8 @@ namespace Physic
|
||||||
delete broadphase;
|
delete broadphase;
|
||||||
delete mShapeLoader;
|
delete mShapeLoader;
|
||||||
|
|
||||||
delete BulletShapeManager::getSingletonPtr();
|
// Moved the cleanup to mwworld/physicssystem
|
||||||
|
//delete BulletShapeManager::getSingletonPtr();
|
||||||
}
|
}
|
||||||
|
|
||||||
void PhysicEngine::addHeightField(float* heights,
|
void PhysicEngine::addHeightField(float* heights,
|
||||||
|
@ -863,5 +864,76 @@ namespace Physic
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int PhysicEngine::toggleDebugRendering(Ogre::SceneManager *sceneMgr)
|
||||||
|
{
|
||||||
|
if(!sceneMgr)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
std::map<Ogre::SceneManager *, BtOgre::DebugDrawer *>::iterator iter =
|
||||||
|
mDebugDrawers.find(sceneMgr);
|
||||||
|
if(iter != mDebugDrawers.end()) // found scene manager
|
||||||
|
{
|
||||||
|
if((*iter).second)
|
||||||
|
{
|
||||||
|
// set a new drawer each time (maybe with a different scene manager)
|
||||||
|
mDynamicsWorld->setDebugDrawer(mDebugDrawers[sceneMgr]);
|
||||||
|
if(!mDebugDrawers[sceneMgr]->getDebugMode())
|
||||||
|
mDebugDrawers[sceneMgr]->setDebugMode(1 /*mDebugDrawFlags*/);
|
||||||
|
else
|
||||||
|
mDebugDrawers[sceneMgr]->setDebugMode(0);
|
||||||
|
mDynamicsWorld->debugDrawWorld();
|
||||||
|
|
||||||
|
return mDebugDrawers[sceneMgr]->getDebugMode();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PhysicEngine::stepDebug(Ogre::SceneManager *sceneMgr)
|
||||||
|
{
|
||||||
|
if(!sceneMgr)
|
||||||
|
return;
|
||||||
|
|
||||||
|
std::map<Ogre::SceneManager *, BtOgre::DebugDrawer *>::iterator iter =
|
||||||
|
mDebugDrawers.find(sceneMgr);
|
||||||
|
if(iter != mDebugDrawers.end()) // found scene manager
|
||||||
|
{
|
||||||
|
if((*iter).second)
|
||||||
|
(*iter).second->step();
|
||||||
|
else
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PhysicEngine::createDebugDraw(Ogre::SceneManager *sceneMgr)
|
||||||
|
{
|
||||||
|
if(mDebugDrawers.find(sceneMgr) == mDebugDrawers.end())
|
||||||
|
{
|
||||||
|
mDebugSceneNodes[sceneMgr] = sceneMgr->getRootSceneNode()->createChildSceneNode();
|
||||||
|
mDebugDrawers[sceneMgr] = new BtOgre::DebugDrawer(mDebugSceneNodes[sceneMgr], mDynamicsWorld);
|
||||||
|
mDebugDrawers[sceneMgr]->setDebugMode(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PhysicEngine::removeDebugDraw(Ogre::SceneManager *sceneMgr)
|
||||||
|
{
|
||||||
|
std::map<Ogre::SceneManager *, BtOgre::DebugDrawer *>::iterator iter =
|
||||||
|
mDebugDrawers.find(sceneMgr);
|
||||||
|
if(iter != mDebugDrawers.end())
|
||||||
|
{
|
||||||
|
delete (*iter).second;
|
||||||
|
mDebugDrawers.erase(iter);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::map<Ogre::SceneManager *, Ogre::SceneNode *>::iterator it =
|
||||||
|
mDebugSceneNodes.find(sceneMgr);
|
||||||
|
if(it != mDebugSceneNodes.end())
|
||||||
|
{
|
||||||
|
std::string sceneNodeName = (*it).second->getName();
|
||||||
|
if(sceneMgr->hasSceneNode(sceneNodeName))
|
||||||
|
sceneMgr->destroySceneNode(sceneNodeName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -348,6 +348,15 @@ namespace Physic
|
||||||
bool isDebugCreated;
|
bool isDebugCreated;
|
||||||
bool mDebugActive;
|
bool mDebugActive;
|
||||||
|
|
||||||
|
// for OpenCS with multiple engines per document
|
||||||
|
std::map<Ogre::SceneManager *, BtOgre::DebugDrawer *> mDebugDrawers;
|
||||||
|
std::map<Ogre::SceneManager *, Ogre::SceneNode *> mDebugSceneNodes;
|
||||||
|
|
||||||
|
int toggleDebugRendering(Ogre::SceneManager *sceneMgr);
|
||||||
|
void stepDebug(Ogre::SceneManager *sceneMgr);
|
||||||
|
void createDebugDraw(Ogre::SceneManager *sceneMgr);
|
||||||
|
void removeDebugDraw(Ogre::SceneManager *sceneMgr);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
PhysicEngine(const PhysicEngine&);
|
PhysicEngine(const PhysicEngine&);
|
||||||
PhysicEngine& operator=(const PhysicEngine&);
|
PhysicEngine& operator=(const PhysicEngine&);
|
||||||
|
|
Loading…
Reference in a new issue