f4dc47ba8053 — Leonard Ritter 3 months ago
* added C bindings for Bullet
5 files changed, 269 insertions(+), 14 deletions(-)

M externals/build_bullet.py
M externals/build_common.py
A => testing/test_bullet.sc
A => tukan/bullet/C.sc
M tukan/ode/init.sc
M externals/build_bullet.py +35 -13
@@ 16,23 16,45 @@ class Builder(BuilderBase):
         self.run_any_build()
 
     def run_linux2_build(self):
-        """
-        os.chdir(os.path.join(self.TARGETDIR, "build3"))
-        cmd = './premake4_linux64 --double gmake'
+        builddir = os.path.join(self.TARGETDIR, "build_cmake")
+        self.makedirs(builddir)
+        self.chdir(builddir)
+        cmd = "cmake -DBUILD_SHARED_LIBS=ON -DUSE_DOUBLE_PRECISION=ON -DBT_USE_EGL=ON -DCMAKE_BUILD_TYPE=Release .."
         self.shell(cmd)
-
-        os.chdir(os.path.join(self.TARGETDIR, "build3", "gmake"))
         self.shell("make -j8")
-        """
-        cmd = './build_cmake_pybullet_double.sh'
-        self.shell(cmd)
 
-        #os.environ['CFLAGS'] = '-fPIC'
-        #os.environ['CXXFLAGS'] = '-fPIC'
-        #os.environ['CPPFLAGS'] = '-fPIC'
-        #cmd = 'make -j 4 nanovg config=release'
-        #self.shell(cmd)
+        version = "2.89"
+        basedir = "build_cmake"
+        libfiles = [
+            ("Extras/BulletRobotics", "libBulletRobotics.so"),
+            ("Extras/InverseDynamics", "libBulletInverseDynamicsUtils.so"),
+            ("Extras/Serialize/BulletWorldImporter", "libBulletWorldImporter.so"),
+            ("Extras/Serialize/BulletFileLoader", "libBulletFileLoader.so"),
+            ("src/BulletSoftBody", "libBulletSoftBody.so"),
+            ("src/BulletDynamics", "libBulletDynamics.so"),
+            ("src/BulletCollision", "libBulletCollision.so"),
+            ("src/BulletInverseDynamics", "libBulletInverseDynamics.so"),
+            ("src/LinearMath", "libLinearMath.so"),
+            ("src/Bullet3Common", "libBullet3Common.so"),
+        ]
+        for libdir,targetname in libfiles:
+            targetname = targetname + "." + version
+            self.copy2(os.path.join(self.TARGETDIR, basedir, libdir, targetname),
+                os.path.join(self.BINDIR, targetname))
 
+        includesrcdir = os.path.join(self.TARGETDIR, 'examples', 'SharedMemory')
+        includedir = os.path.join(self.CDEFDIR, 'bullet')
+        self.rmtree(includedir)
+        self.makedirs(includedir)
+        headerfiles = [
+            'PhysicsClientC_API.h',
+            'SharedMemoryPublic.h',
+            'PhysicsClientSharedMemory_C_API.h',
+            'PhysicsClientSharedMemory2_C_API.h',
+            'PhysicsDirectC_API.h',
+        ]
+        for header in headerfiles:
+            self.copy2(os.path.join(includesrcdir, header), includedir)
         self.run_any_build()
 
     def run_any_build(self):

          
M externals/build_common.py +1 -0
@@ 641,6 641,7 @@ class BuilderBase(object):
     copy2 = staticmethod(shutil.copy2)
     copytree = staticmethod(copytree)
     chdir = staticmethod(os.chdir)
+    makedirs = staticmethod(os.makedirs)
     joinpath = staticmethod(os.path.join)
     pathsep = os.pathsep
     sep = os.sep

          
