def test_physics(): "convert the corners and the center from the world coords" for i in ["topleft", "topright", "bottomleft", "bottomright", "center"]: v = getattr(bounce.Physics.world_rect, i) r = bounce.ToPixels(v) s = bounce.ToWorld(r) print("%s: P%s -> W%s -> P%s" % (i, v, r, s))
def loadFromMap(self,wmap): try: group = wmap.tmx.get_layer_by_name("objects") except ValueError as e: print("Can't find objects layer in the map. Ignoring them") return # load animations for gid, props in wmap.tmx.tile_properties.items(): if 'parent' in props.keys() and props['parent'].lower() == "starship": for animation_frame in props['frames']: image = wmap.tmx.get_tile_image_by_gid(gid) self.engine.add_frame(image, animation_frame.duration) print("adding animation frame %d" % gid) group = wmap.tmx.get_layer_by_name("objects") starship =wmap.tmx.get_object_by_name("starship") if starship == None: print("Can't find starship layer in the map. Fatal. Bailing out") sys.exit(0) # load startship info from here. self.add_frame( starship.image ) rect = starship.image.get_rect() rect.topleft = (starship.x, starship.y) #define the Physics body wcenter = bounce.ScaleToWorld( ( rect.width/2, rect.height/2 )) self.body = bounce.Physics.world.CreateDynamicBody( position = bounce.ToWorld((rect.center)), angle = math.radians(-starship.rotation), fixtures = b2FixtureDef( # collision information # local filterData = { # categoryBits = player, # maskBits = wall + nme + platform, # groupIndex = 0 # } # fixture:setFilterData(filterData) # player, wall, nme, ... are integers variables (must be power of 2 numbers): # player = 1 # wall = 2 # nme = 4 # ... = 16, 32, 64, 128, 256, ... # categoryBits = main object you want to test collisions on # maskBits = you add (with +) all the numbers the main object can collide with. # player = 2 # static = 4 # balls = 8 # boxes = 16 #categoryBits=2, maskBits=4+8+16, groupIndex=0, userData=self, shape = b2PolygonShape(box= wcenter), density = starship.properties['density'], friction = starship.properties['friction'], restitution = starship.properties['restitution']) )
def loadBodiesFromMap(self): self.bodies = [] try: group = self.wmap.tmx.get_layer_by_name("objects") except ValueError as e: print("Can't find objects layer in the map. Ignoring them") return group = self.wmap.tmx.get_layer_by_name("objects") for obj in group: # # process the defined elements for objects. # if obj.type and obj.type.lower() == "wallline": print("wallline found: %s" % obj.name) # all points are defined from the base # <object id="30" name="object5" type="wallline" x="448" y="320"> # <polyline points="0,0 -128,64 -256,0 -256,64 -384,64"/> # </object> orig = (0, 0) # now, translate all the points to the 0,0: xlate = [] for p in obj.points: px, py = bounce.ToWorld(b2Vec2(p) + orig) xlate.append((px, py)) for p in xlate: print(p, len(xlate)) body = bounce.Physics.world.CreateStaticBody( shapes=b2ChainShape( vertices_chain=xlate)) ## the vertice order is CCW #body.fixtures[0].filterData.categoryBits=4 #body.fixtures[0].filterData.maskBits=0 #body.fixtures[0].filterData.groupIndex=0 if obj.type and obj.type.lower() == "wallcircle": print("wallcircle found: %s" % obj.name) center = (0, 0) rectsize = (0, 0) # its a circle, calculate center and radious #b2CircleShape(pos=(1, 2), radius=0.5) center = (obj.x + (obj.width / 2), obj.y + (obj.height / 2)) radius = max(obj.width / 2, obj.height / 2) print(center, radius) radius, _ = bounce.ScaleToWorld((radius, 0)) body = bounce.Physics.world.CreateStaticBody( position=bounce.ToWorld(center), shapes=b2CircleShape(radius=radius)) # dinamic object test if obj.type and obj.type.lower() == "dynpoly": print("dynpoly found: %s" % obj.name) center = (0, 0) rectsize = (0, 0) if not hasattr(obj, "points"): # its a rectangle, easy # x, y, height, width ## self.world.CreateStaticBody(position=(ww,h/2), shapes=b2PolygonShape(box=(ww,h/2)))) center = (obj.x + (obj.width / 2), obj.y + (obj.height / 2)) rectsize = (obj.width / 2, obj.height / 2) print(obj.x, obj.y, obj.width, obj.height) print(center, rectsize) body = bounce.Physics.world.CreateDynamicBody( position=bounce.ToWorld(center), angle=0, fixtures=b2FixtureDef( shape=b2PolygonShape( box=bounce.ScaleToWorld(rectsize)), density=obj.properties['density'], friction=obj.properties['friction'], restitution=obj.properties['restitution'])) else: # vertice chain so calculate the centroid. # create a static body here # first, get the points and calculate the center of the polygon. # calculate the centroid. x = [p[0] for p in obj.points] y = [p[1] for p in obj.points] centroid = (sum(x) / len(obj.points), sum(y) / len(obj.points)) # now, translate all the points to the 0,0: xlate = [] centroid = b2Vec2(centroid) for p in obj.points: # centroid is measure from (0.0) was is upper left, # in the world coords, start in bottom left, so just # swap the points y coord (flipping around axis 0) px, py = bounce.ScaleToWorld(b2Vec2(p) - centroid) xlate.append((px, -py)) for p in obj.points: print(p, centroid) for p in xlate: print(p) body = bounce.Physics.world.CreateDynamicBody( position=bounce.ToWorld(centroid), angle=0, fixtures=b2FixtureDef( shape=b2PolygonShape(vertices=xlate), density=obj.properties['density'], friction=obj.properties['friction'], restitution=obj.properties['restitution'])) if obj.type and obj.type.lower() == "dyncircle": print("dyncircle found: %s" % obj.name) center = (0, 0) rectsize = (0, 0) # its a circle, calculate center and radious #b2CircleShape(pos=(1, 2), radius=0.5) center = (obj.x + (obj.width / 2), obj.y + (obj.height / 2)) radius = max(obj.width / 2, obj.height / 2) print(center, radius) for p in obj.properties.keys(): print("%s: %s" % (p, obj.properties[p])) radius, _ = bounce.ScaleToWorld((radius, 0)) body = bounce.Physics.world.CreateDynamicBody( position=bounce.ToWorld(center), angle=0, fixtures=b2FixtureDef( shape=b2CircleShape(radius=radius), density=obj.properties['density'], friction=obj.properties['friction'], restitution=obj.properties['restitution'])) print(body) if obj.type and obj.type.lower() == "wall": print("wall found: %s" % obj.name) center = (0, 0) rectsize = (0, 0) if not hasattr(obj, "points"): # its a rectangle, easy # x, y, height, width ## self.world.CreateStaticBody(position=(ww,h/2), shapes=b2PolygonShape(box=(ww,h/2)))) center = (obj.x + (obj.width / 2), obj.y + (obj.height / 2)) rectsize = (obj.width / 2, obj.height / 2) print(obj.x, obj.y, obj.width, obj.height) print(center, rectsize) body = bounce.Physics.world.CreateStaticBody( position=bounce.ToWorld(center), shapes=b2PolygonShape( box=bounce.ScaleToWorld(rectsize))) else: # vertice chain so calculate the centroid. # create a static body here # first, get the points and calculate the center of the polygon. # calculate the centroid. x = [p[0] for p in obj.points] y = [p[1] for p in obj.points] centroid = (sum(x) / len(obj.points), sum(y) / len(obj.points)) # now, translate all the points to the 0,0: xlate = [] centroid = b2Vec2(centroid) for p in obj.points: # centroid is measure from (0.0) was is upper left, # in the world coords, start in bottom left, so just # swap the points y coord (flipping around axis 0) px, py = bounce.ScaleToWorld(b2Vec2(p) - centroid) xlate.append((px, -py)) for p in obj.points: print(p, centroid) for p in xlate: print(p) body = bounce.Physics.world.CreateStaticBody( position=bounce.ToWorld(centroid), shapes=b2PolygonShape( vertices=xlate)) ## the vertice order is CCW if obj.image != None and obj.name.lower() != "starship": "allocate the sprite, and update it when the object is updated" body_s = bounce.SpritePhysics(self.clock, body) body_s.add_frame(obj.image) self.sprites.add(body_s) print("adding sprite") self.bodies.append(body)
def test_sprite_physics(): app = bounce.pyGameAppPhysics() app.init() image = pygame.image.load("assets/starship.png") rect = image.get_rect() wcenter = bounce.ScaleToWorld((rect.width / 2, rect.height / 2)) body = bounce.Physics.world.CreateDynamicBody( position=bounce.ToWorld((100, 100)), angle=math.radians(0), fixtures=b2FixtureDef(shape=b2PolygonShape(box=wcenter), density=10, friction=0.5, restitution=0.1)) app.bodies.append(body) mysprite_single = bounce.SpritePhysics(app.clock, body) mysprite_single.add_frame(image) mysprite_single.init() # move done with the physics engine. app.sprites.add(mysprite_single) rect = pygame.Rect((0, 0), (35, 50)) images = bounce.load_spritesheet("assets/engine-layer.png", rect.size) wcenter = bounce.ScaleToWorld((rect.width / 2, rect.height / 2)) body = bounce.Physics.world.CreateDynamicBody( position=bounce.ToWorld((200, 200)), angle=math.radians(0), fixtures=b2FixtureDef(shape=b2PolygonShape(box=wcenter), density=10, friction=0.5, restitution=0.1)) app.bodies.append(body) mysprite_anim = bounce.SpritePhysics(app.clock, body) for i in images: mysprite_anim.add_frame(i) mysprite_anim.init() app.sprites.add(mysprite_anim) #store them so I can change later. app.sprite_dict["single"] = mysprite_single app.sprite_dict["anim"] = mysprite_anim # how to redefine a method in the class application with a new implementation (cool!) #app.on_event = types.MethodType(custom_on_event, app) def custom_on_event(self): for event in pygame.event.get(): if event.type == pygame.QUIT or (event.type == pygame.KEYDOWN and event.key == pygame.K_ESCAPE): self._running = False return if event.type == pygame.KEYDOWN and event.key == pygame.K_SPACE: if self.sprite_dict["anim"].isRunning(): self.sprite_dict["anim"].stop() else: self.sprite_dict["anim"].play() if event.type == pygame.KEYDOWN and event.key == pygame.K_c: self.sprite_dict["anim"].clear() if event.type == pygame.KEYDOWN and event.key == pygame.K_q: #single impulse = 200 y = math.sin(math.radians(45)) * impulse x = math.cos(math.radians(45)) * impulse body = self.sprite_dict["single"].body body.ApplyLinearImpulse(impulse=(x, y), point=body.worldCenter, wake=True) #anim impulse = 100 y = math.sin(math.radians(90)) * impulse x = math.cos(math.radians(90)) * impulse body = self.sprite_dict["anim"].body body.ApplyLinearImpulse(impulse=(x, y), point=body.worldCenter, wake=True) app.on_event = types.MethodType(custom_on_event, app) app.on_execute()