Define single UpdateGuard type in a separate file

7344-support-launching-the-example-suite
elsid 2 years ago
parent 472a36d92a
commit 7a7c20d49e
No known key found for this signature in database
GPG Key ID: 4DE04C198CBA7625

@ -279,7 +279,7 @@ namespace NavMeshTool
return *it->second;
}();
const TileCachedRecastMeshManager::UpdateGuard guard(navMeshInput.mTileCachedRecastMeshManager);
const auto guard = navMeshInput.mTileCachedRecastMeshManager.makeUpdateGuard();
if (exterior)
{
@ -293,15 +293,15 @@ namespace NavMeshTool
getAabb(cellPosition, minHeight, maxHeight), navMeshInput.mAabb, navMeshInput.mAabbInitialized);
navMeshInput.mTileCachedRecastMeshManager.addHeightfield(
cellPosition, ESM::Land::REAL_SIZE, heightfieldShape, &guard);
cellPosition, ESM::Land::REAL_SIZE, heightfieldShape, guard.get());
navMeshInput.mTileCachedRecastMeshManager.addWater(cellPosition, ESM::Land::REAL_SIZE, -1, &guard);
navMeshInput.mTileCachedRecastMeshManager.addWater(cellPosition, ESM::Land::REAL_SIZE, -1, guard.get());
}
else
{
if ((cell.mData.mFlags & ESM::Cell::HasWater) != 0)
navMeshInput.mTileCachedRecastMeshManager.addWater(
cellPosition, std::numeric_limits<int>::max(), cell.mWater, &guard);
cellPosition, std::numeric_limits<int>::max(), cell.mWater, guard.get());
}
forEachObject(cell, esmData, vfs, bulletShapeManager, readers, [&](BulletObject object) {
@ -319,13 +319,13 @@ namespace NavMeshTool
object.getObjectTransform());
navMeshInput.mTileCachedRecastMeshManager.addObject(
objectId, shape, transform, DetourNavigator::AreaType_ground, &guard);
objectId, shape, transform, DetourNavigator::AreaType_ground, guard.get());
if (const btCollisionShape* avoid = object.getShapeInstance()->mAvoidCollisionShape.get())
{
const CollisionShape avoidShape(object.getShapeInstance(), *avoid, object.getObjectTransform());
navMeshInput.mTileCachedRecastMeshManager.addObject(
objectId, avoidShape, transform, DetourNavigator::AreaType_null, &guard);
objectId, avoidShape, transform, DetourNavigator::AreaType_null, guard.get());
}
data.mObjects.emplace_back(std::move(object));

@ -11,7 +11,7 @@
#include <components/detournavigator/debug.hpp>
#include <components/detournavigator/heightfieldshape.hpp>
#include <components/detournavigator/navigator.hpp>
#include <components/detournavigator/navigatorimpl.hpp>
#include <components/detournavigator/updateguard.hpp>
#include <components/esm/records.hpp>
#include <components/loadinglistener/loadinglistener.hpp>
#include <components/misc/convert.hpp>

@ -45,9 +45,9 @@
#include <components/detournavigator/agentbounds.hpp>
#include <components/detournavigator/debug.hpp>
#include <components/detournavigator/navigator.hpp>
#include <components/detournavigator/navigatorimpl.hpp>
#include <components/detournavigator/settings.hpp>
#include <components/detournavigator/stats.hpp>
#include <components/detournavigator/updateguard.hpp>
#include <components/files/conversion.hpp>
#include <components/loadinglistener/loadinglistener.hpp>

@ -398,6 +398,7 @@ add_component_dir(detournavigator
tilecachedrecastmeshmanager
tileposition
tilespositionsrange
updateguard
version
waitconditiontype
)

