mirror of
https://github.com/OpenMW/openmw.git
synced 2025-02-01 09:45:35 +00:00
Preload cell when the player goes near a teleport door. It works!
This commit is contained in:
parent
c155680d3c
commit
023c87b215
3 changed files with 63 additions and 0 deletions
|
@ -66,6 +66,7 @@ namespace MWWorld
|
||||||
/// Preload work to be called from the worker thread.
|
/// Preload work to be called from the worker thread.
|
||||||
virtual void doWork()
|
virtual void doWork()
|
||||||
{
|
{
|
||||||
|
osg::Timer preloadTimer;
|
||||||
for (MeshList::const_iterator it = mMeshes.begin(); it != mMeshes.end(); ++it)
|
for (MeshList::const_iterator it = mMeshes.begin(); it != mMeshes.end(); ++it)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
|
@ -81,6 +82,7 @@ namespace MWWorld
|
||||||
// error will be shown when visiting the cell
|
// error will be shown when visiting the cell
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
std::cout << "preloaded " << mPreloadedNodes.size() << " nodes in " << preloadTimer.time_m() << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
|
@ -193,6 +193,13 @@ namespace MWWorld
|
||||||
|
|
||||||
void Scene::update (float duration, bool paused)
|
void Scene::update (float duration, bool paused)
|
||||||
{
|
{
|
||||||
|
mPreloadTimer += duration;
|
||||||
|
if (mPreloadTimer > 1.f)
|
||||||
|
{
|
||||||
|
preloadCells();
|
||||||
|
mPreloadTimer = 0.f;
|
||||||
|
}
|
||||||
|
|
||||||
mRendering.update (duration, paused);
|
mRendering.update (duration, paused);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -440,6 +447,7 @@ namespace MWWorld
|
||||||
|
|
||||||
Scene::Scene (MWRender::RenderingManager& rendering, MWPhysics::PhysicsSystem *physics)
|
Scene::Scene (MWRender::RenderingManager& rendering, MWPhysics::PhysicsSystem *physics)
|
||||||
: mCurrentCell (0), mCellChanged (false), mPhysics(physics), mRendering(rendering)
|
: mCurrentCell (0), mCellChanged (false), mPhysics(physics), mRendering(rendering)
|
||||||
|
, mPreloadTimer(0.f)
|
||||||
{
|
{
|
||||||
mPreloader.reset(new CellPreloader(rendering.getResourceSystem(), physics->getShapeManager()));
|
mPreloader.reset(new CellPreloader(rendering.getResourceSystem(), physics->getShapeManager()));
|
||||||
}
|
}
|
||||||
|
@ -603,4 +611,54 @@ namespace MWWorld
|
||||||
|
|
||||||
return Ptr();
|
return Ptr();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Scene::preloadCells()
|
||||||
|
{
|
||||||
|
std::vector<MWWorld::ConstPtr> teleportDoors;
|
||||||
|
for (CellStoreCollection::const_iterator iter (mActiveCells.begin());
|
||||||
|
iter!=mActiveCells.end(); ++iter)
|
||||||
|
{
|
||||||
|
const MWWorld::CellStore* cellStore = *iter;
|
||||||
|
typedef MWWorld::CellRefList<ESM::Door>::List DoorList;
|
||||||
|
const DoorList &doors = cellStore->getReadOnlyDoors().mList;
|
||||||
|
for (DoorList::const_iterator doorIt = doors.begin(); doorIt != doors.end(); ++doorIt)
|
||||||
|
{
|
||||||
|
if (!doorIt->mRef.getTeleport()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
teleportDoors.push_back(MWWorld::ConstPtr(&*doorIt, cellStore));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const MWWorld::ConstPtr player = MWBase::Environment::get().getWorld()->getPlayerPtr();
|
||||||
|
const float preloadDist = 500.f;
|
||||||
|
|
||||||
|
for (std::vector<MWWorld::ConstPtr>::iterator it = teleportDoors.begin(); it != teleportDoors.end(); ++it)
|
||||||
|
{
|
||||||
|
const MWWorld::ConstPtr& door = *it;
|
||||||
|
float sqrDistToPlayer = (player.getRefData().getPosition().asVec3() - door.getRefData().getPosition().asVec3()).length2();
|
||||||
|
|
||||||
|
if (sqrDistToPlayer < preloadDist*preloadDist)
|
||||||
|
{
|
||||||
|
MWWorld::CellStore* targetCell = NULL;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (!door.getCellRef().getDestCell().empty())
|
||||||
|
targetCell = MWBase::Environment::get().getWorld()->getInterior(door.getCellRef().getDestCell());
|
||||||
|
else
|
||||||
|
{
|
||||||
|
int x,y;
|
||||||
|
MWBase::Environment::get().getWorld()->positionToIndex (door.getCellRef().getDoorDest().pos[0], door.getCellRef().getDoorDest().pos[1], x, y);
|
||||||
|
targetCell = MWBase::Environment::get().getWorld()->getExterior(x, y);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (std::exception& e)
|
||||||
|
{
|
||||||
|
// ignore error for now, would spam the log too much
|
||||||
|
}
|
||||||
|
if (targetCell)
|
||||||
|
mPreloader->preload(targetCell, mRendering.getReferenceTime());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -58,6 +58,7 @@ namespace MWWorld
|
||||||
MWPhysics::PhysicsSystem *mPhysics;
|
MWPhysics::PhysicsSystem *mPhysics;
|
||||||
MWRender::RenderingManager& mRendering;
|
MWRender::RenderingManager& mRendering;
|
||||||
std::auto_ptr<CellPreloader> mPreloader;
|
std::auto_ptr<CellPreloader> mPreloader;
|
||||||
|
float mPreloadTimer;
|
||||||
|
|
||||||
void insertCell (CellStore &cell, bool rescale, Loading::Listener* loadingListener);
|
void insertCell (CellStore &cell, bool rescale, Loading::Listener* loadingListener);
|
||||||
|
|
||||||
|
@ -112,6 +113,8 @@ namespace MWWorld
|
||||||
bool isCellActive(const CellStore &cell);
|
bool isCellActive(const CellStore &cell);
|
||||||
|
|
||||||
Ptr searchPtrViaActorId (int actorId);
|
Ptr searchPtrViaActorId (int actorId);
|
||||||
|
|
||||||
|
void preloadCells();
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue