fixed moving rock animations for BD engine when on conveyor belt
authorHolger Schemel <holger.schemel@virtion.de>
Mon, 4 Nov 2024 19:43:17 +0000 (20:43 +0100)
committerHolger Schemel <holger.schemel@virtion.de>
Mon, 4 Nov 2024 19:43:19 +0000 (20:43 +0100)
src/game_bd/bd_cave.c
src/game_bd/bd_caveengine.c
src/game_bd/bd_caveengine.h

index e32c5b36c02ee22a350e5e40d2f254c3136341f7..63703d529915cfa38ad0504a97c0cb9d1c276a09 100644 (file)
@@ -1645,7 +1645,8 @@ void gd_drawcave_game(const GdCave *cave,
       }
 
       // draw special graphics if element is moving
-      if (dir_to == GD_MV_LEFT || dir_to == GD_MV_RIGHT)
+      if ((dir_to == GD_MV_LEFT || dir_to == GD_MV_RIGHT) &&
+          !moved_by_conveyor_dir(cave, x, y, dir_to))
       {
         if (actual == O_STONE || actual == O_STONE_F)
         {
index f66cce09791630396b8140680eb28203576dd33f..97ce3fe933f9445183e0280ea0aca022a7e43592 100644 (file)
@@ -552,6 +552,45 @@ static inline boolean moved_by_conveyor_bottom(const GdCave *cave, const int x,
   return has_property(get_dir(cave, x, y, dir), P_MOVED_BY_CONVEYOR_BOTTOM);
 }
 
+// returns true if element can be moved by conveyor belt (above or below)
+boolean moved_by_conveyor(const GdCave *cave, const int x, const int y)
+{
+  int element      = get(cave, x, y);
+  int element_up   = get_dir(cave, x, y, GD_MV_UP);
+  int element_down = get_dir(cave, x, y, GD_MV_DOWN);
+  boolean moved_by_conveyor_top    = has_property(element, P_MOVED_BY_CONVEYOR_TOP);
+  boolean moved_by_conveyor_bottom = has_property(element, P_MOVED_BY_CONVEYOR_BOTTOM);
+  boolean conveyor_up   = (element_up   == O_CONVEYOR_LEFT || element_up   == O_CONVEYOR_RIGHT);
+  boolean conveyor_down = (element_down == O_CONVEYOR_LEFT || element_down == O_CONVEYOR_RIGHT);
+
+  return (!cave->gravity_disabled && cave->conveyor_belts_active &&
+          ((cave->gravity == GD_MV_DOWN && ((conveyor_down && moved_by_conveyor_top) ||
+                                            (conveyor_up   && moved_by_conveyor_bottom))) ||
+           (cave->gravity == GD_MV_UP   && ((conveyor_up   && moved_by_conveyor_top) ||
+                                            (conveyor_down && moved_by_conveyor_bottom)))));
+}
+
+// returns true if moving element is moved by conveyor belt in same direction (above or below)
+boolean moved_by_conveyor_dir(const GdCave *cave, const int x, const int y, const GdDirection dir)
+{
+  int element_dir = (cave->conveyor_belts_direction_changed ? opposite[dir] : dir);
+  int element      = get(cave, x, y);
+  int element_up   = get_dir(cave, x, y, GD_MV_UP);
+  int element_down = get_dir(cave, x, y, GD_MV_DOWN);
+  boolean moved_by_conveyor_top    = has_property(element, P_MOVED_BY_CONVEYOR_TOP);
+  boolean moved_by_conveyor_bottom = has_property(element, P_MOVED_BY_CONVEYOR_BOTTOM);
+  boolean conveyor_up   = ((element_up   == O_CONVEYOR_LEFT  && element_dir == GD_MV_RIGHT) ||
+                           (element_up   == O_CONVEYOR_RIGHT && element_dir == GD_MV_LEFT));
+  boolean conveyor_down = ((element_down == O_CONVEYOR_LEFT  && element_dir == GD_MV_LEFT) ||
+                           (element_down == O_CONVEYOR_RIGHT && element_dir == GD_MV_RIGHT));
+
+  return (!cave->gravity_disabled && cave->conveyor_belts_active &&
+          ((cave->gravity == GD_MV_DOWN && ((conveyor_down && moved_by_conveyor_top) ||
+                                            (conveyor_up   && moved_by_conveyor_bottom))) ||
+           (cave->gravity == GD_MV_UP   && ((conveyor_up   && moved_by_conveyor_top) ||
+                                            (conveyor_down && moved_by_conveyor_bottom)))));
+}
+
 // returns true if the given element is scanned
 boolean is_scanned_element(GdElement e)
 {
index c1e91bf3de9cf5baaebeeabed265fd8d8e622410..6f49a0ee3590892d23e8d4c8838599c1ae6c38b8 100644 (file)
@@ -27,6 +27,8 @@ GdElement non_scanned_pair(GdElement of_what);
 boolean is_player(const GdCave *cave, const int x, const int y);
 boolean is_player_stirring(const GdCave *cave, const int x, const int y);
 boolean can_be_pushed(const GdCave *cave, const int x, const int y, const GdDirection dir);
+boolean moved_by_conveyor(const GdCave *cave, const int x, const int y);
+boolean moved_by_conveyor_dir(const GdCave *cave, const int x, const int y, const GdDirection dir);
 GdDirection gd_direction_from_keypress(boolean up, boolean down, boolean left, boolean right);
 void gd_cave_iterate(GdCave *cave, GdDirection player_move, boolean player_fire, boolean suicide);
 void set_initial_cave_speed(GdCave *cave);