A => testing/test_bullet.sc +178 -0
@@ 0,0 1,178 @@ 
+
+using import glm
+using import Capture
+using import Array
+using import enum
+
+import ..tukan.use
+using import tukan.VertexPainter
+using import tukan.GLMain
+using import tukan.gl
+using import tukan.bullet.C
+using import tukan.rotation
+using import tukan.math
+
+let api = (b3ConnectPhysicsDirect)
+
+
+#
+    global world = (World)
+    world.gravity = (vec3 0 -10 0)
+
+    global space = (SimpleSpace)
+
+    local geoms : (Array Geom)
+    local bodies : (Array Body)
+    local joints : (Array PUJoint)
+    local amotorjoints : (Array AMotorJoint)
+
+    do
+        let planeg =
+            Plane space (vec4 0 1 0 0)
+        let planeb =
+            Body world
+        planeg.body = planeb
+        planeb.kinematic = true
+
+        inline makebox (y r)
+            #let g = (Cylinder space r (2.0 * r))
+            let g = (Capsule space (r * 0.5) (2.0 * r - r * 1.0))
+            #let g = (Box space (2.0 * r) (2.0 * r) (2.0 * r))
+            #let g = (Sphere space r)
+            let b = (Body world)
+            b.position = (vec3 0 y 0)
+            b.quaternion = (versor (vec3 1 0 0) (pi * 0.5))
+            g.body = b
+            _ g b
+        inline append (g b)
+            'append geoms g
+            'append bodies b
+
+        let y = 0.51
+        let r = 0.5
+        let box1g box1b = (makebox y r)
+        let j0 = (PUJoint world)
+        'attach j0 planeb box1b
+        j0.anchor = (vec3 0)
+        j0.axis1 = (vec3 1 0 0)
+        j0.axis2 = (vec3 0 0 1)
+        j0.axis3 = (vec3 0 1 0)
+        'set-lo-stop j0 2 0.0
+        'set-hi-stop j0 2 0.0
+        'append joints j0
+        append planeg planeb
+
+        #D := 0.1
+        D := 0.0
+        #D := -0.01
+
+        let boxg boxb =
+            fold (boxg boxb y r = box1g box1b y r) for i in (range 9)
+                y := y + r + D
+                r := r * 0.9
+                y := y + r
+                let box2g box2b = (makebox y r)
+                do
+                    let j = (PUJoint world)
+                    'attach j boxb box2b
+                    j.anchor = (boxb.position as vec3 + box2b.position as vec3) * 0.5
+                    j.axis1 = (vec3 1 0 0)
+                    j.axis2 = (vec3 0 0 1)
+                    j.axis3 = (vec3 0 1 0)
+                    'set-lo-stop j 2 0.0
+                    'set-hi-stop j 2 0.0
+                    'append joints j
+
+                #do
+                    let j = (AMotorJoint world)
+                    'attach j boxb box2b
+                    'set-num-axes j 2
+                    'set-axis j 0 1 (vec3 1 0 0)
+                    'set-axis j 1 1 (vec3 0 1 0)
+                    'append amotorjoints j
+                append boxg boxb
+                _ box2g box2b y r
+        append boxg boxb
+
+    global jgroup = (JointGroup)
+
+    let glmain =
+        GLMain
+            title = "ODE Test"
+            resizable = true
+            width = 1280
+            height = 720
+
+    global t = 0.0
+    let NUM_CONTACTS = 1024
+
+    @@ 'on GLMain.on-draw
+    inline (time size glmain)
+        let N = 2
+        a := t * pi / 8.0
+        g := (normalize (vec3 (cos a) -2 (sin a))) * 10.0
+        world.gravity = g
+        for i in (range N)
+            'step world (/ 1.0 (N * 60.0))
+            'empty jgroup
+            'collide space
+                fn (o1 o2)
+                    let contacts = (alloca-array Contact NUM_CONTACTS)
+                    for i in (range NUM_CONTACTS)
+                        contacts @ i = (Contact)
+                    let num_collisions =
+                        'collide o1 o2 NUM_CONTACTS
+                            & (contacts @ 0 . geom)
+                            sizeof Contact
+                    for j in (range 0 num_collisions)
+                        let surf = (contacts @ j . surface)
+                        surf.mode = (ContactBounce as u32 as i32)
+                        surf.mu = 250
+                        surf.bounce = 0.6
+                        surf.bounce_vel = 0.05
+                        let c =
+                            ContactJoint world jgroup (contacts @ j)
+                        let b0 =
+                            contacts @ j . geom . g1 . body
+                        let b1 =
+                            contacts @ j . geom . g2 . body
+                        'attach c b0 b1
+            #for j m in (zip joints amotorjoints)
+                print
+                    j.angle1 as f32; j.angle2 as f32
+                    \ ('get-angle m 0) ('get-angle m 1)
+
+        #fn draw (time size glmain)
+        let painter = (VertexPainter)
+        'setup-depth painter
+        GL.BindFramebuffer GL.FRAMEBUFFER 0
+        GL.Viewport 0 0 (i32 size.x) (i32 size.y)
+        GL.ClearColor 0 0 0.5 1
+        GL.Enable GL.CULL_FACE
+        GL.Clear
+            |
+                GL.COLOR_BUFFER_BIT
+                GL.DEPTH_BUFFER_BIT
+                GL.STENCIL_BUFFER_BIT
+
+        t += (/ 60.0)
+
+        from (methodsof painter) let clear color screen rotate AABB \
+            translate quad perspective scale light flush wireframe moveto lineto \
+            closepath fill stroke push pop
+        # setup view
+        light 0.3 -1 -0.2
+        scale 2.0
+        perspective size
+        translate
+            vec3 0 -4 10
+        rotate
+            radians 45.0
+            #pi * t * 0.25
+            vec3 0 1 0
+        'debugdraw space painter
+        drop painter
+
+    'run glmain
+
+    ;

          
A => tukan/bullet/C.sc +28 -0
@@ 0,0 1,28 @@ 
+import ..stage
+
+# currently not available by default
+
+if (operating-system == 'windows)
+    #load-library "ODE.dll"
+else
+    load-library
+        module-dir .. "/../../bin/libBulletRobotics.so.2.89"
+
+run-stage;
+
+vvv bind lib
+include
+    options "-I" (module-dir .. "/../../cdefs")
+    """"#include "bullet/PhysicsClientC_API.h"
+
+do
+    #using lib.define filter "^(B3(.+))$"
+    #using lib.const filter "^(b3(.+))$"
+    using lib.typedef filter "^(b3(.+))$"
+    using lib.extern filter "^(b3(.+))$"
+
+    #@@ 'on stage.on-init
+    #inline ()
+        dInitODE;
+
+    locals;

          
M tukan/ode/init.sc +27 -1
@@ 11,6 11,13 @@ let fvec2 = (vec-type float 2)
 let fvec3 = (vec-type float 3)
 let fvec4 = (vec-type float 4)
 
+inline spring->ERP+CFM (kp kd h)
+    """"kp = spring constant, kd = damping constant, h = step size
+    # from http://ode.org/wiki/index.php?title=Manual#How_To_Use_ERP_and_CFM
+    cfm := (float 1.0) / (h * kp + kd)
+    erp := (h * kp) * cfm
+    _ erp cfm
+
 typedef Wrapper
     inline _storagecast (self)
         dupe (storagecast (view self))

          
@@ 122,6 129,12 @@ typedef+ Mass
     inline... capsule (self : &this-type, density : float, direction : i32, radius : float, length : float)
         dMassSetCapsule &self density direction radius length
 
+    inline... sphere (self : &this-type, density : float, radius : float)
+        dMassSetSphere &self density radius
+
+    inline... sphere-total (self : &this-type, total-mass : float, radius : float)
+        dMassSetSphereTotal &self total-mass radius
+
 typedef Body < Wrapper :: dBodyID
     inline __typecall (cls world)
         imply (dBodyCreate world) this-type

          
@@ 155,6 168,7 @@ typedef Body < Wrapper :: dBodyID
         linear-damping-threshold = (property dBodyGetLinearDampingThreshold dBodySetLinearDampingThreshold)
         angular-damping-threshold = (property dBodyGetAngularDampingThreshold dBodySetAngularDampingThreshold)
         max-angular-speed = (property dBodyGetMaxAngularSpeed dBodySetMaxAngularSpeed)
+        data = (property dBodyGetData dBodySetData)
 
     let _dBodyGetFirstGeom =
         bitcast dBodyGetFirstGeom

          
@@ 228,6 242,10 @@ typedef World < Wrapper :: dWorldID
         #static-body = (property _cpSpaceGetStaticBody)
         gravity =
             vector-property fvec3 dWorldGetGravity dWorldSetGravity
+        ERP =
+            property dWorldGetERP dWorldSetERP
+        CFM =
+            property dWorldGetCFM dWorldSetCFM
         quick-step-num-iterations =
             property dWorldGetQuickStepNumIterations dWorldSetQuickStepNumIterations
 

          
@@ 491,6 509,10 @@ typedef+ GeomType
     let position = (vector-property2 fvec3 dGeomGetPosition dGeomSetPosition)
     let quaternion = (quaternion-property dGeomGetQuaternion dGeomSetQuaternion)
     let enabled = (boolean-property dGeomIsEnabled dGeomEnable dGeomDisable)
+    let data = (property dGeomGetData dGeomSetData)
+
+    fn body? (self)
+        (storagecast (_dGeomGetBody self)) != null
 
 typedef Plane < GeomType :: dGeomID
     inline... __typecall

          
@@ 878,6 900,10 @@ do
         \ PUJoint PistonJoint FixedJoint AMotorJoint LMotorJoint Plane2DJoint
         \ DBallJoint DHingeJoint TransmissionJoint
 
-    let ContactBounce = dContactBounce
+    let
+        ContactBounce = dContactBounce
+        ContactApprox1 = dContactApprox1
+
+    let spring->ERP+CFM
 
     locals;