Timer() controlled BALL Physics demo by walaber14th Jan 2004 9:35
|
---|
Summary A simple 2D example of trajectory physics. throw a ball around in a room an watch it bounce off the walls with friction and gravity. timer controlled to ensure performance on a wid Description no media is required. This is basically aimed at beginners who want to see an example of simple gravity, etc. also useful for learning how to make your game run the same speed on different speed systems, using a very simple timer() technique! Code ` This code was downloaded from The Game Creators ` It is reproduced here with full permission ` http://www.thegamecreators.com REMSTART This is a simple BALL physics program... there are a couple progams like this one in the codebase, But this one incorporates the timer() to maintain the same ball speed regardless of system speed, which I think makes it stand out. This program is still pretty simple, it could be adjusted to have the ball bounce off of oddly shaped objects, air friction could be added, etc. If the codes helps you in any way, I'm glad! if you have any questions or comments (especially improvements) e-mail me at tfitzrandolph@yahoo.co.jp thanks, Walaber REMEND sync on : sync rate 0 set display mode 640,480,32 `just some constants to make handling the code easier! #constant Ready = 1 #constant Flying = 2 #constant Resetting = 3 ` OK these types are exactly the same, I separated them solely because I think it's good to keep ` positions ans vectors separate in my head! Type 2DVector x as float y as float ENDTYPE Type 2DPoint x as float y as float ENDTYPE TYPE Object status as byte Pos as 2DPoint Vel as 2DVector ENDTYPE `Initialize the BALL (that circle on the screen) object with its current status, etc. Ball as Object Ball.Pos.x = 30 Ball.Pos.y = 380 Ball.Vel.x = 0 Ball.Vel.y = 0 Ball.status = Ready startangle = -45 startvel = 10 Gravity as 2DVector Gravity.y = 1000 `In This case Gravity has no effect on the X component... you can try changing this value `to create a wind-like effect on the ball! Gravity.x = 0 ` because of my timer() system, the units above (and everywhere else) are UNITS(pixels) PER SECOND! ` percentage of energy retained when the ball bounces (loss of energy due to friction/etc) ` you can try changing this value to see the effects on the ball too. bounceconstant# = 0.80 `just to make sure the first loop has a valid ElapsedInSec# value oldtimer = timer() - 100 ` MAIN LOOP!!!! do ` Calculate the amout of time that has elapsed since the last program loop... Elapsed = (timer() - oldtimer) : ` time elapsed in MILLISECONDS oldtimer = timer() ElapsedInSec# = Elapsed / 1000.0 : ` time elapsed in SECONDS cls ` HANDLE THE BALL.... select Ball.status ` USER IS SETTING THE ANGLE AND VELOCITY OF THE BALL... case Ready startangle = wrapvalue(startangle+(downkey()-upkey())) inc startvel, (rightkey()-leftkey()) `X and Y components of the angle currentx = cos(startangle) * startvel currenty = sin(startangle) * startvel `USER wants to throw the BALL... if returnkey() Ball.Vel.x = currentx * 10 : `this makes the velocity more reasonable (x10) Ball.Vel.y = currenty * 10 Ball.status = Flying start = timer() endif ` Update the screen with the ball, angle indicator, walls, etc circle Ball.Pos.x,Ball.Pos.y,5 line Ball.Pos.x,Ball.Pos.y,Ball.Pos.x+currentx,Ball.Pos.y+currenty line 0,400,639,400 line 0,20,639,20 line 620,20,620,400 line 20,20,20,400 text 10,410,"Angle: "+str$(wrapvalue(360-startangle)) text 10,420,"Velocity: "+str$(startvel) text 10,430,"UP/DOWN to change angle, RIGHT/LEFT to change velocity" text 10,440,"Press RETURN to throw the BALL!!!!" endcase ` BALL is flying through the air, calculate its variables. case Flying inc Ball.Vel.x,Gravity.x * ElapsedInSec# : `subtract gravity inc Ball.Vel.y,Gravity.y * ElapsedInSec# inc Ball.Pos.x,Ball.Vel.x * ElapsedInSec# : `calculate new position inc Ball.Pos.y,Ball.vel.y * ElapsedInSec# ` check for if the ball hits any of the walls... if Ball.Pos.y > 395 Ball.Pos.y = 395 Ball.Vel.y = Ball.Vel.y * ((-1)*bounceconstant#) Ball.Vel.x = Ball.Vel.x * bounceconstant# endif if Ball.Pos.y < 25 Ball.Pos.y = 25 Ball.Vel.y = Ball.Vel.y * ((-1)*bounceconstant#) Ball.Vel.x = Ball.Vel.x * bounceconstant# endif if Ball.Pos.x < 25 Ball.Pos.x = 25 Ball.Vel.x = Ball.Vel.x * ((-1)*bounceconstant#) Ball.Vel.y = Ball.Vel.y * bounceconstant# endif if Ball.Pos.x > 615 Ball.Pos.x = 615 Ball.Vel.x = Ball.Vel.x * ((-1)*bounceconstant#) Ball.Vel.y = Ball.Vel.y * bounceconstant# endif `if the ball is out of energy, then RESET! if Ball.Pos.y = 395.0 if Ball.Vel.y < 0.0 and abs(Ball.Vel.x) < 0.05 then Ball.status = Resetting : finish = timer() endif ` update screen... circle Ball.Pos.x,Ball.Pos.y,5 line 0,400,639,400 line 0,20,639,20 line 620,20,620,400 line 20,20,20,400 text 10,410,"XVel: "+str$(Ball.Vel.x) text 10,420,"YVel: "+str$(Ball.Vel.y) text 10,430,"Elap: "+str$(ElapsedInSec#) endcase ` Ball has died, reset the variables! case Resetting if returnkey() Ball.Pos.x = 30 Ball.Pos.y = 380 Ball.Vel.x = 0 Ball.Vel.y = 0 startangle = -45 startvel = 10 Ball.status = Ready repeat until returnkey()=0 endif circle Ball.Pos.x,Ball.Pos.y,5 line 0,400,639,400 line 0,20,639,20 line 620,20,620,400 line 20,20,20,400 text 10,410,"TimeElapsed: "+str$((finish-start)/1000.0)+" seconds" text 10,420,"PRESS RETURN..." endcase endselect text 300,410,"FPS "+str$(screen fps()) sync loop |