#### Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

# Inaccuracy of the physics engine?

2»

• Posts: 8,463

.@inoddy Heres your butterfly effect. I draw the initial path and keep it for the first loop, then I overlay the loops after that without saving them to show the effect of increasing the initial speed (x axis) of the pendulum. The paths are similar starting at 1 until it gets to the 470’s which is where I start this example. This shows how small changes have small effects until it reaches a critical point, then it has a major change. I draw each loop for 10 seconds then add 2 to the speed and draw the next loop.

``````supportedOrientations(PORTRAIT)
displayMode(FULLSCREEN)

function setup()
speed=470  -- starting speed
tab1={}
tab2={}
loop=1
c1 = physics.body(CIRCLE,0)
c1.x = 400
c1.y = 900
c1.restitution = 1
c1.type = STATIC
setup2()
end

function setup2()
et=ElapsedTime
if c2 ~= nil then
loop=2
tab2={}
c2:destroy()
c3:destroy()
speed=speed+2  -- speed increase each loop
end
c2 = physics.body(CIRCLE,25)
c2.x = 400
c2.y = 600
c2.restitution = 1

c3 = physics.body(CIRCLE, 25)
c3.x = 400
c3.y = 800
c3.linearVelocity=vec2(speed,0)
c3.restitution = 1

joint1 = physics.joint(REVOLUTE,c1,c2,c1.position)
joint2 = physics.joint(REVOLUTE, c2, c3,vec2(c2.x,c2.y))
end

function draw()
background(40, 40, 50)
fill(255)
text("Speed".."  "..speed,400,920)
if ElapsedTime-et>10 then  -- draw loop for 10 seconds
setup2()
end

noFill()
stroke(255)
strokeWidth(2)
line(c1.x,c1.y,c2.x,c2.y)
line(c2.x,c2.y,c3.x,c3.y)
ellipse(c1.x,c1.y,2)

if loop==1 then
table.insert(tab1,vec2(c3.x,c3.y))  -- save initial loop
else
table.insert(tab2,vec2(c3.x,c3.y))   -- save current loop
end
for a,b in pairs(tab1) do  -- draw initial loop
stroke(255, 255, 0, 255)
ellipse(b.x,b.y,2)
end
for a,b in pairs(tab2) do  -- draw current loop
stroke(255)
ellipse(b.x,b.y,2)
end
end

``````
• Posts: 36

Thanks @dave1707. That's actually quite pretty. I'm going to use that code as my starting point for exploration of the physics engine.

• edited June 2013 Posts: 372

@Dave1707 can you share the code of the 2 bouncing balls where you used to get two results and fixed it and got one result by creating the body twice. I am not able to recreate the same results every time. Thanks!!

• Posts: 8,463

.@Saurabh Here's the code. I keep the x,y values from loop 1 to compare to loops 2,3,4,5, etc. The values (20 of them) are every 5 collisions for 100 collisions. Run this code for several loops to see how the odd loops match loop 1 and the even loops don't. Then uncomment the line in the draw routine that will do a double setup2 to skip the even loops.

``````supportedOrientations(PORTRAIT_ANY)
displayMode(FULLSCREEN)

function setup()
font("Courier")
loop=0
tab1={}
tab2={}
restart=true
end

function setup2()
tab2={}
count=0
loop=loop+1
if b1 then
b1:destroy()
b2:destroy()
e1:destroy()
e2:destroy()
e3:destroy()
e4:destroy()
end

e1=physics.body(EDGE,vec2(0,0),vec2(0,HEIGHT))
e2=physics.body(EDGE,vec2(0,HEIGHT),vec2(WIDTH,HEIGHT))
e3=physics.body(EDGE,vec2(WIDTH,HEIGHT),vec2(WIDTH,0))
e4=physics.body(EDGE,vec2(WIDTH,0),vec2(0,0))

b1=physics.body(CIRCLE,60)
b1.gravityScale=0
b1.restitution=1
b1.linearDamping=0
b1.linearVelocity=vec2(380,700)
b1.x=200
b1.y=600
b1.friction=0

b2=physics.body(CIRCLE,60)
b2.gravityScale=0
b2.restitution=1
b2.linearDamping=0
b2.linearVelocity=vec2(620,450)
b2.x=400
b2.y=200
b2.friction=0

end

function draw()
background(40,40,50)
textMode(CORNER)
if restart then
setup2()  -- setup for the physics objects
if loop>1 then
--setup2() -- uncomment this line to skip loops
end
restart=false
end
noFill()
strokeWidth(4)
stroke(255)
ellipse(b1.x,b1.y,120)
ellipse(b2.x,b2.y,120)
fill(255)
text("x,y loop 1          x,y loop 2,3,4 etc.",100,1000)
text("loop "..loop,600,1000)
text("Shows the x,y position every 5 collisions for 100 collisions.",100,300)
text("Retains the values for loop 1 to compare to loops 2,3,4, etc.",100,260)
text("The odd loops are the same and the even loops are the same.",100,220)
text("But the odd loops and the even loops don't match each other.",100,180)
text("The odd, even loops start out equal, but then differ.",100,140)
for a,b in pairs(tab1) do
text(b.x.." "..b.y,100,HEIGHT-50-a*20)
end
for a,b in pairs(tab2) do
text(b.x.." "..b.y,300,HEIGHT-50-a*20)
end
end

function collide(c)
if c.state==BEGAN then
count = count + 1
if count%5 == 0 then
if loop==1 then
table.insert(tab1,vec2(b1.x,b1.y))
end
if loop>1 then
table.insert(tab2,vec2(b1.x,b1.y))
end
end
if count==100 then
restart=true
end
end
end

``````
• Posts: 622

Thanks for the example @dave1707. I'm going to do some testing to try to get to the bottom of the Physics determinism issues. It's interesting how it manifests only on even play throughs.

• Posts: 8,463

.@John It's not the even plays, it's the alternating plays. All of the odd runs have the same values, and all of the even runs have the same values. It's just that the odd/even runs differ from each other. It's like every time the physics engine does a soft restart, some starting value alternates. Like one run starts with 0 and the next starts with 1, then 0, then 1, etc. It would be interesting to see what's really happening.

• Posts: 1,595

Thats what I have been seeing a lot @dave1707 it has different attributes applied to the body when the physics engine is run/restarted and they consist of 2 different sets of attributes which alternate but I dont think its the actual attributes of the physics bodies, maybe the way they're applied with set values in the engine which change every restart, from what I've seen anyway

• Posts: 372

Thanks @Dave1707 useful code.

• edited July 2013 Posts: 372

Okay so I was just wondering if the new restart function will give the same result every time or different result. Anyone has any idea??

• Posts: 455

I haven't tried double pendulum, but you can probably throw one into my physics sandbox quite easily.

http://twolivesleft.com/Codea/Talk/discussion/2125/physics-sandbox

• Posts: 372

Thanks @spacemonkey i'll try it out..

• Posts: 8,463

When I first posted the program above, the even runs gave the same values and the odd run gave the same values, but the even and odd runs were different from each other. When I run it now, the even and odd runs match each other. I don't know if it was fixed on purpose or fixed by chance in the latest version of Codea, but it seems to work the same now. So I dont think the new restart function will change anything.

• Posts: 372

Yeah that's weird. Don't know what's wrong with the code I've written it's giving different results every time. I'll check it out again.

• Posts: 1,595

@Saurabh I just got out my spline project and got rid of the double reset so it now only creates the bodies once and it seems to be fixed..

• Posts: 372

Thanks guys got it running finally.