Enemies appear
authorNeil <neil@dip.sun.ac.za>
Sat, 5 Mar 2016 19:40:04 +0000 (21:40 +0200)
committerNeil <neil@dip.sun.ac.za>
Sat, 5 Mar 2016 19:41:12 +0000 (21:41 +0200)
koperkapel/gamelib/enemy_generator.py
koperkapel/gamelib/enemy_roach.py [new file with mode: 0644]
koperkapel/gamelib/level.py
koperkapel/loaders/levelloader.py
koperkapel/roaches.py
koperkapel/scenes/level.py

index 3003064c8ae4a6f9e6b11bea7499e3c4305b70a3..1329660b1881140768f557e2912c5e0305a018ee 100644 (file)
@@ -4,17 +4,21 @@ import os
 from pgzero.actor import Actor
 from pgzero.clock import each_tick
 
+from .enemy_roach import get_enemy_roach
+
 class EnemyGenerator(Actor):
     """Generators are currently invisble, but we want the update hook."""
 
-    def __init__(self, info):
+    def __init__(self, info, level):
         self.gen_pos = info['pos']
+        self.level = level
         self.enemy_type = info['type']
         self.rate = info['rate']
         self.max_enemies = info['max']
         self._time_since_last_update = 0
         self.paused = False
         each_tick(self.update)
+        self._made_enemies = []
         super().__init__(os.path.join('weapons', 'blank'))
 
     def update(self, dt):
@@ -22,8 +26,18 @@ class EnemyGenerator(Actor):
             return
         self._time_since_last_update += dt
         if self._time_since_last_update > self.rate:
-            print('A horrible monster (%s) appears' % self.enemy_type, self.gen_pos)
-            self._time_since_last_update = 0
+            if len(self._made_enemies) < self.max_enemies:
+                self._make_enemy()
+
+    def _make_enemy(self):
+        if self.enemy_type == 'roach':
+            roach = get_enemy_roach()
+            self._made_enemies.append(roach)
+            self.level.add_enemy(roach, *self.gen_pos)
+
+    def killed(self, enemy):
+        if enemy in self._made_enemies:
+            self._made_enemies.remove(enemy)
 
     def pause(self):
         self.paused = True
diff --git a/koperkapel/gamelib/enemy_roach.py b/koperkapel/gamelib/enemy_roach.py
new file mode 100644 (file)
index 0000000..95b3e19
--- /dev/null
@@ -0,0 +1,11 @@
+# Roach utilities
+
+from ..roaches import t32_roaches, WorldRoach
+
+
+def get_enemy_roach():
+    # red
+    roach = t32_roaches.assemble(WorldRoach(), color=(255, 0, 0, 255))
+    roach.anchor = (0, 0)
+    roach.game_pos = (0, 0)
+    return roach
index bcc319a2886d2f5e530d30ff70be6f7f50478a09..3df9fe03598dc598db85666491d342370c7b2eee 100644 (file)
@@ -1,5 +1,7 @@
 """ Class holding the level info """
 
+import random
+
 
 class Level(object):
 
@@ -84,3 +86,30 @@ class Level(object):
 
     def get_exit_level(self):
         return self.exit["next level"]
+
+    def is_on_enemy(self, x, y):
+        for enemy in self.enemies:
+            if (x, y) == enemy.game_pos:
+                return True
+        return False
+
+    def get_enemy(self, x, y):
+        for enemy in self.enemies:
+            if (x, y) == enemy.game_pos:
+                return enemy
+        return None
+
+    def add_enemy(self, enemy, x, y):
+        """Add an enemy to an empty floor space near x, y"""
+        added = False
+        while not added:
+            if self.can_walk(x, y, 'floor'):
+                if not self.is_on_friend(x, y):
+                    if not self.is_on_enemy(x, y):
+                        added = True
+                        enemy.game_pos = (x, y)
+                        self.enemies.append(enemy)
+                        added = True
+            x += random.randint(-1, 1)
+            y += random.randint(-1, 1)
+
index a775838dc54b1b02c18734ab69709d4a34c16230..14db3bee5419de099d785e50d87fbbc7db72783c 100644 (file)
@@ -73,7 +73,7 @@ class LevelLoader(ResourceLoader):
         for item in level_data['items']:
             self._level.items.append(get_item(item))
         for generator in level_data['enemy generators']:
-            enemy = EnemyGenerator(generator)
+            enemy = EnemyGenerator(generator, self._level)
             self._level.enemy_generators.append(enemy)
         return self._level
 
index 680d2a69b24b0183a70700cde72e68cfcaea458a..1d77563953442090efc97e766d62d0dd243569d2 100644 (file)
@@ -89,8 +89,9 @@ class RoachFactory:
         frame.blit(eyes, (0, 0))
         return frame
 
-    def assemble(self, roach_data, weapon=None):
-        color = roach_serum_color(roach_data)
+    def assemble(self, roach_data, color=None, weapon=None):
+        if not color:
+            color = roach_serum_color(roach_data)
         frames = []
         frames = [
             self.assemble_frame(i, color, roach_data, weapon)
index a6844663caf020b5ffdafb3d9ad6c470ab677e14..e5d102a265d9772b9095d3915166c1bbf479dceb 100644 (file)
@@ -146,7 +146,9 @@ class GameLevelScene(BaseLevelScene):
 
     def _can_move(self, x, y):
         if self._mode == 'walk':
-            return self._level.can_walk(x, y, self._level_layer)
+            if not self._level.is_on_enemy(x, y):
+                return self._level.can_walk(x, y, self._level_layer)
+            return False
         elif self._mode == 'fly':
             return self._level.can_fly(x, y, self._level_layer)
         elif self._mode == 'crawl':
@@ -198,11 +200,22 @@ class GameLevelScene(BaseLevelScene):
         for item in self._items:
             item.pos = self.calc_offset(
                 item.game_pos[0] * TILE_SIZE, item.game_pos[1] * TILE_SIZE)
+        self._check_enemies()
+        for enemy in self._enemies:
+            enemy.pos = self.calc_offset(
+                enemy.game_pos[0] * TILE_SIZE, enemy.game_pos[1] * TILE_SIZE)
         more = self._check_held_keys(dt)
         if more:
             events.extend(more)
         return events
 
+    def _check_enemies(self):
+        if len(self._level.enemies) != len(self._enemies):
+            # New nemy has spawned
+            for enemy in self._level.enemies:
+                if enemy not in self._enemies:
+                    self._enemies.add(enemy)
+
     def _check_held_keys(self, dt):
         for key in self._held_keys:
             self._last_key_down += dt