PDA

View Full Version : Detecting KActor Stopped moving



ninjabadger
11-13-2009, 06:11 PM
Hi,

I'm programming a golf game in UDK and I'm having troubles trying to find out how to detect when the ball has stopped moving, or is moving at very low speed.

I've created a ball class that is inherited from KActor, but I can't see any functions that will do this for me.

Is there something I can check with a Tick function, but I suspect that would be expensive...

Steve Polge
11-13-2009, 06:25 PM
Ticking a single actor in UnrealScript will be negligibly expensive.

If you want to check whether a physics object has stopped moving, you can implement the actor event OnSleepRBPhysics(). However, you may not get the results you want - in some cases the ball may take a long time to go to sleep, even though it is hardly moving. I'd recommend testing the velocity of the ball in a tick or timer function instead.

If you really need to optimize the check, I'd suggest using a timer rather than a tick function, and setting the timer interval on each check based on the current velocity and an estimate of when it might come to rest.

ninjabadger
11-13-2009, 06:28 PM
Ticking a single actor in UnrealScript will be negligibly expensive.

If you want to check whether a physics object has stopped moving, you can implement the actor event OnSleepRBPhysics(). However, you may not get the results you want - in some cases the ball may take a long time to go to sleep, even though it is hardly moving. I'd recommend testing the velocity of the ball in a tick or timer function instead.

If you really need to optimize the check, I'd suggest using a timer rather than a tick function, and setting the timer interval on each check based on the current velocity and an estimate of when it might come to rest.

Awesome - thanks muchly :)

ninjabadger
11-13-2009, 06:37 PM
Anyone know if there is a built in function for the magnitude of a vector? Would save a little bit of maths. :)

ninjabadger
11-13-2009, 06:52 PM
Ah - is VSize the magnitude?

I'm testing for VSize of velocity being = 0 and it seems to be instantaneous - i.e. the ball now won't move.

simulated function Tick(float DeltaTime)
{
if (bShotTaken)
{
if (VSize(Velocity) == 0)
{
Gotostate('AtRest');
}
}
}

Then AtRest does the following:

state AtRest
{
Begin:
StaticMeshComponent.SetRBLinearVelocity( Vect(0,0,0) );
StaticMeshComponent.SetRBAngularVelocity( Vect(0,0,0) );
bShotTaken=false;
}


Am I doing something wrong?

TheSpaceMan
11-13-2009, 06:58 PM
Isn't it possible that your linear and angular velocities are applied on the first frame, it runs a tick and haven't appliced the actuall velocity yet (depends on Tick vs. Physics update order), the tick runs and since the Velocity is Zero, it will go into the rest state and remove the velocities.
Maybe wait a while before you do the check, or a number for updates etc.

ninjabadger
11-13-2009, 07:01 PM
Isn't it possible that your linear and angular velocities are applied on the first frame, it runs a tick and haven't appliced the actuall velocity yet (depends on Tick vs. Physics update order), the tick runs and since the Velocity is Zero, it will go into the rest state and remove the velocities.
Maybe wait a while before you do the check, or a number for updates etc.

Yeah - that's why I added the takenShot bool to make sure it was actually moving first. Maybe I should just try setting the bool a little later.

ninjabadger
11-13-2009, 07:02 PM
Heh - putting a small sleep in there worked :)

Solid Snake
11-13-2009, 07:26 PM
You could also use VSizeSq which is the same as VSize but without doing a square root. May not matter in performance in the grand scheme of things, but usually if you can avoid a square root, I'd recommend it.

Blade[UG]
11-13-2009, 08:26 PM
You could also avoid checking it until after it's come into contact with something.

ninjabadger
11-14-2009, 03:16 AM
;26977133']You could also avoid checking it until after it's come into contact with something.

Yeah - very good point - will try doing that