Initial work on dynamic physics object rewind
This commit is contained in:
parent
7e2d25d4a9
commit
99659e8021
@ -27,8 +27,6 @@
|
||||
#include "network/rewind_info.hpp"
|
||||
#include "physics/physics.hpp"
|
||||
#include "race/history.hpp"
|
||||
#include "tracks/track.hpp"
|
||||
#include "tracks/track_object_manager.hpp"
|
||||
#include "utils/log.hpp"
|
||||
#include "utils/profiler.hpp"
|
||||
|
||||
@ -292,8 +290,6 @@ void RewindManager::playEventsTill(int world_ticks, int *ticks)
|
||||
void RewindManager::rewindTo(int rewind_ticks, int now_ticks)
|
||||
{
|
||||
assert(!m_is_rewinding);
|
||||
// TODO Do it properly for track objects like soccer ball
|
||||
Track::getCurrentTrack()->getTrackObjectManager()->removeForRewind();
|
||||
bool is_history = history->replayHistory();
|
||||
history->setReplayHistory(false);
|
||||
|
||||
@ -385,6 +381,5 @@ void RewindManager::rewindTo(int rewind_ticks, int now_ticks)
|
||||
}
|
||||
|
||||
history->setReplayHistory(is_history);
|
||||
Track::getCurrentTrack()->getTrackObjectManager()->addForRewind();
|
||||
m_is_rewinding = false;
|
||||
} // rewindTo
|
||||
|
@ -23,10 +23,11 @@
|
||||
/** Constructor. It will add this object to the list of all rewindable
|
||||
* objects in the rewind manager.
|
||||
*/
|
||||
Rewinder::Rewinder(bool can_be_destroyed)
|
||||
Rewinder::Rewinder(bool can_be_destroyed, bool auto_add)
|
||||
{
|
||||
m_can_be_destroyed = can_be_destroyed;
|
||||
RewindManager::get()->addRewinder(this);
|
||||
m_can_be_destroyed = can_be_destroyed;
|
||||
if (auto_add)
|
||||
add();
|
||||
} // Rewinder
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
@ -35,3 +36,9 @@ Rewinder::Rewinder(bool can_be_destroyed)
|
||||
Rewinder::~Rewinder()
|
||||
{
|
||||
} // ~Rewinder
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void Rewinder::add()
|
||||
{
|
||||
RewindManager::get()->addRewinder(this);
|
||||
} // Rewinder
|
||||
|
@ -25,6 +25,8 @@ class BareNetworkString;
|
||||
|
||||
class Rewinder
|
||||
{
|
||||
protected:
|
||||
void add();
|
||||
private:
|
||||
/** True if this object can be destroyed, i.e. if this object is a 'stand
|
||||
* alone' (i.e. not used in inheritance). If the object is used in
|
||||
@ -34,7 +36,7 @@ private:
|
||||
bool m_can_be_destroyed;
|
||||
|
||||
public:
|
||||
Rewinder(bool can_be_destroyed);
|
||||
Rewinder(bool can_be_destroyed, bool auto_add = true);
|
||||
virtual ~Rewinder();
|
||||
|
||||
/** Called before a rewind. Is used to save the previous position of an
|
||||
@ -58,30 +60,30 @@ public:
|
||||
*/
|
||||
virtual void undoEvent(BareNetworkString *buffer) = 0;
|
||||
|
||||
/** Called when an event needs to be replayed. This is called during
|
||||
/** Called when an event needs to be replayed. This is called during
|
||||
* rewind, i.e. when going forward in time again.
|
||||
*/
|
||||
virtual void rewindToEvent(BareNetworkString *buffer) = 0;
|
||||
|
||||
/** Called when a state needs to be replayed. This is called during
|
||||
/** Called when a state needs to be replayed. This is called during
|
||||
* rewind, i.e. when going forward in time again, and only for confirmed
|
||||
* states.
|
||||
*/
|
||||
virtual void restoreState(BareNetworkString *buffer, int count) = 0;
|
||||
|
||||
/** Undo the effects of the given state, but do not rewind to that
|
||||
* state (which is done by rewindTo). This is called while going
|
||||
* backwards for rewinding - all stored events will get an 'undo' call.
|
||||
*/
|
||||
virtual void undoState(BareNetworkString *buffer) = 0;
|
||||
/** Undo the effects of the given state, but do not rewind to that
|
||||
* state (which is done by rewindTo). This is called while going
|
||||
* backwards for rewinding - all stored events will get an 'undo' call.
|
||||
*/
|
||||
virtual void undoState(BareNetworkString *buffer) = 0;
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
/** Nothing to do here. */
|
||||
virtual void reset() {};
|
||||
// -------------------------------------------------------------------------
|
||||
/** True if this rewinder can be destroyed. Karts can not be destroyed,
|
||||
* cakes can. This is used by the RewindManager in reset. */
|
||||
bool canBeDestroyed() const { return m_can_be_destroyed; }
|
||||
// -------------------------------------------------------------------------
|
||||
/** Nothing to do here. */
|
||||
virtual void reset() {}
|
||||
// -------------------------------------------------------------------------
|
||||
/** True if this rewinder can be destroyed. Karts can not be destroyed,
|
||||
* cakes can. This is used by the RewindManager in reset. */
|
||||
bool canBeDestroyed() const { return m_can_be_destroyed; }
|
||||
// -------------------------------------------------------------------------
|
||||
virtual std::function<void()> getLocalStateRestoreFunction()
|
||||
{ return nullptr; }
|
||||
|
@ -28,6 +28,7 @@
|
||||
#include "io/xml_node.hpp"
|
||||
#include "physics/physics.hpp"
|
||||
#include "physics/triangle_mesh.hpp"
|
||||
#include "network/network_string.hpp"
|
||||
#include "tracks/track.hpp"
|
||||
#include "tracks/track_object.hpp"
|
||||
#include "utils/constants.hpp"
|
||||
@ -134,6 +135,7 @@ PhysicalObject* PhysicalObject::fromXML(bool is_dynamic,
|
||||
PhysicalObject::PhysicalObject(bool is_dynamic,
|
||||
const PhysicalObject::Settings& settings,
|
||||
TrackObject* object)
|
||||
: Rewinder(false/*can_be_destroyed*/, false/*auto_add*/)
|
||||
{
|
||||
m_shape = NULL;
|
||||
m_body = NULL;
|
||||
@ -166,6 +168,7 @@ PhysicalObject::PhysicalObject(bool is_dynamic,
|
||||
m_current_transform.setOrigin(Vec3());
|
||||
m_current_transform.setRotation(
|
||||
btQuaternion(0.0f, 0.0f, 0.0f, 1.0f));
|
||||
m_previous_transform = m_current_transform;
|
||||
|
||||
m_body_added = false;
|
||||
|
||||
@ -773,5 +776,53 @@ void PhysicalObject::hit(const Material *m, const Vec3 &normal)
|
||||
} // hit
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
/* EOF */
|
||||
void PhysicalObject::addForRewind()
|
||||
{
|
||||
Rewinder::add();
|
||||
} // addForRewind
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void PhysicalObject::saveTransform()
|
||||
{
|
||||
} // saveTransform
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void PhysicalObject::computeError()
|
||||
{
|
||||
} // computeError
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
BareNetworkString* PhysicalObject::saveState()
|
||||
{
|
||||
BareNetworkString *buffer = new BareNetworkString();
|
||||
buffer->add(m_current_transform.getOrigin());
|
||||
buffer->add(m_current_transform.getRotation());
|
||||
buffer->add(m_body->getLinearVelocity());
|
||||
buffer->add(m_body->getAngularVelocity());
|
||||
return buffer;
|
||||
} // saveState
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void PhysicalObject::restoreState(BareNetworkString *buffer, int count)
|
||||
{
|
||||
btTransform t;
|
||||
t.setOrigin(buffer->getVec3());
|
||||
t.setRotation(buffer->getQuat());
|
||||
m_body->setLinearVelocity(buffer->getVec3());
|
||||
m_body->setAngularVelocity(buffer->getVec3());
|
||||
m_body->proceedToTransform(t);
|
||||
} // restoreState
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
std::function<void()> PhysicalObject::getLocalStateRestoreFunction()
|
||||
{
|
||||
btTransform t = m_current_transform;
|
||||
Vec3 lv = m_body->getLinearVelocity();
|
||||
Vec3 av = m_body->getAngularVelocity();
|
||||
return [t, lv, av, this]()
|
||||
{
|
||||
m_body->setLinearVelocity(lv);
|
||||
m_body->setAngularVelocity(av);
|
||||
m_body->proceedToTransform(t);
|
||||
};
|
||||
} // getLocalStateRestoreFunction
|
||||
|
@ -23,6 +23,7 @@
|
||||
|
||||
#include "btBulletDynamicsCommon.h"
|
||||
|
||||
#include "network/rewinder.hpp"
|
||||
#include "physics/user_pointer.hpp"
|
||||
#include "utils/vec3.hpp"
|
||||
#include "utils/leak_check.hpp"
|
||||
@ -35,7 +36,7 @@ class XMLNode;
|
||||
/**
|
||||
* \ingroup physics
|
||||
*/
|
||||
class PhysicalObject
|
||||
class PhysicalObject : public Rewinder
|
||||
{
|
||||
public:
|
||||
/** The supported collision shapes. */
|
||||
@ -141,6 +142,8 @@ private:
|
||||
* world transform. */
|
||||
btTransform m_current_transform;
|
||||
|
||||
btTransform m_previous_transform;
|
||||
|
||||
/** The mesh might not have the same center as bullet does. This
|
||||
* offset is used to offset the location of the graphical mesh
|
||||
* so that the graphics are aligned with the bullet collision shape. */
|
||||
@ -269,6 +272,15 @@ public:
|
||||
/** @} */
|
||||
/** @} */
|
||||
|
||||
void addForRewind();
|
||||
virtual void saveTransform();
|
||||
virtual void computeError();
|
||||
virtual BareNetworkString* saveState();
|
||||
virtual void undoEvent(BareNetworkString *buffer) {}
|
||||
virtual void rewindToEvent(BareNetworkString *buffer) {}
|
||||
virtual void restoreState(BareNetworkString *buffer, int count);
|
||||
virtual void undoState(BareNetworkString *buffer) {}
|
||||
virtual std::function<void()> getLocalStateRestoreFunction();
|
||||
LEAK_CHECK()
|
||||
}; // PhysicalObject
|
||||
|
||||
|
@ -69,8 +69,14 @@ void TrackObjectManager::init()
|
||||
for_var_in(TrackObject*, curr, m_all_objects)
|
||||
{
|
||||
curr->onWorldReady();
|
||||
|
||||
// onWorldReady will hide some track objects using scripting
|
||||
if (curr->isEnabled() && curr->getPhysicalObject() &&
|
||||
curr->getPhysicalObject()->isDynamic())
|
||||
curr->getPhysicalObject()->addForRewind();
|
||||
}
|
||||
} // reset
|
||||
} // init
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
/** Initialises all track objects.
|
||||
*/
|
||||
@ -82,6 +88,7 @@ void TrackObjectManager::reset()
|
||||
curr->resetEnabled();
|
||||
}
|
||||
} // reset
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
/** returns a reference to the track object
|
||||
* with a particular ID
|
||||
@ -238,25 +245,3 @@ void TrackObjectManager::removeObject(TrackObject* obj)
|
||||
m_all_objects.remove(obj);
|
||||
delete obj;
|
||||
} // removeObject
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void TrackObjectManager::removeForRewind()
|
||||
{
|
||||
for (TrackObject* curr : m_all_objects)
|
||||
{
|
||||
if (curr->isEnabled() && curr->getPhysicalObject() &&
|
||||
curr->getPhysicalObject()->isDynamic())
|
||||
curr->getPhysicalObject()->removeBody();
|
||||
}
|
||||
} // removeForRewind
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void TrackObjectManager::addForRewind()
|
||||
{
|
||||
for (TrackObject* curr : m_all_objects)
|
||||
{
|
||||
if (curr->isEnabled() && curr->getPhysicalObject() &&
|
||||
curr->getPhysicalObject()->isDynamic())
|
||||
curr->getPhysicalObject()->addBody();
|
||||
}
|
||||
} // addForRewind
|
||||
|
@ -76,8 +76,6 @@ public:
|
||||
|
||||
PtrVector<TrackObject>& getObjects() { return m_all_objects; }
|
||||
const PtrVector<TrackObject>& getObjects() const { return m_all_objects; }
|
||||
void removeForRewind();
|
||||
void addForRewind();
|
||||
|
||||
}; // class TrackObjectManager
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user