changeset 123:d1c82d43bbf3

Various optimizations
author Thibaut Girka <thib@sitedethib.com>
date Sat, 10 Sep 2011 11:58:24 +0200
parents 174324a4da51
children f06e96dbed4e
files pytouhou/game/bullet.py pytouhou/game/enemy.py pytouhou/game/game.py pytouhou/opengl/gamerenderer.py pytouhou/utils/matrix.py
diffstat 5 files changed, 53 insertions(+), 49 deletions(-) [+]
line wrap: on
line diff
--- a/pytouhou/game/bullet.py
+++ b/pytouhou/game/bullet.py
@@ -20,14 +20,14 @@ from pytouhou.game.sprite import Sprite
 
 
 class Bullet(object):
-    def __init__(self, pos, type_idx, sprite_idx_offset,
+    def __init__(self, pos, bullet_type, sprite_idx_offset,
                        angle, speed, attributes, flags, player, game_state):
         self._game_state = game_state
         self._sprite = None
         self._anmrunner = None
         self._removed = False
         self._launched = False
-        self._bullet_type = game_state.bullet_types[type_idx]
+        self._bullet_type = bullet_type
 
         self.speed_interpolator = None
         self.frame = 0
@@ -48,21 +48,20 @@ class Bullet(object):
 
         #TODO
         if flags & 14:
-            bt = self._bullet_type
             if flags & 2:
-                index = bt.launch_anim2_index
-                launch_mult = bt.launch_anim_penalties[0]
+                index = bullet_type.launch_anim2_index
+                launch_mult = bullet_type.launch_anim_penalties[0]
             elif flags & 4:
-                index = bt.launch_anim4_index
-                launch_mult = bt.launch_anim_penalties[1]
+                index = bullet_type.launch_anim4_index
+                launch_mult = bullet_type.launch_anim_penalties[1]
             else:
-                index = bt.launch_anim8_index
-                launch_mult = bt.launch_anim_penalties[2]
+                index = bullet_type.launch_anim8_index
+                launch_mult = bullet_type.launch_anim_penalties[2]
             self.launch_delta = dx * launch_mult, dy * launch_mult
             self._sprite = Sprite()
-            self._anmrunner = ANMRunner(bt.anm_wrapper,
+            self._anmrunner = ANMRunner(bullet_type.anm_wrapper,
                                         index, self._sprite,
-                                        bt.launch_anim_offsets[sprite_idx_offset])
+                                        bullet_type.launch_anim_offsets[sprite_idx_offset])
             self._anmrunner.run_frame()
         else:
             self.launch()
@@ -72,16 +71,15 @@ class Bullet(object):
 
     def is_visible(self, screen_width, screen_height):
         tx, ty, tw, th = self._sprite.texcoords
-        if self._sprite.corner_relative_placement:
-            raise Exception #TODO
+        x, y = self.x, self.y
 
         max_x = tw / 2.
         max_y = th / 2.
 
-        if any((max_x < self.x - screen_width,
-                max_x < -self.x,
-                max_y < self.y - screen_height,
-                max_y < -self.y)):
+        if (max_x < x - screen_width
+            or max_x < -x
+            or max_y < y - screen_height
+            or max_y < -y):
             return False
         return True
 
--- a/pytouhou/game/enemy.py
+++ b/pytouhou/game/enemy.py
@@ -85,9 +85,11 @@ class Enemy(object):
 
 
     def fire(self):
-        (type_, anim, sprite_idx_offset, bullets_per_shot, number_of_shots,
+        (type_, type_idx, sprite_idx_offset, bullets_per_shot, number_of_shots,
          speed, speed2, launch_angle, angle, flags) = self.bullet_attributes
 
+        bullet_type = self._game_state.bullet_types[type_idx]
+
         ox, oy = self.bullet_launch_offset
         launch_pos = self.x + ox, self.y + oy
 
@@ -116,7 +118,7 @@ class Enemy(object):
                 if type_ == 75: # 102.h@0x4138cf
                     bullet_angle = self._game_state.prng.rand_double() * (launch_angle - angle) + angle
                     shot_speed = self._game_state.prng.rand_double() * (speed - speed2) + speed2
-                bullets.append(Bullet(launch_pos, anim, sprite_idx_offset,
+                bullets.append(Bullet(launch_pos, bullet_type, sprite_idx_offset,
                                       bullet_angle, shot_speed,
                                       self.extended_bullet_attributes,
                                       flags, player, self._game_state))
@@ -173,15 +175,14 @@ class Enemy(object):
         else:
             tx, ty, tw, th = 0., 0., 0., 0.
 
+        x, y = self.x, self.y
         max_x = tw / 2.
         max_y = th / 2.
-        min_x = -max_x
-        min_y = -max_y
 
-        if any((min_x > screen_width - self.x,
-                max_x < -self.x,
-                min_y > screen_height - self.y,
-                max_y < -self.y)):
+        if (max_x < x - screen_width
+            or max_x < -x
+            or max_y < y - screen_height
+            or max_y < -y):
             return False
         return True
 
--- a/pytouhou/game/game.py
+++ b/pytouhou/game/game.py
@@ -65,7 +65,7 @@ class Game(object):
         self.ecl_runner.run_iter()
 
         # 2. Filter out destroyed enemies
-        self.enemies[:] = (enemy for enemy in self.enemies if not enemy._removed)
+        self.enemies = [enemy for enemy in self.enemies if not enemy._removed]
 
         # 3. Let's play!
         for enemy in self.enemies:
@@ -92,10 +92,7 @@ class Game(object):
 
         # Filter out-of-scren bullets
         # TODO: was_visible thing
-        bullets = self.game_state.bullets
-        for bullet in tuple(bullets):
-            if not bullet.is_visible(384, 448):
-                bullets.remove(bullet)
+        self.game_state.bullets = [bullet for bullet in self.game_state.bullets if bullet.is_visible(384, 448)]
 
         # Disable boss mode if it is dead/it has timeout
         if self.game_state.boss and self.game_state.boss._removed:
--- a/pytouhou/opengl/gamerenderer.py
+++ b/pytouhou/opengl/gamerenderer.py
@@ -55,7 +55,7 @@ class GameRenderer(pyglet.window.Window)
         glEnableClientState(GL_VERTEX_ARRAY)
         glEnableClientState(GL_TEXTURE_COORD_ARRAY)
 
-        pyglet.clock.schedule_interval(self.update, 1./60)
+        pyglet.clock.schedule_interval(self.update, 1./120)
         pyglet.app.run()
 
 
--- a/pytouhou/utils/matrix.py
+++ b/pytouhou/utils/matrix.py
@@ -28,52 +28,60 @@ class Matrix(object):
 
 
     def flip(self):
-        self.data[0][:] = (-x for x in self.data[0])
+        data = self.data
+        a, b, c, d = data[0]
+        data[0] = [-a, -b, -c, -d]
 
 
     def scale(self, x, y, z):
         d1 = self.data
-        d1[0][:] = (a * x for a in d1[0])
-        d1[1][:] = (a * y for a in d1[1])
-        d1[2][:] = (a * z for a in d1[2])
+        d1[0] = [a * x for a in d1[0]]
+        d1[1] = [a * y for a in d1[1]]
+        d1[2] = [a * z for a in d1[2]]
 
 
     def scale2d(self, x, y):
-        d1 = self.data
-        d1[0][:] = (a * x for a in d1[0])
-        d1[1][:] = (a * y for a in d1[1])
+        data = self.data
+        d1a, d1b, d1c, d1d = data[0]
+        d2a, d2b, d2c, d2d = data[1]
+        data[0] = [d1a * x, d1b * x, d1c * x, d1d * x]
+        data[1] = [d2a * y, d2b * y, d2c * y, d2d * y]
 
 
     def translate(self, x, y, z):
-        d1 = self.data
-        a, b, c = (v * m for v, m in zip(d1[3][:3], (x, y, z)))
-        d1[0][:] = (v + a for v in d1[0])
-        d1[1][:] = (v + b for v in d1[1])
-        d1[2][:] = (v + c for v in d1[2])
+        data = self.data
+        a, b, c = data[3][:3]
+        a, b, c = a * x, b * y, c * z
+        d1a, d1b, d1c, d1d = data[0]
+        d2a, d2b, d2c, d2d = data[1]
+        d3a, d3b, d3c, d3d = data[2]
+        data[0] = [d1a + a, d1b + a, d1c + a, d1d + a]
+        data[1] = [d2a + b, d2b + b, d2c + b, d2d + b]
+        data[2] = [d3a + c, d3b + c, d3c + c, d3d + c]
 
 
     def rotate_x(self, angle):
         d1 = self.data
         cos_a = cos(angle)
         sin_a = sin(angle)
-        d1[1][:], d1[2][:] = ([cos_a * d1[1][i] - sin_a * d1[2][i] for i in range(4)],
-                              [sin_a * d1[1][i] + cos_a * d1[2][i] for i in range(4)])
+        d1[1], d1[2] = ([cos_a * d1[1][i] - sin_a * d1[2][i] for i in range(4)],
+                        [sin_a * d1[1][i] + cos_a * d1[2][i] for i in range(4)])
 
 
     def rotate_y(self, angle):
         d1 = self.data
         cos_a = cos(angle)
         sin_a = sin(angle)
-        d1[0][:], d1[2][:] = ([cos_a * d1[0][i] + sin_a * d1[2][i] for i in range(4)],
-                              [- sin_a * d1[0][i] + cos_a * d1[2][i] for i in range(4)])
+        d1[0], d1[2] = ([cos_a * d1[0][i] + sin_a * d1[2][i] for i in range(4)],
+                        [- sin_a * d1[0][i] + cos_a * d1[2][i] for i in range(4)])
 
 
     def rotate_z(self, angle):
         d1 = self.data
         cos_a = cos(angle)
         sin_a = sin(angle)
-        d1[0][:], d1[1][:] = ([cos_a * d1[0][i] - sin_a * d1[1][i] for i in range(4)],
-                              [sin_a * d1[0][i] + cos_a * d1[1][i] for i in range(4)])
+        d1[0], d1[1] = ([cos_a * d1[0][i] - sin_a * d1[1][i] for i in range(4)],
+                        [sin_a * d1[0][i] + cos_a * d1[1][i] for i in range(4)])
 
 
     @classmethod