@ -8,6 +8,7 @@
#include "objecttransform.hpp"
#include "recastmeshtiles.hpp"
#include "sharednavmeshcacheitem.hpp"
#include "updateguard.hpp"
#include "waitconditiontype.hpp"
#include <components/resource/bulletshape.hpp>
@ -58,8 +59,6 @@ namespace DetourNavigator
}
};
class UpdateGuard;
/**
* @brief Top level interface of detournavigator component. Navigator allows to build a scene with navmesh and find
* a path for an agent there. Scene contains agents, geometry objects and water. Agent are distinguished only by
@ -71,7 +70,7 @@ namespace DetourNavigator
{
virtual ~Navigator() = default;
virtual std::unique_ptr<const UpdateGuard> makeUpdateGuard() = 0;
virtual ScopedUpdateGuard makeUpdateGuard() = 0;
/**
* @brief addAgent should be called for each agent even if all of them has same half extents.

@ -35,12 +35,12 @@ namespace DetourNavigator
void NavigatorImpl::setWorldspace(std::string_view worldspace, const UpdateGuard* guard)
{
mNavMeshManager.setWorldspace(worldspace, getImpl(guard));
mNavMeshManager.setWorldspace(worldspace, guard);
}
void NavigatorImpl::updateBounds(const osg::Vec3f& playerPosition, const UpdateGuard* guard)
{
mNavMeshManager.updateBounds(playerPosition, getImpl(guard));
mNavMeshManager.updateBounds(playerPosition, guard);
}
void NavigatorImpl::addObject(
@ -54,12 +54,12 @@ namespace DetourNavigator
{
const CollisionShape collisionShape(
shapes.mShapeInstance, *shapes.mShapeInstance->mCollisionShape, shapes.mTransform);
bool result = mNavMeshManager.addObject(id, collisionShape, transform, AreaType_ground, getImpl(guard));
bool result = mNavMeshManager.addObject(id, collisionShape, transform, AreaType_ground, guard);
if (const btCollisionShape* const avoidShape = shapes.mShapeInstance->mAvoidCollisionShape.get())
{
const ObjectId avoidId(avoidShape);
const CollisionShape avoidCollisionShape(shapes.mShapeInstance, *avoidShape, shapes.mTransform);
if (mNavMeshManager.addObject(avoidId, avoidCollisionShape, transform, AreaType_null, getImpl(guard)))
if (mNavMeshManager.addObject(avoidId, avoidCollisionShape, transform, AreaType_null, guard))
{
updateAvoidShapeId(id, avoidId, guard);
result = true;
@ -83,11 +83,11 @@ namespace DetourNavigator
void NavigatorImpl::updateObject(
const ObjectId id, const ObjectShapes& shapes, const btTransform& transform, const UpdateGuard* guard)
{
mNavMeshManager.updateObject(id, transform, AreaType_ground, getImpl(guard));
mNavMeshManager.updateObject(id, transform, AreaType_ground, guard);
if (const btCollisionShape* const avoidShape = shapes.mShapeInstance->mAvoidCollisionShape.get())
{
const ObjectId avoidId(avoidShape);
if (mNavMeshManager.updateObject(avoidId, transform, AreaType_null, getImpl(guard)))
if (mNavMeshManager.updateObject(avoidId, transform, AreaType_null, guard))
updateAvoidShapeId(id, avoidId, guard);
}
}
@ -100,35 +100,35 @@ namespace DetourNavigator
void NavigatorImpl::removeObject(const ObjectId id, const UpdateGuard* guard)
{
mNavMeshManager.removeObject(id, getImpl(guard));
mNavMeshManager.removeObject(id, guard);
const auto avoid = mAvoidIds.find(id);
if (avoid != mAvoidIds.end())
mNavMeshManager.removeObject(avoid->second, getImpl(guard));
mNavMeshManager.removeObject(avoid->second, guard);
const auto water = mWaterIds.find(id);
if (water != mWaterIds.end())
mNavMeshManager.removeObject(water->second, getImpl(guard));
mNavMeshManager.removeObject(water->second, guard);
mNavMeshManager.removeOffMeshConnections(id);
}
void NavigatorImpl::addWater(const osg::Vec2i& cellPosition, int cellSize, float level, const UpdateGuard* guard)
{
mNavMeshManager.addWater(cellPosition, cellSize, level, getImpl(guard));
mNavMeshManager.addWater(cellPosition, cellSize, level, guard);
}
void NavigatorImpl::removeWater(const osg::Vec2i& cellPosition, const UpdateGuard* guard)
{
mNavMeshManager.removeWater(cellPosition, getImpl(guard));
mNavMeshManager.removeWater(cellPosition, guard);
}
void NavigatorImpl::addHeightfield(
const osg::Vec2i& cellPosition, int cellSize, const HeightfieldShape& shape, const UpdateGuard* guard)
{
mNavMeshManager.addHeightfield(cellPosition, cellSize, shape, getImpl(guard));
mNavMeshManager.addHeightfield(cellPosition, cellSize, shape, guard);
}
void NavigatorImpl::removeHeightfield(const osg::Vec2i& cellPosition, const UpdateGuard* guard)
{
mNavMeshManager.removeHeightfield(cellPosition, getImpl(guard));
mNavMeshManager.removeHeightfield(cellPosition, guard);
}
void NavigatorImpl::addPathgrid(const ESM::Cell& cell, const ESM::Pathgrid& pathgrid)
@ -151,7 +151,7 @@ namespace DetourNavigator
void NavigatorImpl::update(const osg::Vec3f& playerPosition, const UpdateGuard* guard)
{
removeUnusedNavMeshes();
mNavMeshManager.update(playerPosition, getImpl(guard));
mNavMeshManager.update(playerPosition, guard);
}
void NavigatorImpl::wait(WaitConditionType waitConditionType, Loading::Listener* listener)
@ -195,7 +195,7 @@ namespace DetourNavigator
auto inserted = ids.insert(std::make_pair(id, updateId));
if (!inserted.second)
{
mNavMeshManager.removeObject(inserted.first->second, getImpl(guard));
mNavMeshManager.removeObject(inserted.first->second, guard);
inserted.first->second = updateId;
}
}

@ -3,6 +3,7 @@
#include "navigator.hpp"
#include "navmeshmanager.hpp"
#include "updateguard.hpp"
#include <map>
#include <memory>
@ -21,10 +22,7 @@ namespace DetourNavigator
*/
explicit NavigatorImpl(const Settings& settings, std::unique_ptr<NavMeshDb>&& db);
std::unique_ptr<const DetourNavigator::UpdateGuard> makeUpdateGuard() override
{
return std::make_unique<const UpdateGuard>(*this);
}
ScopedUpdateGuard makeUpdateGuard() override { return mNavMeshManager.makeUpdateGuard(); }
bool addAgent(const AgentBounds& agentBounds) override;
@ -97,23 +95,6 @@ namespace DetourNavigator
friend class UpdateGuard;
};
class UpdateGuard
{
public:
explicit UpdateGuard(NavigatorImpl& navigator)
: mImpl(navigator.mNavMeshManager)
{
}
private:
NavMeshManager::UpdateGuard mImpl;
friend inline const NavMeshManager::UpdateGuard* getImpl(const UpdateGuard* guard)
{
return guard == nullptr ? nullptr : &guard->mImpl;
}
};
}
#endif

