Creating a simple, networked, moving object that doesn't jitter
by Aloshi · in Torque 3D Professional · 06/05/2011 (6:41 pm) · 2 replies
So, I've been trying to create a relatively simple class based on StaticShape, except that it has a velocity. It's not affected by gravity, nor does it collide with anything. I've gotten it almost working; the object spawns correctly and moves smoothly most of the time, but not all of the time; occasionally, the object will "jitter." I think I'm also may be networking it incorrectly.
I've been having trouble tracking down exactly what the problem is; it seems partially latency dependent and partially framerate dependent. I've been using client.setSimulatedNetParams(0, 300) to test latency. I get no jitter at 60fps (vsync turned on), both with and without simulated net params. At lower framerates (30, 45), I get jitter, again both with and without simulated net params. At framerates over 60 (200 to 500), I get no jitter without simulated net params, but jitter with simulated net params at what seems like certain framerates (it'll jitter, I'll look away from the terrain to get a higher framerate, then it'll stop for a bit, then continue).
I pieced together what I could from Player.cpp and some other resources, and it's very possible that I implemented the calculation of the new position (in my processTick), interpolation, and/or networking, wrong...hopefully someone who knows what they're doing can help me out here? If there's another thread or resource on this topic, could someone link me to it?
My packUpdate:
My unpackUpdate:
My processTick:
And my interpolateTick:
(oh, and ShipObject::setTransform just calls Parent::setTransform and does setMaskBits(PositionMask), and Parent is just StaticShape; I probably used Parent more than I needed to, as I'm not experienced with C++)
And here's a video of what I mean by jitter (taken at 45fps, no simulated latency): http://youtu.be/U_PE2HAldVM
I've been having trouble tracking down exactly what the problem is; it seems partially latency dependent and partially framerate dependent. I've been using client.setSimulatedNetParams(0, 300) to test latency. I get no jitter at 60fps (vsync turned on), both with and without simulated net params. At lower framerates (30, 45), I get jitter, again both with and without simulated net params. At framerates over 60 (200 to 500), I get no jitter without simulated net params, but jitter with simulated net params at what seems like certain framerates (it'll jitter, I'll look away from the terrain to get a higher framerate, then it'll stop for a bit, then continue).
I pieced together what I could from Player.cpp and some other resources, and it's very possible that I implemented the calculation of the new position (in my processTick), interpolation, and/or networking, wrong...hopefully someone who knows what they're doing can help me out here? If there's another thread or resource on this topic, could someone link me to it?
My packUpdate:
U32 ShipObject::packUpdate(NetConnection *con, U32 mask, BitStream *stream)
{
U32 retMask = ShapeBase::packUpdate(con, mask, stream);
//Transform
if (stream->writeFlag(mask & PositionMask))
{
mathWrite(*stream,mObjToWorld);
}
//Scale
if(stream->writeFlag(mask & ExtendedInfoMask))
{
mathWrite(*stream, mObjScale);
}
//Velocity
if(stream->writeFlag(mask & VelocityMask))
{
mathWrite(*stream, mVelocity);
}
return retMask;
}My unpackUpdate:
void ShipObject::unpackUpdate(NetConnection *con, BitStream *stream)
{
ShapeBase::unpackUpdate(con, stream);
//Transform
if (stream->readFlag())
{
MatrixF mat;
mathRead(*stream,&mat);
setTransform(mat);
}
//Scale
if(stream->readFlag())
{
VectorF scale;
mathRead(*stream, &scale);
setScale(scale);
}
//Velocity
if(stream->readFlag())
{
mathRead(*stream, &mVelocity);
}
}My processTick:
void ShipObject::processTick(const Move* move)
{
Parent::processTick(move);
MatrixF mat = Parent::getTransform();
mat.setPosition(mat.getPosition() + (mVelocity * TickSec)); //Velocity * (32 / 1000)
//Delta is just a struct used to store some variables for interpolation
delta.DeltaBase = mat.getPosition();
delta.BackDelta = mat.getPosition() - Parent::getPosition();
setTransform(mat);
}And my interpolateTick:
void ShipObject::interpolateTick(F32 dt)
{
Parent::interpolateTick(dt);
MatrixF startmat = Parent::getTransform();
MatrixF endmat = Parent::getTransform();
endmat.setPosition(delta.DeltaBase - (delta.BackDelta * dt));
Parent::setRenderTransform(endmat);
}(oh, and ShipObject::setTransform just calls Parent::setTransform and does setMaskBits(PositionMask), and Parent is just StaticShape; I probably used Parent more than I needed to, as I'm not experienced with C++)
And here's a video of what I mean by jitter (taken at 45fps, no simulated latency): http://youtu.be/U_PE2HAldVM
#2
06/08/2011 (8:28 pm)
This sounds like a warping problem. Warping (I believe) is a way that torque does networked movement where the client extrapolates from what position and velocity information it has, and updates this information when it gets a new server packet. You can see this in action in, for example, item.cpp around line 1035.
Torque 3D Owner Aloshi