class Camera: """ Camera object """ def __init__(self): self.rect = Rect() self.fen = None #Undefined yet self.angle = 0 self.rotation_effect = False #Timed effect of rotation self.remove_rotation_effect = True #Possibility to remove it def move(self, v): """ Translates the camera by vector v""" self.rect.translate(v) def link_world(self, w): """ Set the world attribute """ self.world = w def set_position(self, pos): """ Sets the position of the camera in the GameLevel""" self.rect.set_position(pos) if not (self.fen is None): self.compute_distorsion() def set_dimension(self, size): """ Set the dimension of the Camera (useful to zoom). Note that size is a Vector. """ self.rect.set_dimension(size) if not (self.fen is None): self.compute_distorsion() def get_position(self): """ Returns the position of the camera """ return self.rect.get_position() def get_dimension(self): """ Returns the dimension of the camera """ return self.rect.get_dimension() def set_fen(self, fen): """ Set the window in which the camera will output """ self.fen = fen self.compute_distorsion() def get_fen(self): """ Returns the windows associated with the camera """ return self.fen def set_distorsion(self, dis): """ Set the distorsion of the camera (rescale objects and """ self.distorsion = dis def get_distorsion(self): """ Returns the distorsion of the camera """ return self.distorsion def compute_distorsion(self): """ Computes the distorsion of the camera """ (width, height) = (self.fen.get_width(), self.fen.get_height()) dim = self.get_dimension() pos = self.get_position() distorsion_scale = Vector(width / dim.x, height / dim.y) distorsion_translate = -pos self.distorsion = (distorsion_scale, distorsion_translate) def is_in_camera(self, rect): """ Returns true if the polygon is completely in the camera's rect or if it intersects a side """ r = self.rect.intersect(rect) return r def center_on(self, pos): """ Centers the camera on a position """ pos = pos pos = pos + (-self.get_dimension() / 2) self.set_position(pos) def threeforth_on(self, pos): """ Makes a 3/4 on the position (this position will be on the left and 3/4 of the screen is free on the right -> usefull for a Canabalt style game """ dim = self.get_dimension() pos += (-Vector(dim.x / 4, dim.y / 2)) self.set_position(pos) def flashblack(self): """ Fill the camera with black in order to blit images right after """ self.get_fen().fill((0, 0, 0)) def reset_rotation(self): """ Reset the rotation """ self.angle = 0 def rotate(self, angle): """ Add the rotation of [angle] to the camera """ self.angle += angle def set_rotation_effect(self): self.rotation_effect = True self.rotate(0.5) def rotate_view(self, angle): """ Rotates the current content of the window by "angle" degrees """ if self.rotation_effect: self.rotate(0.5) if self.angle % 360 == 0 and self.remove_rotation_effect: self.rotation_effect = False center = self.get_fen().get_rect().center rotated_fen = pygame.transform.rotate(self.get_fen(), angle) rotated_rect = rotated_fen.get_rect() rotated_rect.center = center self.flashblack() self.get_fen().blit(rotated_fen, rotated_rect.topleft) def aff(self, objects, bg, score, dt): """ Show all objects of the given argument that are in the camera as well as the background and the score """ #Starts with a flashblack if not (self.get_fen() is None): self.flashblack() #Shows the Background (see Background) bg.show() #Shows all objects that are in the camera to_discard = [] for o in objects: if self.is_in_camera(o.get_hit_box().get_world_rect() ): #Checks if the hitbox is in the camera o.aff(self.get_fen(), self.get_distorsion(), dt) elif not (self.rect.collidex(o.get_hit_box().get_world_rect())): if o.stase(0) == 0: to_discard.append(o) elif self.rect.dist( o.get_hit_box().get_world_rect()) > self.rect.radius() * 2: if o.stase(1) == 0: to_discard.append(o) for o in to_discard: self.world.dynamic_objects.discard(o) del o #Show the score d = self.get_dimension() x = int(d.x * 15 / 16) #Computes where to put it y = int(d.y * 1 / 16) distorsion_scale = self.get_distorsion()[0] vpos = Vector(x, y) * distorsion_scale T(self.get_fen(), str(score), vpos.x, vpos.y, 255, 255, 255, size=45) if self.world.player.poisoned_timeout > 0: T(self.get_fen(), str("Poison!"), vpos.x - 150, vpos.y, 91 + (140 - self.world.player.poisoned_timeout * 14), 47, 82, size=45) T(self.get_fen(), str(self.world.name), vpos.x - 400, vpos.y, 255, 255, 255, size=45) # Rotation self.rotate_view(self.angle) def __repr__(self): txt = "Camera(" + str(self.rect) + ")" if self.fen is None: txt += "(not init)" return txt