From 03b86c232be6788443f687cd58acf98794e43db1 Mon Sep 17 00:00:00 2001 From: fredzio Date: Sat, 13 Mar 2021 09:52:05 +0100 Subject: [PATCH] Apply the position offset even if the simulation is not performed because we're too fast. --- apps/openmw/mwphysics/actor.cpp | 11 +++++++++++ apps/openmw/mwphysics/actor.hpp | 7 +++++++ apps/openmw/mwphysics/mtphysics.cpp | 1 + apps/openmw/mwphysics/physicssystem.cpp | 4 ++++ 4 files changed, 23 insertions(+) diff --git a/apps/openmw/mwphysics/actor.cpp b/apps/openmw/mwphysics/actor.cpp index bbec4d445..06abe7240 100644 --- a/apps/openmw/mwphysics/actor.cpp +++ b/apps/openmw/mwphysics/actor.cpp @@ -190,6 +190,17 @@ void Actor::adjustPosition(const osg::Vec3f& offset) mPositionOffset += offset; } +void Actor::applyOffsetChange() +{ + if (mPositionOffset.length() == 0) + return; + mWorldPosition += mPositionOffset; + mPosition += mPositionOffset; + mPreviousPosition += mPositionOffset; + mPositionOffset = osg::Vec3f(); + mWorldPositionChanged = true; +} + osg::Vec3f Actor::getPosition() const { return mPosition; diff --git a/apps/openmw/mwphysics/actor.hpp b/apps/openmw/mwphysics/actor.hpp index 9d129f2ba..031125f40 100644 --- a/apps/openmw/mwphysics/actor.hpp +++ b/apps/openmw/mwphysics/actor.hpp @@ -96,9 +96,16 @@ namespace MWPhysics * Returns true if the new position is different. */ bool setPosition(const osg::Vec3f& position); + + // force set actor position to be as in Ptr::RefData void updatePosition(); + + // register a position offset that will be applied during simulation. void adjustPosition(const osg::Vec3f& offset); + // apply position offset. Can't be called during simulation + void applyOffsetChange(); + osg::Vec3f getPosition() const; osg::Vec3f getPreviousPosition() const; diff --git a/apps/openmw/mwphysics/mtphysics.cpp b/apps/openmw/mwphysics/mtphysics.cpp index 754bb60af..2b0db5b82 100644 --- a/apps/openmw/mwphysics/mtphysics.cpp +++ b/apps/openmw/mwphysics/mtphysics.cpp @@ -492,6 +492,7 @@ namespace MWPhysics if (actor->setPosition(actorData.mPosition)) { std::scoped_lock lock(mCollisionWorldMutex); + actorData.mPosition = actor->getPosition(); // account for potential position change made by script actor->updateCollisionObjectPosition(); mCollisionWorld->updateSingleAabb(actor->getCollisionObject()); } diff --git a/apps/openmw/mwphysics/physicssystem.cpp b/apps/openmw/mwphysics/physicssystem.cpp index b2decde2f..dc9ab629a 100644 --- a/apps/openmw/mwphysics/physicssystem.cpp +++ b/apps/openmw/mwphysics/physicssystem.cpp @@ -961,6 +961,10 @@ namespace MWPhysics void ActorFrameData::updatePosition() { mActorRaw->updateWorldPosition(); + // If physics runs "fast enough", position are interpolated without simulation + // By calling this here, we are sure that offsets are applied at least once per frame, + // regardless of simulation speed. + mActorRaw->applyOffsetChange(); mPosition = mActorRaw->getPosition(); if (mMoveToWaterSurface) {