Search code examples
pythonphysicssegmentknifepymunk

weight on Box using Pymunk


I have written the below program which is aimed at simulating a weight balancing experiment using knife edge. however, the weight of the box is not affecting the segment as shown when simulated. I am currently new on learning how to code with pymunk. kindly help me out on this

    import pyglet
    import pymunk
    import chipmunk
    from pymunk import Vec2d
    from pymunk.pyglet_util import DrawOptions

    window = pyglet.window.Window(800,600,"Knife Edge Mass Balancing Simulation",resizable=False)# W,H
    options=DrawOptions()

    space=pymunk.Space()
    space.gravity= 0,-100

    mass = 1
    radius=30


    ground_moment = pymunk.moment_for_segment(800,(0,0),(800,0),2)
    ground_body = pymunk.Body(body_type=pymunk.Body.STATIC)
    ground_shape = pymunk.Segment(ground_body,(0,0),(800,0),20)
    ground_body.position=0,100
    ground_body.elasticity=0.1
    ground_body.friction=0.1

    poly_shape=pymunk.Poly(None,((0,0),(100,0),(50,150)))
    poly_moment = pymunk.moment_for_poly(500,poly_shape.get_vertices())
    poly_body=pymunk.Body(body_type=pymunk.Body.STATIC)
    poly_shape.body=poly_body
    poly_body.position = 350,100
    poly_body.elasticity=0.1


    segment_moment = pymunk.moment_for_segment(mass,(0,0),(300,0),2)
    segment_body = pymunk.Body(mass,segment_moment)
    segment_shape = pymunk.Segment(segment_body,(0,0),(400,0),5)
    segment_body.position= 210,250
    segment_shape.elasticity = 0.1
    segment_shape.friction = 0.1

    size = 20
    box_mass = 0.0

    moment = pymunk.moment_for_box(box_mass, (size, size))
    box_body = pymunk.Body(box_mass, moment)
    box_body.position = Vec2d(300, 265.5)
    box_shape = pymunk.Poly.create_box(box_body, (size, size))
    box_shape.friction = 0.8
    box_shape.elasticity = 0.1


    space.add(ground_body, ground_shape,poly_body,poly_shape,segment_body, segment_shape, box_body, box_shape)


   @window.event
   def on_draw():
   window.clear()
   space.debug_draw(options)

   def update(dt):
   space.step(dt)

   if __name__=="__main__":
       pyglet.clock.schedule_interval(update,1.0/60)
       pyglet.app.run()

Solution

  • The problem is that the the segment shape has its weight in one end, and not in the center. This happens because weight in Pymunk is collected at the position of the Body of the shape(s).

    Try to change the segment code to something like this:

    segment_moment = pymunk.moment_for_segment(mass,(-150,0),(150,0),2)
    segment_body = pymunk.Body(mass,segment_moment)
    segment_shape = pymunk.Segment(segment_body,(-200,0),(200,0),5)
    segment_body.position= 400,250
    segment_shape.elasticity = 0.1
    segment_shape.friction = 0.1