Lovely bit of code
I've tweaked it a bit. I thought the only things missing were side walls and the ability to have more than one ball.
Just change the constant on the first line to adjust the number of balls:
#constant qtyBalls 20
// this example should work with AGK V1 and V2
// watch the ball fall and bounce off the pegs
// set a radius for the ball which will also be the radius for the sphere case
radius# = 5
// create a balls and color them
global ball as tball[qtyBalls]
for b = 0 to qtyBalls
ball[b].ID = CreateObjectSphere(radius#*2,16,16)
SetObjectColor(ball[b].ID,255,255,0,255)
SetObjectCollisionMode(ball[b].ID,0) // turn collision off so it doesn't interfere with the sphere cast
resetBall(b)
next b
// create an array of pegs on the xy plane
offset = 10
i = 1
for y = 0 to 5
for x = 0 to 5
inc i
CreateObjectCylinder(i,12,12,24)
SetObjectRotation(i,90,0,0)
SetObjectPosition(i,x*40 + offset,y*40,0)
next x
// this creates a diamond pattern by offseting each row of pegs
offset = offset * -1
next y
lb = CreateObjectBox(12, 250, 12)
SetObjectPosition(lb, -40, 100, 0)
rb = CreateObjectBox(12, 250, 12)
SetObjectPosition(rb, 250, 100, 0)
// save the number of pegs created (will be used later and I can be bothered to work it out in my head)
num_pegs = i-1
// create a directional light (to make the scene look better)
CreateLightDirectional(1,-1,-0.5,1,255,255,255)
// position and orientate the camera
SetCameraPosition(1,100,250,-350)
SetCameraLookAt(1,100,100,0,0)
// set the value for gravity
gravity# = 0.01
// main loop
do
// ball falling loop
for b = 0 to qtyBalls
// save old position
ball[b].old.x = GetObjectX(ball[b].ID)
ball[b].old.y = GetObjectY(ball[b].ID)
// apply gravity to downward velocity
ball[b].vel.y = ball[b].vel.y - gravity#
// calculate new position of ball
ball[b].pos.x = ball[b].pos.x + ball[b].vel.x
ball[b].pos.y = ball[b].pos.y + ball[b].vel.y
// detect collision of ball against pegs
object_hit = ObjectSphereSlide(0, ball[b].old.x, ball[b].old.y,0.0,ball[b].pos.x, ball[b].pos.y,0.0,radius#)
// if ball hits a peg then have the ball bounce off it
if object_hit <> 0
// get new position (over write the current values
ball[b].pos.x = GetObjectRayCastSlideX(0)
ball[b].pos.y = GetObjectRayCastSlideY(0)
// get the new velocities based on the collision bounce
ball[b].vel.x = GetObjectRayCastBounceX(0)
ball[b].vel.y = GetObjectRayCastBounceY(0)
endif
// position the ball
SetObjectPosition(ball[b].ID, ball[b].pos.x, ball[b].pos.y, 0.0)
if ball[b].pos.y <= -50
resetball(b)
endif
next b
sync()
loop
function resetBall(b)
// set the ball's initial position
ball[b].pos.x = random(50,150)+0.5
ball[b].pos.y = 230.0
// set the ball's velocities to zero
ball[b].vel.x = 0.0
ball[b].vel.y = 0.0
// position the ball
SetObjectPosition(ball[b].ID, ball[b].pos.x, ball[b].pos.y, 0.0)
endfunction
type tBall
ID as integer
pos as tVect2
vel as tVect2
old as tVect2
endtype
type tVect2
x as float
y as float
endtype