2D Motion and Vectors
Hi All,
I am really having a difficult time learning about motion in 2D (or 3D for that matter).
I found a great site that had a 2D Vector Class to use, but my problem is that I don't understand how to use it.
I understand that I would need my object (a car for example) to have a vector for its current location, it would also need a velocity variable with an angle and magnitude to calculate the next point where the car will end up.
I don't quite understand how to incorporate velocity and angles into the mix. I am not really a great mathematician so this is really hard for me to understand.
Can someone point me in the right direction on how to work with vectors, angles and motion (doesn't even have to be related to programming).
I want to make a small car game, but my lack of maths skills is really holding me back. Any help is greatly appreciated
Thanks
I think you'll need to look into Sine and Cosine, for angular movement. If you're using C++, you can include math.h for sin() and cos(). For example, to move at an angle(in degrees) at your current speed, you would do this:
Degrees_to_radians would be something like this(C++):
If you'd like to understand HOW these work, you could look up some trigonometry lessons on google or something.
x+=cos(degrees_to_radians(angle))*speed;y-=sin(degrees_to_radians(angle))*speed;
Degrees_to_radians would be something like this(C++):
float degrees_to_radians(float number){ return number/(180/M_PI); }
If you'd like to understand HOW these work, you could look up some trigonometry lessons on google or something.
Thanks dude, that was really helpfull. I will try it out tonight although I am not sure if the results of those equations will map to the screen coordinate system. I might have to look into so trig stuff on the net. Thanks again.
You're welcome :D
If you're worried about it working with the screen coords, I wrote that assuming 0,0 was in the top-left corner of your screen. If it's in the bottom-left, then just change the "y-=stuff" to "y+=stuff". Good luck with your game!
If you're worried about it working with the screen coords, I wrote that assuming 0,0 was in the top-left corner of your screen. If it's in the bottom-left, then just change the "y-=stuff" to "y+=stuff". Good luck with your game!
I will plug your code into my game so far and see how it goes. Its basically just me moving a square around the screen as though it was a Car. Its all SDL based. Just sort of starting off.
Thanks again. I will update on how it goes.
Thanks again. I will update on how it goes.
Hi again,
I put that code into my game and it works... sort of. I think it might be in my implamentation.
Here is my car object (with some stuff removed for brevity)
The direction can be any value between 0 and 359. Perhaps this is the point that is going wrong. I am not too sure. I currently only have the code compiled on Linux, but I can probably make a windows executable if you want to look at it (unless you are on Linux to begin with).
Thanks so much for the help so far. It feel really good to have it working, even if it is behaving improperly.
[Edited by - timbobsteve on August 11, 2006 2:45:49 AM]
I put that code into my game and it works... sort of. I think it might be in my implamentation.
Here is my car object (with some stuff removed for brevity)
class Car{ private: SDL_Surface* m_Sprite int x,y; // Coo-ords (x,y) int direction,speed; // Direction = angle 0-359 **Is that right?** public: //... void Accelerate() { speed = speed + 1; }; void Decelerate() { speed = speed - 1; }; void TurnLeft() { direction = direction - 1; if(direction < 0) direction = 359; } void TurnRight() { direction = direction + 1; if(direction > 359) direction = 0; } void Update() { x += cos(degrees_to_rad(direction))*speed; //... // Check Leave Screen here & adjust //... y += sin(degrees_to_rad(direction))*speed; //... // Check Leave Screen here & adjust //... }};
The direction can be any value between 0 and 359. Perhaps this is the point that is going wrong. I am not too sure. I currently only have the code compiled on Linux, but I can probably make a windows executable if you want to look at it (unless you are on Linux to begin with).
Thanks so much for the help so far. It feel really good to have it working, even if it is behaving improperly.
[Edited by - timbobsteve on August 11, 2006 2:45:49 AM]
Your treatment of sin and cos is ok, assuming that (a) you understand your coordinate system (In mathematics, we let an angle of 0 be to the right, and increasing value turns counter-clockwise; however, in math we draw positive y going up, but most screen-position APIs treat positive y as going downwards, so you sometimes have to use -sin where you'd expect to use sin, or do the mapping elsewhere), and (b) your degrees_to_rad() function works.
The bug here is that in Update(), because the direction and speed represent *velocity* of the car, but x and y represent *position*, you want to *add* the cos/sin components to the x and y, rather than setting them.
That said:
- You need a semicolon after the m_Sprite declaration (since you have something compiling, I assume that's just a typo in shortening things for board posting).
- You can use the 'immediate' mathematical operators in order to avoid typing redundant things. It's also more expressive: in real life, you wouldn't command "set x to be x plus 1", but instead "add 1 to x". In C++, this translates as "x += 1". Similarly, there exist -=, *=, /=, and most if not all other combinations you would expect (I don't know what you'd expect ;) ).
For the special case of adding or subtracting 1, you can also use "x++" or "++x", but I usually (teach to) use these only in specific circumstances where it's idiomatic C++ to do so.
- To make values "loop around", you can try making use of the modulus (%) operator. It returns the remainder of a division.
- Some real-world APIs use, instead of degrees, "256ths of a circle". That way, you don't have to write any looping around explicitly: you store the value in a signed char, and the overflow behaviour takes care of things automatically (if the value hits 256, the 256-bit is discarded since it overflows the type, and you get 0 again). This is not terribly intuitive, though, and smells of premature optimization - but it's worth exposure to different techniques so you can get an idea of how these things work.
- By the way, good job with your class design so far, from what I can see. You have abstracted things properly and made functions that do real work; a concept that ought to be obvious, but with which many people inexplicably have huge amounts of trouble. With abstractions like 'accelerate()', you have a convenient place to add code as you develop your "physics model" to make the car behaviour more accurate.
The bug here is that in Update(), because the direction and speed represent *velocity* of the car, but x and y represent *position*, you want to *add* the cos/sin components to the x and y, rather than setting them.
That said:
- You need a semicolon after the m_Sprite declaration (since you have something compiling, I assume that's just a typo in shortening things for board posting).
- You can use the 'immediate' mathematical operators in order to avoid typing redundant things. It's also more expressive: in real life, you wouldn't command "set x to be x plus 1", but instead "add 1 to x". In C++, this translates as "x += 1". Similarly, there exist -=, *=, /=, and most if not all other combinations you would expect (I don't know what you'd expect ;) ).
For the special case of adding or subtracting 1, you can also use "x++" or "++x", but I usually (teach to) use these only in specific circumstances where it's idiomatic C++ to do so.
- To make values "loop around", you can try making use of the modulus (%) operator. It returns the remainder of a division.
- Some real-world APIs use, instead of degrees, "256ths of a circle". That way, you don't have to write any looping around explicitly: you store the value in a signed char, and the overflow behaviour takes care of things automatically (if the value hits 256, the 256-bit is discarded since it overflows the type, and you get 0 again). This is not terribly intuitive, though, and smells of premature optimization - but it's worth exposure to different techniques so you can get an idea of how these things work.
- By the way, good job with your class design so far, from what I can see. You have abstracted things properly and made functions that do real work; a concept that ought to be obvious, but with which many people inexplicably have huge amounts of trouble. With abstractions like 'accelerate()', you have a convenient place to add code as you develop your "physics model" to make the car behaviour more accurate.
Thanks for the reply Zahlman. I think you are right when you talk about my current implimentation of the coordinate system.
I will try some of the stuff you said. I know what you mean about making code shorter (like using ++x instead of x = x + 1), but you will find that these forums don't display "++x" properley, instead of:
"++x"
it displays
" x" (no pluses)
Its only when you put it in the "{source}" brackets for formating that it doesn't display. That is the only reason why I took the time to type it all out. I will mostly take the shorter option ( "++" or "+=" etc ) if possible.
I will try playing with the coordinates system and how I change the value of x and y. I will get back to you later.
Thanks again.
I will try some of the stuff you said. I know what you mean about making code shorter (like using ++x instead of x = x + 1), but you will find that these forums don't display "++x" properley, instead of:
"++x"
it displays
" x" (no pluses)
Its only when you put it in the "{source}" brackets for formating that it doesn't display. That is the only reason why I took the time to type it all out. I will mostly take the shorter option ( "++" or "+=" etc ) if possible.
I will try playing with the coordinates system and how I change the value of x and y. I will get back to you later.
Thanks again.
Quote:Original post by timbobsteve
Thanks for the reply Zahlman. I think you are right when you talk about my current implimentation of the coordinate system.
I will try some of the stuff you said. I know what you mean about making code shorter (like using ++x instead of x = x + 1), but you will find that these forums don't display "++x" properley, instead of:
"++x"
it displays
" x" (no pluses)
++worksforme;
For some wicked reason, the preview doesn't show plus symbols. They will, however, be visible in the actual reply when you submit it.
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement