What the ENTIRE progam?!?! Really what I've got is a setup phase, and then a run simulation phase which is nothing more than ODE's update. I hand over to that. At present I use something like...
I will be adding a test each frame along the lines of
For each object, If Frame = object\Entry_time, object visibile=true, ODE_active=true
This loop calls the simulation update once per iteration and so that's called 1/60th or 1/75th frame or whatever depending on screen refresh (which is something I'm a little concerned about, but not a great deal), or less than that if the simulation time overruns one frame. Simulations are nothing complex so it's not an issue on most machines but on the test case at say <30 fps main loop update the simulation runs at about half speed. If I change the quickstep value ODE_Resolution to 0.25 the low spec'd machine runs it nicely but of course it's too fast on anything more up to date.
It's not a time critical system and if the program runs slightly faster or slower on different machines that's fine. However I'd like to be able to offer at least a reasonably realistic speed even on slow machines and I know ODE can handle that if only I could figure how to tweak it.
Global ODE_Resolution# = 0.15 While Not KeyHit(1) frame=advance_simulation(frame) For obj.ODE_object=Each ODE_object Update_object(obj) Next UpdateWorld() RenderWorld() Flip Wend Function advance_simulation(t%) ; Advances the simluation, incrementing frame count ; Performs friction calculations ; Disables 'non-existant' objects dSpaceCollide(ODE_space,ODE_world,ODE_contactGroup) ;#Region Apply Rotational Friction For ode.ODE_object=Each ODE_object If ode\body If dBodyGetPositionY(ode\body)<-50.0 dBodyDisable(ode\body) HideEntity ode\mesh HideEntity ode\outline_mesh EndIf If dBodyIsEnabled(ode\body) numjoints=dBodyGetNumJoints(ode\body) If numjoints>0 ; If joined to another body For joints=0 To numjoints-1 ; for all joints attached to body... joint=dBodyGetJoint(ode\body,joints) If dJointGetType(joint)=dJointTypeContact ; If joint type is a collision contact ; Get Angular velocity vector bx#=dBodyGetAngularVelX#(ode\body) by#=dBodyGetAngularVelY#(ode\body) bz#=dBodyGetAngularVelZ#(ode\body) ; Calculate magnitudes ForceB#=Sqr(bx*bx+by*by+bz*bz) If forceb>.01 friction#=ode\mat\rotational_friction*-1.0 dBodyAddTorque ode\body,dBodyGetAngularVelX(ode\body)*friction,dBodyGetAngularVelY(ode\body)*friction,dBodyGetAngularVelZ(ode\body)*friction End If End If Next EndIf EndIf EndIf Next ;#End Region dWorldQuickStep(ODE_world,ODE_Resolution#) dJointGroupEmpty(ODE_contactGroup) Return t+1 End Function Function update_object(obj.ODE_Object) RotateEntity obj\mesh,dGeomGetPitch#(obj\geom),dGeomGetYaw#(obj\geom),dGeomGetRoll#(obj\geom) PositionEntity obj\mesh,dGeomGetPositionX#(obj\geom),dGeomGetPositionY#(obj\geom),dGeomGetPositionZ#(obj\geom) End Function
I will be adding a test each frame along the lines of
For each object, If Frame = object\Entry_time, object visibile=true, ODE_active=true
This loop calls the simulation update once per iteration and so that's called 1/60th or 1/75th frame or whatever depending on screen refresh (which is something I'm a little concerned about, but not a great deal), or less than that if the simulation time overruns one frame. Simulations are nothing complex so it's not an issue on most machines but on the test case at say <30 fps main loop update the simulation runs at about half speed. If I change the quickstep value ODE_Resolution to 0.25 the low spec'd machine runs it nicely but of course it's too fast on anything more up to date.
It's not a time critical system and if the program runs slightly faster or slower on different machines that's fine. However I'd like to be able to offer at least a reasonably realistic speed even on slow machines and I know ODE can handle that if only I could figure how to tweak it.