@ -4,6 +4,7 @@
#include "navigator.hpp"
#include "settings.hpp"
#include "stats.hpp"
#include "updateguard.hpp"
namespace Loading
{
@ -17,7 +18,7 @@ namespace DetourNavigator
public:
NavigatorStub() = default;
std::unique_ptr<const UpdateGuard> makeUpdateGuard() override { return nullptr; }
ScopedUpdateGuard makeUpdateGuard() override { return nullptr; }
bool addAgent(const AgentBounds& /*agentBounds*/) override { return true; }

@ -64,7 +64,7 @@ namespace DetourNavigator
{
if (worldspace == mWorldspace)
return;
mRecastMeshManager.setWorldspace(worldspace, getImpl(guard));
mRecastMeshManager.setWorldspace(worldspace, guard);
for (auto& [agent, cache] : mCache)
cache = std::make_shared<GuardedNavMeshCacheItem>(++mGenerationCounter, mSettings);
mWorldspace = worldspace;
@ -74,45 +74,45 @@ namespace DetourNavigator
{
const TilePosition playerTile = toNavMeshTilePosition(mSettings.mRecast, playerPosition);
const TilesPositionsRange range = makeRange(playerTile, mSettings.mMaxTilesNumber);
mRecastMeshManager.setRange(range, getImpl(guard));
mRecastMeshManager.setRange(range, guard);
}
bool NavMeshManager::addObject(const ObjectId id, const CollisionShape& shape, const btTransform& transform,
const AreaType areaType, const UpdateGuard* guard)
{
return mRecastMeshManager.addObject(id, shape, transform, areaType, getImpl(guard));
return mRecastMeshManager.addObject(id, shape, transform, areaType, guard);
}
bool NavMeshManager::updateObject(
const ObjectId id, const btTransform& transform, const AreaType areaType, const UpdateGuard* guard)
{
return mRecastMeshManager.updateObject(id, transform, areaType, getImpl(guard));
return mRecastMeshManager.updateObject(id, transform, areaType, guard);
}
void NavMeshManager::removeObject(const ObjectId id, const UpdateGuard* guard)
{
mRecastMeshManager.removeObject(id, getImpl(guard));
mRecastMeshManager.removeObject(id, guard);
}
void NavMeshManager::addWater(const osg::Vec2i& cellPosition, int cellSize, float level, const UpdateGuard* guard)
{
mRecastMeshManager.addWater(cellPosition, cellSize, level, getImpl(guard));
mRecastMeshManager.addWater(cellPosition, cellSize, level, guard);
}
void NavMeshManager::removeWater(const osg::Vec2i& cellPosition, const UpdateGuard* guard)
{
mRecastMeshManager.removeWater(cellPosition, getImpl(guard));
mRecastMeshManager.removeWater(cellPosition, guard);
}
void NavMeshManager::addHeightfield(
const osg::Vec2i& cellPosition, int cellSize, const HeightfieldShape& shape, const UpdateGuard* guard)
{
mRecastMeshManager.addHeightfield(cellPosition, cellSize, shape, getImpl(guard));
mRecastMeshManager.addHeightfield(cellPosition, cellSize, shape, guard);
}
void NavMeshManager::removeHeightfield(const osg::Vec2i& cellPosition, const UpdateGuard* guard)
{
mRecastMeshManager.removeHeightfield(cellPosition, getImpl(guard));
mRecastMeshManager.removeHeightfield(cellPosition, guard);
}
void NavMeshManager::addAgent(const AgentBounds& agentBounds)
@ -166,7 +166,7 @@ namespace DetourNavigator
return;
mLastRecastMeshManagerRevision = mRecastMeshManager.getRevision();
mPlayerTile = playerTile;
const auto changedTiles = mRecastMeshManager.takeChangedTiles(getImpl(guard));
const auto changedTiles = mRecastMeshManager.takeChangedTiles(guard);
const TilesPositionsRange range = mRecastMeshManager.getLimitedObjectsRange();
for (const auto& [agentBounds, cached] : mCache)
update(agentBounds, playerTile, range, cached, changedTiles);

@ -20,25 +20,10 @@ namespace DetourNavigator
class NavMeshManager
{
public:
class UpdateGuard
{
public:
explicit UpdateGuard(NavMeshManager& manager)
: mImpl(manager.mRecastMeshManager)
{
}
friend const TileCachedRecastMeshManager::UpdateGuard* getImpl(const UpdateGuard* guard)
{
return guard == nullptr ? nullptr : &guard->mImpl;
}
private:
const TileCachedRecastMeshManager::UpdateGuard mImpl;
};
explicit NavMeshManager(const Settings& settings, std::unique_ptr<NavMeshDb>&& db);
ScopedUpdateGuard makeUpdateGuard() { return mRecastMeshManager.makeUpdateGuard(); }
void setWorldspace(std::string_view worldspace, const UpdateGuard* guard);
void updateBounds(const osg::Vec3f& playerPosition, const UpdateGuard* guard);

@ -3,6 +3,7 @@
#include "gettilespositions.hpp"
#include "recastmeshbuilder.hpp"
#include "settingsutils.hpp"
#include "updateguard.hpp"
#include <components/bullethelpers/aabb.hpp>
#include <components/misc/convert.hpp>
@ -45,7 +46,7 @@ namespace DetourNavigator
class MaybeLockGuard
{
public:
explicit MaybeLockGuard(Mutex& mutex, const TileCachedRecastMeshManager::UpdateGuard* guard)
explicit MaybeLockGuard(Mutex& mutex, const UpdateGuard* guard)
: mImpl(guard == nullptr ? std::optional<std::unique_lock<Mutex>>(mutex) : std::nullopt)
{
}

@ -10,6 +10,7 @@
#include "recastmesh.hpp"
#include "recastmeshobject.hpp"
#include "tileposition.hpp"
#include "updateguard.hpp"
#include "version.hpp"
#include <boost/geometry/geometries/box.hpp>
@ -36,20 +37,14 @@ namespace DetourNavigator
class TileCachedRecastMeshManager
{
public:
class UpdateGuard
{
public:
explicit UpdateGuard(TileCachedRecastMeshManager& manager)
: mImpl(manager.mMutex)
{
}
private:
const std::lock_guard<std::mutex> mImpl;
};
explicit TileCachedRecastMeshManager(const RecastSettings& settings);
ScopedUpdateGuard makeUpdateGuard()
{
mMutex.lock();
return ScopedUpdateGuard(&mUpdateGuard);
}
void setRange(const TilesPositionsRange& range, const UpdateGuard* guard);
TilesPositionsRange getLimitedObjectsRange() const;
@ -147,6 +142,7 @@ namespace DetourNavigator
std::size_t mGeneration = 0;
std::size_t mRevision = 0;
mutable std::mutex mMutex;
UpdateGuard mUpdateGuard{ mMutex };
inline static IndexPoint makeIndexPoint(const TilePosition& tilePosition);

@ -0,0 +1,31 @@
#ifndef OPENMW_COMPONENTS_DETOURNAVIGATOR_UPDATEGUARD_H
#define OPENMW_COMPONENTS_DETOURNAVIGATOR_UPDATEGUARD_H
#include <memory>
#include <mutex>
namespace DetourNavigator
{
class UpdateGuard
{
public:
explicit UpdateGuard(std::mutex& mutex)
: mMutex(mutex)
{
}
private:
std::mutex& mMutex;
friend struct UnlockUpdateGuard;
};
struct UnlockUpdateGuard
{
void operator()(UpdateGuard* value) const { value->mMutex.unlock(); }
};
using ScopedUpdateGuard = std::unique_ptr<UpdateGuard, UnlockUpdateGuard>;
}
#endif
Loading…
Cancel
Save