X-Git-Url: https://git.artsoft.org/?a=blobdiff_plain;f=src%2Fgame.c;h=25e138060311fa14b1ebca089bd154b2c7dc68db;hb=fbe0eaa3234fb6a69a65136f764922e24943501d;hp=0f4ce58eb9455bbb3bcd9d0231a783da8a3ad5dd;hpb=ecba6429f85a26d8b7f350ae99bdb3dbef6d6f32;p=rocksndiamonds.git diff --git a/src/game.c b/src/game.c index 0f4ce58e..25e13806 100644 --- a/src/game.c +++ b/src/game.c @@ -14,9 +14,9 @@ #include "libgame/libgame.h" #include "game.h" +#include "init.h" #include "tools.h" #include "screens.h" -#include "init.h" #include "files.h" #include "tape.h" #include "network.h" @@ -500,9 +500,13 @@ static void InitGameEngine() { int i; + /* set game engine from tape file when re-playing, else from level file */ game.engine_version = (tape.playing ? tape.engine_version : level.game_version); + /* dynamically adjust element properties according to game engine version */ + InitElementPropertiesEngine(game.engine_version); + #if 0 printf("level %d: level version == %06d\n", level_nr, level.game_version); printf(" tape version == %06d [%s] [file: %06d]\n", @@ -520,6 +524,7 @@ static void InitGameEngine() game.initial_move_delay_value = (level.double_speed ? MOVE_DELAY_HIGH_SPEED : MOVE_DELAY_NORMAL_SPEED); +#if 0 /* dynamically adjust element properties according to game engine version */ { static int ep_em_slippery_wall[] = @@ -543,6 +548,7 @@ static void InitGameEngine() (level.em_slippery_gems && game.engine_version > VERSION_IDENT(2,0,1))); } +#endif /* initialize changing elements information */ for (i=0; iactive) return; -#if 1 /* remove accessible field at the player's position */ Feld[jx][jy] = EL_EMPTY; -#else - if (IS_PFORTE(Feld[jx][jy])) - Feld[jx][jy] = EL_EMPTY; -#endif /* deactivate shield (else Bang()/Explode() would not work right) */ player->shield_normal_time_left = 0; @@ -5753,17 +5701,57 @@ void RemoveHero(struct PlayerInfo *player) ExitY = ZY = jy; } -#if 0 /* checkDiagonalPushing() ----------------------------------------------------------------------------- check if diagonal input device direction results in pushing of object + (by checking if the alternative direction is walkable, diggable, ...) */ -static boolean checkDiagonalPushing(int x, int y, int real_dx, int real_dy) +static boolean checkDiagonalPushing(struct PlayerInfo *player, + int x, int y, int real_dx, int real_dy) { -} +#if 1 + int jx, jy, dx, dy, xx, yy; + + if (real_dx == 0 || real_dy == 0) /* no diagonal direction => push */ + return TRUE; + + /* diagonal direction: check alternative direction */ + jx = player->jx; + jy = player->jy; + dx = x - jx; + dy = y - jy; + xx = jx + (dx == 0 ? real_dx : 0); + yy = jy + (dy == 0 ? real_dy : 0); + + return (!IN_LEV_FIELD(xx, yy) || IS_SOLID(Feld[xx][yy])); +#else + + if (real_dx && real_dy) /* diagonal direction input => do check */ + { + /* diagonal direction: check alternative direction */ + int jx = player->jx, jy = player->jy; + int dx = x - jx, dy = y - jy; + int xx = jx + (dx == 0 ? real_dx : 0); + int yy = jy + (dy == 0 ? real_dy : 0); + + if (IN_LEV_FIELD(xx, yy)) + { + int element = Feld[xx][yy]; + + if (game.engine_version < VERSION_IDENT(2,2,0)) + return IS_HISTORIC_SOLID(element); + else + return !(IS_WALKABLE(element) || + IS_DIGGABLE(element) || + IS_COLLECTIBLE(element)); + } + } + + return TRUE; /* no diagonal direction input => push object */ #endif +} /* DigField() @@ -5802,9 +5790,15 @@ int DigField(struct PlayerInfo *player, if (IS_MOVING(x, y) || IS_PLAYER(x, y)) return MF_NO_ACTION; - if (IS_TUBE(Feld[jx][jy])) +#if 0 + if (IS_TUBE(Feld[jx][jy]) || IS_TUBE(Back[jx][jy])) +#else + if (IS_TUBE(Feld[jx][jy]) || + (IS_TUBE(Back[jx][jy]) && game.engine_version >= VERSION_IDENT(2,2,0))) +#endif { int i = 0; + int tube_element = (IS_TUBE(Feld[jx][jy]) ? Feld[jx][jy] : Back[jx][jy]); int tube_leave_directions[][2] = { { EL_TUBE_ANY, MV_LEFT | MV_RIGHT | MV_UP | MV_DOWN }, @@ -5821,7 +5815,7 @@ int DigField(struct PlayerInfo *player, { -1, MV_LEFT | MV_RIGHT | MV_UP | MV_DOWN } }; - while (tube_leave_directions[i][0] != Feld[jx][jy]) + while (tube_leave_directions[i][0] != tube_element) { i++; if (tube_leave_directions[i][0] == -1) /* should not happen */ @@ -6112,11 +6106,17 @@ int DigField(struct PlayerInfo *player, if (!IN_LEV_FIELD(x+dx, y+dy) || !IS_FREE(x+dx, y+dy)) return MF_NO_ACTION; +#if 1 + if (!checkDiagonalPushing(player, x, y, real_dx, real_dy)) + return MF_NO_ACTION; +#else if (real_dy) { - if (IN_LEV_FIELD(jx, jy+real_dy) && !IS_SOLID(Feld[jx][jy+real_dy])) + if (IN_LEV_FIELD(jx, jy+real_dy) && + !IS_HISTORIC_SOLID(Feld[jx][jy+real_dy])) return MF_NO_ACTION; } +#endif if (player->push_delay == 0) player->push_delay = FrameCounter; @@ -6358,16 +6358,23 @@ int DigField(struct PlayerInfo *player, || !IS_SB_ELEMENT(element)))) return MF_NO_ACTION; +#if 1 + if (!checkDiagonalPushing(player, x, y, real_dx, real_dy)) + return MF_NO_ACTION; +#else if (dx && real_dy) { - if (IN_LEV_FIELD(jx, jy+real_dy) && !IS_SOLID(Feld[jx][jy+real_dy])) + if (IN_LEV_FIELD(jx, jy+real_dy) && + !IS_HISTORIC_SOLID(Feld[jx][jy+real_dy])) return MF_NO_ACTION; } else if (dy && real_dx) { - if (IN_LEV_FIELD(jx+real_dx, jy) && !IS_SOLID(Feld[jx+real_dx][jy])) + if (IN_LEV_FIELD(jx+real_dx, jy) && + !IS_HISTORIC_SOLID(Feld[jx+real_dx][jy])) return MF_NO_ACTION; } +#endif if (player->push_delay == 0) player->push_delay = FrameCounter; @@ -6467,16 +6474,23 @@ int DigField(struct PlayerInfo *player, if (!IN_LEV_FIELD(x+dx, y+dy) || !IS_FREE(x+dx, y+dy)) return MF_NO_ACTION; +#if 1 + if (!checkDiagonalPushing(player, x, y, real_dx, real_dy)) + return MF_NO_ACTION; +#else if (dx && real_dy) { - if (IN_LEV_FIELD(jx, jy+real_dy) && !IS_SOLID(Feld[jx][jy+real_dy])) + if (IN_LEV_FIELD(jx, jy+real_dy) && + !IS_HISTORIC_SOLID(Feld[jx][jy+real_dy])) return MF_NO_ACTION; } else if (dy && real_dx) { - if (IN_LEV_FIELD(jx+real_dx, jy) && !IS_SOLID(Feld[jx+real_dx][jy])) + if (IN_LEV_FIELD(jx+real_dx, jy) && + !IS_HISTORIC_SOLID(Feld[jx+real_dx][jy])) return MF_NO_ACTION; } +#endif if (player->push_delay == 0) player->push_delay = FrameCounter; @@ -6569,6 +6583,11 @@ boolean PlaceBomb(struct PlayerInfo *player) IS_ACTIVE_BOMB(element) || element == EL_EXPLOSION) return FALSE; +#if 0 + if (element != EL_EMPTY) + return FALSE; +#endif + if (element != EL_EMPTY) { #if 0