Some Scripting Help
by Barry "Yossarian" Whitley · in Torque Game Builder · 04/20/2005 (9:24 am) · 15 replies
Been banging my head on this for a while, figured I'd see if someone could look at it real quick and probably instantly recognize why this stupid bit isn't working...
What *should* be happening is that when the S key is held down, the player slows and then starts reversing up to the maximum reverse speed. The scheduling and timestep are there to give a sense of acceleration/decceleration. This works perfectly fine when going forward, and acheives the desired effect nicely.
Unless I'm thinking wrong on this, I really need to have the reverse act as an accelration force, stopping and then reversing will create a stutter and ruin any smooth transitions between forward and reverse.
Unfortunately, what the code *is* doing is is hanging up at -0.25 speed, setting itself to 0, then -0.25, and on and on and on... it never wants to reach the max of -4.
Any ideas?
$Acceleration = 0.25;
$SpeedTimeStep = 50;
$maxSpeedBackwards = -4;
function playerDownEvent()
{
if($playerDownSwitch != 1)
return;
%a = mAbs($player.getLinearVelocityX());
%a2 = mPow(%a, 2);
%b = mAbs($player.getLinearVelocityY());
%b2 = mPow(%b, 2);
%ab = %a2 + %b2;
%c = mSqrt(%ab);
%newSpeedR = %c - $Acceleration;
if(%newSpeedR < $maxSpeedBackwards)
%newSpeedR = $maxSpeedBackwards;
$player.setLinearVelocityPolar( $player.getRotation(), %newSpeedR );
echo(%newSpeedR);
schedule($SpeedTimeStep, 0, "playerDownEvent");
}What *should* be happening is that when the S key is held down, the player slows and then starts reversing up to the maximum reverse speed. The scheduling and timestep are there to give a sense of acceleration/decceleration. This works perfectly fine when going forward, and acheives the desired effect nicely.
Unless I'm thinking wrong on this, I really need to have the reverse act as an accelration force, stopping and then reversing will create a stutter and ruin any smooth transitions between forward and reverse.
Unfortunately, what the code *is* doing is is hanging up at -0.25 speed, setting itself to 0, then -0.25, and on and on and on... it never wants to reach the max of -4.
Any ideas?
#2
04/20/2005 (10:05 am)
Try$Acceleration = 0.25;
$SpeedTimeStep = 50;
$maxSpeedBackwards = 4;
function playerDownEvent()
{
if($playerDownSwitch != 1)
return;
%a = mAbs($player.getLinearVelocityX());
%a2 = mPow(%a, 2);
%b = mAbs($player.getLinearVelocityY());
%b2 = mPow(%b, 2);
%ab = %a2 + %b2;
%c = mSqrt(%ab);
%newSpeedR = %c + $Acceleration;
if(%newSpeedR < $maxSpeedBackwards)
%newSpeedR = $maxSpeedBackwards;
%playerRot = $player.getRotation();
if(%playerRot > 0)
{
%rot = %playerRot - 180;
} else
{
%rot = %playerRot + 180;
}
$player.setLinearVelocityPolar( %rot, %newSpeedR );
echo(%newSpeedR);
schedule($SpeedTimeStep, 0, "playerDownEvent");
}
#3
When going reverse once you pass speed 0, your first speed is -0.25, second time through the loop, your abs() functions convert that to +0.25, so you subtract your deceleration value 0.25... and you get 0.
04/20/2005 (10:07 am)
Well... you're using an abs() on the x/y values.When going reverse once you pass speed 0, your first speed is -0.25, second time through the loop, your abs() functions convert that to +0.25, so you subtract your deceleration value 0.25... and you get 0.
#4
I'd do something like this:
NOTE: if you have an acceleration function you would need to make simliar changes.
edit: Had my Above 0 and Below 0 accelerations swapped
04/20/2005 (10:09 am)
Matt - You're function will add to the speed regardless of the direction the player is travelingI'd do something like this:
$Acceleration = 0.25;
$SpeedTimeStep = 50;
$maxSpeedBackwards = -4;
function playerDownEvent()
{
if($playerDownSwitch != 1)
return;
%a = mAbs($player.getLinearVelocityX());
%a2 = mPow(%a, 2);
%b = mAbs($player.getLinearVelocityY());
%b2 = mPow(%b, 2);
%ab = %a2 + %b2;
%c = mSqrt(%ab);
if($player.reverse)
{
%newSpeedR = 0 - (%c + $Acceleration);
}
else
{
%newSpeedR = %c - $Acceleration;
}
if(%newSpeedR < 0)
{
$player.reverse = true;
}
else if (%newSpeedR >=0)
{
$player.reverse = false;
}
if(%newSpeedR < $maxSpeedBackwards)
%newSpeedR = $maxSpeedBackwards;
$player.setLinearVelocityPolar( $player.getRotation(), %newSpeedR );
echo(%newSpeedR);
schedule($SpeedTimeStep, 0, "playerDownEvent");
}NOTE: if you have an acceleration function you would need to make simliar changes.
edit: Had my Above 0 and Below 0 accelerations swapped
#5
your right Harold, saw the problem and was applying it wrongly
04/20/2005 (10:13 am)
$Acceleration = 0.25;
$SpeedTimeStep = 50;
$maxSpeedBackwards = 4;
function playerDownEvent()
{
if($playerDownSwitch != 1)
return;
%a = mAbs($player.getLinearVelocityX());
%a2 = mPow(%a, 2);
%b = mAbs($player.getLinearVelocityY());
%b2 = mPow(%b, 2);
%ab = %a2 + %b2;
%c = mSqrt(%ab);
%newSpeedR = %c + $Acceleration;
if(%newSpeedR < $maxSpeedBackwards)
%newSpeedR = $maxSpeedBackwards;
%newSpeedR = -(%newSpeedR);
$player.setLinearVelocityPolar( $player.getRotation(), %newSpeedR );
echo(%newSpeedR);
schedule($SpeedTimeStep, 0, "playerDownEvent");
}your right Harold, saw the problem and was applying it wrongly
#6
04/20/2005 (10:17 am)
Your last one will switch to reverse on the first tick. So traveling at 4... the next tick you'll be a -3.75.
#7
04/20/2005 (10:24 am)
Your right... right now at work so just posting different progress steps... lol not quite working yet :)
#8
04/20/2005 (10:26 am)
Though the abs doesn't matter since he squares them anyways
#9
04/20/2005 (10:28 am)
Any suggestions ? at the moment my mind is stuck lol
#10
About the only way I can think of is to flag the player as moving in reverse the first time it dips below 0 (the -0.25 in the sample code) then modify the code path based on the flag.
04/20/2005 (10:34 am)
Hehe.. Look at my code posting just above your last one.About the only way I can think of is to flag the player as moving in reverse the first time it dips below 0 (the -0.25 in the sample code) then modify the code path based on the flag.
#11
though Harold's idea of flaggin reverse is probably more accurate...
04/20/2005 (10:38 am)
The best way I can think of (and this is just me so might not be the best way) is keeping track of the players velocity yourselfthough Harold's idea of flaggin reverse is probably more accurate...
$Acceleration = 0.25;
$SpeedTimeStep = 50;
$maxSpeedBackwards = -4;
$playerVelocity = 0;
function playerDownEvent()
{
if($playerDownSwitch != 1)
return;
$playerVelocity -= $Acceleration;
if($playerVelocity< $maxSpeedBackwards)
$playerVelocity = $maxSpeedBackwards;
$player.setLinearVelocityPolar( $player.getRotation(), $playerVelocity);
echo($playerVelocity);
schedule($SpeedTimeStep, 0, "playerDownEvent");
}
#12
04/20/2005 (10:39 am)
Rofl I'm blind Harold... didn't think of flagging reverse :)
#13
04/20/2005 (10:50 am)
Well, I was going to mention setting $maxSpeedBackwards as a negative value to begin with, but was beaten to the punch :-)
#14
only reason I did a posotive 4 is because down is really posotive, but I was just thinking in reference to an object facing up, not polar velocities lol (I was a little slow at first)
04/20/2005 (10:56 am)
Yeah, its tricky since the velocity formula will always return a posotive velocity... not in reference to where the object is facing (since the values are squared and it loses sense of negative or posotive)... so unless you either flag reverse, keep track of your own velocity, or do some fancy trig+vectors to figure out if the X and Y velocity is neg or pos in reference to the rotationonly reason I did a posotive 4 is because down is really posotive, but I was just thinking in reference to an object facing up, not polar velocities lol (I was a little slow at first)
#15
Just need to add the reverse flags around to the other functions as well. Adding it to the playerUpEvent to set to false gives pretty much what I needed. Although for the sake of making it bulletproof, the stopEvent functions also need some checks as well, as you can get some funky results if you hit keys fast enough that one of the moves fires off before the game call the stop function.
04/20/2005 (10:57 am)
Ty Harold, got it working with a slight modificationfunction playerDownEvent()
{
if($playerDownSwitch != 1)
return;
%a = mAbs($player.getLinearVelocityX());
%a2 = mPow(%a, 2);
%b = mAbs($player.getLinearVelocityY());
%b2 = mPow(%b, 2);
%ab = %a2 + %b2;
%c = mSqrt(%ab);
%newSpeedR = %c - $Acceleration;
if($player.reverse)
{
%newSpeedR = 0 - (%c + $Acceleration);
}
else
{
%newSpeedR = %c - $Acceleration;
}
if(%newSpeedR < 0)
{
$player.reverse = true;
}
else if (%newSpeedR >=0)
{
$player.reverse = false;
}
if(%newSpeedR < $maxSpeedBackwards)
%newSpeedR = $maxSpeedBackwards;
$player.setLinearVelocityPolar( $player.getRotation(), %newSpeedR );
schedule($SpeedTimeStep, 0, "playerDownEvent");
}Just need to add the reverse flags around to the other functions as well. Adding it to the playerUpEvent to set to false gives pretty much what I needed. Although for the sake of making it bulletproof, the stopEvent functions also need some checks as well, as you can get some funky results if you hit keys fast enough that one of the moves fires off before the game call the stop function.
Torque 3D Owner Matthew Langley
Torque