home · contact · privacy
Fix FOV bug by respecting HexMap start indentation consequences.
authorChristian Heller <c.heller@plomlompom.de>
Tue, 30 Apr 2019 21:17:26 +0000 (23:17 +0200)
committerChristian Heller <c.heller@plomlompom.de>
Tue, 30 Apr 2019 21:17:26 +0000 (23:17 +0200)
new/plomrogue/mapping.py
new/plomrogue/things.py

index 33a8aa95f0978a17f743d919017d20adf3cf05ad..4c7658de4af83168481d24f3d16edd23a67f1813 100644 (file)
@@ -18,9 +18,10 @@ class YX(collections.namedtuple('YX', ('y', 'x'))):
 
 class Map:
 
-    def __init__(self, size=YX(0, 0), init_char = '?'):
+    def __init__(self, size=YX(0, 0), init_char = '?', start_indented=True):
         self.size = size
         self.terrain = init_char*self.size_i
+        self.start_indented = start_indented
 
     def __getitem__(self, yx):
         return self.terrain[self.get_position_index(yx)]
@@ -72,17 +73,20 @@ class MapGeometry():
                 directions += [name[5:]]
         return directions
 
-    def get_neighbors(self, pos, map_size):
+    def get_neighbors(self, pos, map_size, start_indented=True):
         neighbors = {}
         if not hasattr(self, 'neighbors_to'):
             self.neighbors_to = {}
         if not map_size in self.neighbors_to:
             self.neighbors_to[map_size] = {}
-        if pos in self.neighbors_to[map_size]:
-            return self.neighbors_to[map_size][pos]
+        if not start_indented in self.neighbors_to[map_size]:
+            self.neighbors_to[map_size][start_indented] = {}
+        if pos in self.neighbors_to[map_size][start_indented]:
+            return self.neighbors_to[map_size][start_indented][pos]
         for direction in self.get_directions():
-            neighbors[direction] = self.move(pos, direction, map_size)
-        self.neighbors_to[map_size][pos] = neighbors
+            neighbors[direction] = self.move(pos, direction, map_size,
+                                             start_indented)
+        self.neighbors_to[map_size][start_indented][pos] = neighbors
         return neighbors
 
     def undouble_coordinate(self, maps_size, coordinate):
@@ -98,7 +102,8 @@ class MapGeometry():
         return self.undouble_coordinate(maps_size, pos) - offset
 
     def get_view(self, maps_size, get_map, radius, view_offset):
