0
\$\begingroup\$

I need some help with math in a 2d environment. I have a joystick that controls the acceleration vetor for the player figure.

Its suppose to look like the ground is slippery which makes the figure turn slowly and accelerate and decelerate slowly.

Now, I can do this without any problem if I remove the maximum speed, but Im having problem when using a speed cap.

This is my calculation:

func move() {
    if acceleration == CGPointZero && currentSpeed != 0 {
        direction *= 0.95
    }
    else {
        if self.currentSpeed > maxSpeed {
            // This is almost working, just a little buggy, please help here with quality mathamatics :)

            let angle = CGPointZero.angleToPoint(direction) // In Radians
            direction = CGPoint(cos(angle), sin(angle)) * maxSpeed
        }
        else {
            direction += acceleration
        }
    }

    self.center += direction
}

move() is getting called by a timer running at 32 fps. acceleration is a Vector pointing to the direction the user wants his figure to go. currentSpeed is calculated using Pythagorean theorem. direction is acceleration * speed. maxSpeed is a number. self.center is the centerpoint of the figure.

\$\endgroup\$
  • 1
    \$\begingroup\$ What actually happens with the current code? Hard to look for a problem without knowing the problem. \$\endgroup\$ – Chaosed0 Mar 16 '15 at 15:50
  • \$\begingroup\$ When steering while moving at max speed it isnt smooth, its like the calculation lost some decimals. \$\endgroup\$ – user172650 Mar 16 '15 at 16:09
  • \$\begingroup\$ And sometimes it doesnt steer at all. \$\endgroup\$ – user172650 Mar 16 '15 at 16:10
  • 1
    \$\begingroup\$ Have you tried debugging the code on your own? Set a breakpoint and see what happens. At which point does it deviate from your expectations? (Also, what programming language is this?) \$\endgroup\$ – Anko Mar 16 '15 at 17:05
2
\$\begingroup\$

I don't see any real problems with your implementation here, but I suspect your problem is buried in angleToPoint(). I couldn't find any mention of it in the CGPoint documentation, so I assume it's something you've implemented yourself. Make sure you're using atan2() or equivalent, not just atan().

However, it'd be easier not to use any trigonometry at all:

if self.currentSpeed > maxSpeed {
    direction *= maxSpeed/direction.magnitude();
}

This scales direction down to maxSpeed while keeping the direction of the vector the same.


I'd suggest renaming direction to velocity - not only is that what it is called canonically, but also direction doesn't just contain the direction of movement, it's also got the magnitude of that movement.

\$\endgroup\$
  • \$\begingroup\$ Thanks! I did like this: direction *= maxSpeed/currentSpeed And yes, calling it velocity seems like a better name, thanks for some standards too x) \$\endgroup\$ – user172650 Mar 17 '15 at 10:07

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.