changeset 20:6ebf9539c077

Handle more enemies types and movements
author Thibaut Girka <thib@sitedethib.com>
date Thu, 11 Aug 2011 12:13:48 +0200
parents ca7886296d4a
children bf225780973f
files pytouhou/formats/ecl.py pytouhou/formats/std.py pytouhou/game/enemymanager.py pytouhou/utils/interpolator.py
diffstat 4 files changed, 29 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/pytouhou/formats/ecl.py
+++ b/pytouhou/formats/ecl.py
@@ -42,9 +42,7 @@ class ECL(object):
                 break
             sub, instr_type, size = unpack('<HHH', file.read(6))
             data = file.read(size - 8)
-            if instr_type == 0: # Normal enemy
-                args = unpack('<ffIhHHH', data)
-            elif instr_type == 2: # Mirrored enemy
+            if instr_type in (0, 2, 4, 6): # Enemy spawn
                 args = unpack('<ffIhHHH', data)
             else:
                 print('ECL: Warning: unknown opcode %d (%r)' % (instr_type, data)) #TODO
--- a/pytouhou/formats/std.py
+++ b/pytouhou/formats/std.py
@@ -86,7 +86,7 @@ class Stage(object):
             elif message_type == 1: # Color
                 args = unpack('<BBBBff', data)
             elif message_type == 2: # ViewPos2
-                args = unpack('<Iff', data)
+                args = unpack('<fff', data)
             elif message_type == 3:  # StartInterpolatingViewPos2
                 args = tuple(unpack('<III', data)[:1])
             elif message_type == 4: # StartInterpolatingFog
--- a/pytouhou/game/enemymanager.py
+++ b/pytouhou/game/enemymanager.py
@@ -2,8 +2,9 @@ from itertools import chain
 from io import BytesIO
 import os
 from struct import unpack, pack
+from pytouhou.utils.interpolator import Interpolator
 from pytouhou.game.sprite import Sprite
-from math import cos, sin
+from math import cos, sin, atan2
 
 
 class Enemy(object):
@@ -17,6 +18,7 @@ class Enemy(object):
         self.frame = 0
         self.sprite = None
 
+        self.interpolator = None #TODO
         self.angle = 0.
         self.speed = 0.
         self.rotation_speed = 0.
@@ -38,6 +40,10 @@ class Enemy(object):
                     else:
                         self.sprite = Sprite(self.anms[1], script_index)
                         self.anm = self.anms[1]
+                elif instr_type == 43: # set_pos
+                    self.x, self.y, z = unpack('<fff', args)
+                    self.interpolator = Interpolator((self.x, self.y)) #TODO: better interpolation
+                    self.interpolator.set_interpolation_start(self.frame, (self.x, self.y))
                 elif instr_type == 45: # set_angle_speed
                     self.angle, self.speed = unpack('<ff', args)
                 elif instr_type == 46: # set_angle
@@ -46,14 +52,31 @@ class Enemy(object):
                     self.speed, = unpack('<f', args)
                 elif instr_type == 48: # set_acceleration
                     self.acceleration, = unpack('<f', args)
+                elif instr_type == 51: # move_towards_player #TODO: main
+                    unknown, self.speed = unpack('<If', args) #TODO: unknown
+                    player_x, player_y = 192., 400.#TODO
+                    self.angle = atan2(player_y - self.y, player_x - self.x)
+                elif instr_type == 57:
+                    duration, x, y, z = unpack('<Ifff', args)
+                    self.interpolator.set_interpolation_end(self.frame + duration, (x, y))
         if self.sprite:
             self.sprite.update()
 
+        if self.interpolator:
+            self.interpolator.update(self.frame)
+            x, y = self.interpolator.values
+            dx, dy = x - self.x, y - self.y
+            #TODO: animations
+            if abs(dx) > abs(dy):
+                pass #TODO
+            else:
+                pass #TODO
+            self.x, self.y = x, y
         self.speed += self.acceleration #TODO: units? Execution order?
         self.angle += self.rotation_speed #TODO: units? Execution order?
 
         dx, dy = cos(self.angle) * self.speed, sin(self.angle) * self.speed
-        if self.type == 2:
+        if self.type & 2:
             self.x -= dx
         else:
             self.x += dx
@@ -95,7 +118,7 @@ class EnemyManager(object):
     def update(self, frame):
         if self.main and self.main[0][0] == frame:
             for sub, instr_type, args in self.main.pop(0)[1]:
-                if instr_type in (0, 2): # Normal/mirrored enemy
+                if instr_type in (0, 2, 4, 6): # Normal/mirrored enemy
                     x, y, z, life, unknown1, unknown2, unknown3 = args
                     self.enemies.append(Enemy((x, y), life, instr_type, self.subs[sub], self.anims))
 
--- a/pytouhou/utils/interpolator.py
+++ b/pytouhou/utils/interpolator.py
@@ -34,3 +34,4 @@ class Interpolator(object):
             truc = float(frame - self.start_frame) / float(self.end_frame - self.start_frame)
             self.values = tuple(start_value + truc * (end_value - start_value)
                                 for (start_value, end_value) in zip(self.start_values, self.end_values))
+