-        m = Map(size=YX(radius*2+1, radius*2+1)
+        m = Map(size=YX(radius*2+1, radius*2+1),
+                start_indented=(view_offset.y % 2 == 0))
         for pos in m:
             seen_pos = self.correct_double_coordinate(maps_size, (0,0),
                                                       pos + view_offset)
@@ -108,9 +113,6 @@ class MapGeometry():
             m[pos] = seen_map[seen_pos[1]]
         return m
 
-    def get_correcting_map_size(self, size, offset):
-        return size
-
     def correct_double_coordinate(self, map_size, big_yx, little_yx):
 
         def adapt_axis(axis):
@@ -123,10 +125,10 @@ class MapGeometry():
         new_big_x, new_little_x = adapt_axis(1)
         return YX(new_big_y, new_big_x), YX(new_little_y, new_little_x)
 
-    def move(self, start_pos, direction, map_size):
+    def move(self, start_pos, direction, map_size, start_indented=True):
         mover = getattr(self, 'move_' + direction)
         big_yx, little_yx = start_pos
-        uncorrected_target = mover(little_yx)
+        uncorrected_target = mover(little_yx, start_indented)
         return self.correct_double_coordinate(map_size, big_yx,
                                               uncorrected_target)
 
@@ -134,20 +136,20 @@ class MapGeometry():
 
 class MapGeometryWithLeftRightMoves(MapGeometry):
 
-    def move_LEFT(self, start_pos):
+    def move_LEFT(self, start_pos, _):
         return YX(start_pos.y, start_pos.x - 1)
 
-    def move_RIGHT(self, start_pos):
+    def move_RIGHT(self, start_pos, _):
         return YX(start_pos.y, start_pos.x + 1)
 
 
 
 class MapGeometrySquare(MapGeometryWithLeftRightMoves):
 
-    def move_UP(self, start_pos):
+    def move_UP(self, start_pos, _):
         return YX(start_pos.y - 1, start_pos.x)
 
-    def move_DOWN(self, start_pos):
+    def move_DOWN(self, start_pos, _):
         return YX(start_pos.y + 1, start_pos.x)
 
 
@@ -158,37 +160,39 @@ class MapGeometryHex(MapGeometryWithLeftRightMoves):
         super().__init__(*args, **kwargs)
         self.fov_map_type = FovMapHex
 
-    def move_UPLEFT(self, start_pos):
-        if start_pos.y % 2 == 1:
+    def move_UPLEFT(self, start_pos, start_indented):
+        if start_pos.y % 2 == start_indented:
             return YX(start_pos.y - 1, start_pos.x - 1)
         else:
             return YX(start_pos.y - 1, start_pos.x)
 
-    def move_UPRIGHT(self, start_pos):
-        if start_pos.y % 2 == 1:
+    def move_UPRIGHT(self, start_pos, start_indented):
+        if start_pos.y % 2 == start_indented:
             return YX(start_pos.y - 1, start_pos.x)
         else:
             return YX(start_pos.y - 1, start_pos.x + 1)
 
-    def move_DOWNLEFT(self, start_pos):
-        if start_pos.y % 2 == 1:
+    def move_DOWNLEFT(self, start_pos, start_indented):
+        if start_pos.y % 2 == start_indented:
              return YX(start_pos.y + 1, start_pos.x - 1)
         else:
                return YX(start_pos.y + 1, start_pos.x)
 
-    def move_DOWNRIGHT(self, start_pos):
-        if start_pos.y % 2 == 1:
+    def move_DOWNRIGHT(self, start_pos, start_indented):
+        if start_pos.y % 2 == start_indented:
             return YX(start_pos.y + 1, start_pos.x)
         else:
             return YX(start_pos.y + 1, start_pos.x + 1)
 
 
+
 class FovMap(Map):
 
     def __init__(self, source_map, center):
         self.source_map = source_map
         self.size = self.source_map.size
         self.fov_radius = (self.size.y / 2) - 0.5
+        self.start_indented = source_map.start_indented
         self.terrain = '?' * self.size_i
         self[center] = '.'
         self.shadow_cones = []
@@ -264,7 +268,7 @@ class FovMap(Map):
     def basic_circle_out_move(self, pos, direction):
         """Move position pos into direction. Return whether still in map."""
         mover = getattr(self.geometry, 'move_' + direction)
-        pos = mover(pos)
+        pos = mover(pos, self.start_indented)
         if pos.y < 0 or pos.x < 0 or \
             pos.y >= self.size.y or pos.x >= self.size.x:
             return pos, False
index aded05c60d777918d975023968c8dd1959111d56..0e47cc0b6cd6df06fb4f83e6df8b5b856a232456 100644 (file)
@@ -113,27 +113,29 @@ class ThingAnimate(Thing):
 
     def move_on_dijkstra_map(self, own_pos, targets):
         visible_map = self.get_visible_map()
-        dijkstra_map = Map(visible_map.size)
+        dijkstra_map = Map(visible_map.size,
+                           start_indented=visible_map.start_indented)
         n_max = 256
         dijkstra_map.terrain = [n_max for i in range(dijkstra_map.size_i)]
         for target in targets:
             dijkstra_map[target] = 0
         shrunk = True
+        get_neighbors = self.game.map_geometry.get_neighbors
         while shrunk:
             shrunk = False
             for pos in dijkstra_map:
                 if visible_map[pos] != '.':
                     continue
-                neighbors = self.game.map_geometry.get_neighbors((YX(0,0), pos),
-                                                                 dijkstra_map.size)
+                neighbors = get_neighbors((YX(0,0), pos), dijkstra_map.size,
+                                          dijkstra_map.start_indented)
                 for direction in neighbors:
                     big_yx, small_yx = neighbors[direction]
                     if big_yx == YX(0,0) and \
                        dijkstra_map[small_yx] < dijkstra_map[pos] - 1:
                         dijkstra_map[pos] = dijkstra_map[small_yx] + 1
                         shrunk = True
-        neighbors = self.game.map_geometry.get_neighbors((YX(0,0), own_pos),
-                                                         dijkstra_map.size)
+        get_neighbors((YX(0,0), own_pos), dijkstra_map.size,
+                      dijkstra_map.start_indented)
         n = n_max
         target_direction = None
         for direction in sorted(neighbors.keys()):
@@ -267,7 +269,7 @@ class ThingAnimate(Thing):
     def get_stencil(self):
         if self._stencil is not None:
             return self._stencil
-        m = Map(self.surroundings.size, ' ')
+        m = Map(self.surroundings.size, ' ', self.surroundings.start_indented)
         for pos in self.surroundings:
             if self.surroundings[pos] in {'.', '~'}:
                 m[pos] = '.'