(s)==SND_TYGER || (s)==SND_VOYAGER || \
(s)==SND_TWILIGHT)
-/* score for elements */
-#define SC_EDELSTEIN 0
-#define SC_DIAMANT 1
-#define SC_KAEFER 2
-#define SC_FLIEGER 3
-#define SC_MAMPFER 4
-#define SC_ROBOT 5
-#define SC_PACMAN 6
-#define SC_KOKOSNUSS 7
-#define SC_DYNAMIT 8
-#define SC_SCHLUESSEL 9
-#define SC_ZEITBONUS 10
+/* values for player movement speed (which is in fact a delay value) */
+#define MOVE_DELAY_NORMAL_SPEED 8
+#define MOVE_DELAY_HIGH_SPEED 4
+
+#define DOUBLE_MOVE_DELAY(x) (x = (x <= MOVE_DELAY_HIGH_SPEED ? x * 2 : x))
+#define HALVE_MOVE_DELAY(x) (x = (x >= MOVE_DELAY_HIGH_SPEED ? x / 2 : x))
+#define DOUBLE_PLAYER_SPEED(p) (HALVE_MOVE_DELAY((p)->move_delay_value))
+#define HALVE_PLAYER_SPEED(p) (DOUBLE_MOVE_DELAY((p)->move_delay_value))
/* game button identifiers */
#define GAME_CTRL_ID_STOP 0
#define NUM_GAME_BUTTONS 6
/* forward declaration for internal use */
+static void CheckGravityMovement(struct PlayerInfo *);
+
static void MapGameButtons();
static void HandleGameButtons(struct GadgetInfo *);
player->present = TRUE;
- /*
- if (!network_playing || player->connected)
- */
-
if (!options.network || player->connected)
{
player->active = TRUE;
player->programmed_action = 0;
player->score = 0;
- player->gems_still_needed = level.edelsteine;
+ player->gems_still_needed = level.gems_needed;
player->sokobanfields_still_needed = 0;
player->lights_still_needed = 0;
player->friends_still_needed = 0;
player->move_delay = 0;
player->last_move_dir = MV_NO_MOVING;
- player->move_speed = (level.double_speed ? 4 : 8);
- player->snapped = FALSE;
+ player->move_delay_value =
+ (level.double_speed ? MOVE_DELAY_HIGH_SPEED : MOVE_DELAY_NORMAL_SPEED);
- player->gone = FALSE;
+ player->snapped = FALSE;
player->last_jx = player->last_jy = 0;
player->jx = player->jy = 0;
ZX = ZY = -1;
- MampferNr = 0;
+ game.yam_content_nr = 0;
FrameCounter = 0;
TimeFrames = 0;
TimePlayed = 0;
ScreenMovPos = 0;
ScreenGfxPos = 0;
- /*
- MoveSpeed = (level.double_speed ? 4 : 8);
- ScrollStepSize = TILEX / MoveSpeed;
- */
-
- ScrollStepSize = 0;
+ ScrollStepSize = 0; /* will be correctly initialized by ScrollScreen() */
AllPlayersGone = FALSE;
- SiebAktiv = FALSE;
- SiebCount = 0;
+ game.magic_wall_active = FALSE;
+ game.magic_wall_time_left = 0;
for (i=0; i<MAX_NUM_AMOEBA; i++)
AmoebaCnt[i] = AmoebaCnt2[i] = 0;
}
}
- game_emulation = (emulate_bd ? EMU_BOULDERDASH :
+ game.emulation = (emulate_bd ? EMU_BOULDERDASH :
emulate_sb ? EMU_SOKOBAN :
emulate_sp ? EMU_SUPAPLEX : EMU_NONE);
- /* determine border element for this level */
- SetBorderElement();
-
if (BorderElement == EL_LEERRAUM)
{
SBX_Left = 0;
DrawAllPlayers();
FadeToFront();
- XCopyArea(display, pix[PIX_DOOR], pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX5, DOOR_GFX_PAGEY1, DXSIZE, DYSIZE,
- DOOR_GFX_PAGEX1, DOOR_GFX_PAGEY1);
- DrawTextExt(pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX1 + XX_LEVEL, DOOR_GFX_PAGEY1 + YY_LEVEL,
- int2str(level_nr, 2), FS_SMALL, FC_YELLOW);
- DrawTextExt(pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX1 + XX_EMERALDS, DOOR_GFX_PAGEY1 + YY_EMERALDS,
- int2str(local_player->gems_still_needed,3), FS_SMALL, FC_YELLOW);
- DrawTextExt(pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX1 + XX_DYNAMITE, DOOR_GFX_PAGEY1 + YY_DYNAMITE,
- int2str(local_player->dynamite, 3), FS_SMALL, FC_YELLOW);
- DrawTextExt(pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX1 + XX_SCORE, DOOR_GFX_PAGEY1 + YY_SCORE,
- int2str(local_player->score, 5), FS_SMALL, FC_YELLOW);
- DrawTextExt(pix[PIX_DB_DOOR], gc,
- DOOR_GFX_PAGEX1 + XX_TIME, DOOR_GFX_PAGEY1 + YY_TIME,
- int2str(TimeLeft, 3), FS_SMALL, FC_YELLOW);
+#if 1
+ if (setup.soft_scrolling)
+ XCopyArea(display, fieldbuffer, backbuffer, gc,
+ FX, FY, SXSIZE, SYSIZE, SX, SY);
+
+ redraw_mask |= REDRAW_FROM_BACKBUFFER;
+
+#endif
+
+
+ /* copy default game door content to main double buffer */
+ XCopyArea(display, pix[PIX_DOOR], drawto, gc,
+ DOOR_GFX_PAGEX5, DOOR_GFX_PAGEY1, DXSIZE, DYSIZE, DX, DY);
+
+ if (level_nr < 100)
+ DrawText(DX + XX_LEVEL, DY + YY_LEVEL,
+ int2str(level_nr, 2), FS_SMALL, FC_YELLOW);
+ else
+ DrawText(DX + XX_LEVEL - 1, DY + YY_LEVEL + 1,
+ int2str(level_nr, 3), FS_SMALL, FC_SPECIAL3);
+
+ DrawText(DX + XX_EMERALDS, DY + YY_EMERALDS,
+ int2str(local_player->gems_still_needed,3), FS_SMALL, FC_YELLOW);
+ DrawText(DX + XX_DYNAMITE, DY + YY_DYNAMITE,
+ int2str(local_player->dynamite, 3), FS_SMALL, FC_YELLOW);
+ DrawText(DX + XX_SCORE, DY + YY_SCORE,
+ int2str(local_player->score, 5), FS_SMALL, FC_YELLOW);
+ DrawText(DX + XX_TIME, DY + YY_TIME,
+ int2str(TimeLeft, 3), FS_SMALL, FC_YELLOW);
-#if 0
- DrawGameButton(BUTTON_GAME_STOP);
- DrawGameButton(BUTTON_GAME_PAUSE);
- DrawGameButton(BUTTON_GAME_PLAY);
- DrawSoundDisplay(BUTTON_SOUND_MUSIC | (setup.sound_music ? BUTTON_ON : 0));
- DrawSoundDisplay(BUTTON_SOUND_LOOPS | (setup.sound_loops ? BUTTON_ON : 0));
- DrawSoundDisplay(BUTTON_SOUND_SIMPLE | (setup.sound_simple ? BUTTON_ON : 0));
-#else
UnmapGameButtons();
game_gadget[SOUND_CTRL_ID_MUSIC]->checked = setup.sound_music;
game_gadget[SOUND_CTRL_ID_LOOPS]->checked = setup.sound_loops;
game_gadget[SOUND_CTRL_ID_SIMPLE]->checked = setup.sound_simple;
MapGameButtons();
MapTapeButtons();
-#endif
+ /* copy actual game door content to door double buffer for OpenDoor() */
XCopyArea(display, drawto, pix[PIX_DB_DOOR], gc,
- DX + GAME_CONTROL_XPOS, DY + GAME_CONTROL_YPOS,
- GAME_CONTROL_XSIZE, 2 * GAME_CONTROL_YSIZE,
- DOOR_GFX_PAGEX1 + GAME_CONTROL_XPOS,
- DOOR_GFX_PAGEY1 + GAME_CONTROL_YPOS);
-
-
+ DX, DY, DXSIZE, DYSIZE, DOOR_GFX_PAGEX1, DOOR_GFX_PAGEY1);
OpenDoor(DOOR_OPEN_ALL);
if (options.verbose)
{
for (i=0; i<4; i++)
- printf("Spieler %d %saktiv.\n",
- i+1, (stored_player[i].active ? "" : "nicht "));
+ printf("Player %d %sactive.\n",
+ i + 1, (stored_player[i].active ? "" : "not "));
}
}
phase = 7 - phase;
}
- if (game_emulation == EMU_SUPAPLEX)
+ if (game.emulation == EMU_SUPAPLEX)
DrawGraphic(sx, sy, GFX_SP_DISK_RED);
else if (Store[x][y])
DrawGraphicThruMask(sx, sy, graphic + phase);
break;
}
- if (game_emulation == EMU_SUPAPLEX)
+ if (game.emulation == EMU_SUPAPLEX)
Store[x][y] = EL_LEERRAUM;
}
else if (center_element == EL_MAULWURF)
else if (center_element == EL_SP_ELECTRON)
Store[x][y] = EL_SP_INFOTRON;
else if (center_element == EL_MAMPFER)
- Store[x][y] = level.mampfer_inhalt[MampferNr][x-ex+1][y-ey+1];
+ Store[x][y] = level.yam_content[game.yam_content_nr][x-ex+1][y-ey+1];
else if (center_element == EL_AMOEBA2DIAM)
- Store[x][y] = level.amoebe_inhalt;
+ Store[x][y] = level.amoeba_content;
else if (element == EL_ERZ_EDEL)
Store[x][y] = EL_EDELSTEIN;
else if (element == EL_ERZ_DIAM)
}
if (center_element == EL_MAMPFER)
- MampferNr = (MampferNr + 1) % MampferMax;
+ game.yam_content_nr = (game.yam_content_nr + 1) % level.num_yam_contents;
return;
}
{
int graphic = GFX_EXPLOSION;
- if (game_emulation == EMU_SUPAPLEX)
+ if (game.emulation == EMU_SUPAPLEX)
graphic = (Store[x][y] == EL_SP_INFOTRON ?
GFX_SP_EXPLODE_INFOTRON :
GFX_SP_EXPLODE_EMPTY);
{
int element = Feld[x][y];
- if (game_emulation == EMU_SUPAPLEX)
+ if (game.emulation == EMU_SUPAPLEX)
PlaySoundLevel(x, y, SND_SP_BOOOM);
else
PlaySoundLevel(x, y, SND_ROAAAR);
if (Feld[x][y] == smashed)
Feld[x][y] = activated_magic_wall;
- SiebCount = level.dauer_sieb * FRAMES_PER_SECOND;
- SiebAktiv = TRUE;
+ game.magic_wall_time_left = level.time_magic_wall * FRAMES_PER_SECOND;
+ game.magic_wall_active = TRUE;
}
if (IS_PLAYER(x, y+1))
struct PlayerInfo *player = &stored_player[i];
int jx = player->jx, jy = player->jy;
- if (!player->active || player->gone)
+ if (!player->active)
continue;
if (attr_x == -1 || ABS(jx-x)+ABS(jy-y) < ABS(attr_x-x)+ABS(attr_y-y))
{
struct PlayerInfo *player = &stored_player[i];
- if (player->active && !player->gone &&
- player->Pushing && player->MovPos)
+ if (player->active && player->Pushing && player->MovPos)
{
int next_jx = player->jx + (player->jx - player->last_jx);
int next_jy = player->jy + (player->jy - player->last_jy);
if (left || right)
{
- if (left && right && game_emulation != EMU_BOULDERDASH)
+ if (left && right && game.emulation != EMU_BOULDERDASH)
left = !(right = RND(2));
InitMovingField(x, y, left ? MV_LEFT : MV_RIGHT);
else if (Store[x][y] == EL_SIEB_VOLL)
{
Store[x][y] = 0;
- element = Feld[newx][newy] = (SiebAktiv ? EL_SIEB_VOLL : EL_SIEB_TOT);
+ element = Feld[newx][newy] =
+ (game.magic_wall_active ? EL_SIEB_VOLL : EL_SIEB_TOT);
}
else if (Store[x][y] == EL_SIEB_LEER)
{
Store[x][y] = Store2[x][y] = 0;
- Feld[x][y] = (SiebAktiv ? EL_SIEB_LEER : EL_SIEB_TOT);
+ Feld[x][y] = (game.magic_wall_active ? EL_SIEB_LEER : EL_SIEB_TOT);
}
else if (Store[x][y] == EL_SIEB2_VOLL)
{
Store[x][y] = 0;
- element = Feld[newx][newy] = (SiebAktiv ? EL_SIEB2_VOLL : EL_SIEB2_TOT);
+ element = Feld[newx][newy] =
+ (game.magic_wall_active ? EL_SIEB2_VOLL : EL_SIEB2_TOT);
}
else if (Store[x][y] == EL_SIEB2_LEER)
{
Store[x][y] = Store2[x][y] = 0;
- Feld[x][y] = (SiebAktiv ? EL_SIEB2_LEER : EL_SIEB2_TOT);
+ Feld[x][y] = (game.magic_wall_active ? EL_SIEB2_LEER : EL_SIEB2_TOT);
}
else if (Store[x][y] == EL_SALZSAEURE)
{
{ 0, +1 }
};
- if (!level.tempo_amoebe)
+ if (!level.amoeba_speed)
{
Feld[ax][ay] = EL_AMOEBE_TOT;
DrawLevelField(ax, ay);
}
if (!MovDelay[ax][ay]) /* start making new amoeba field */
- MovDelay[ax][ay] = RND(FRAMES_PER_SECOND * 25 / (1 + level.tempo_amoebe));
+ MovDelay[ax][ay] = RND(FRAMES_PER_SECOND * 25 / (1 + level.amoeba_speed));
if (MovDelay[ax][ay]) /* wait some time before making new amoeba */
{
if (newax == ax && neway == ay) /* amoeba cannot grow */
{
- if (i == 4 && (!waiting_for_player || game_emulation == EMU_BOULDERDASH))
+ if (i == 4 && (!waiting_for_player || game.emulation == EMU_BOULDERDASH))
{
Feld[ax][ay] = EL_AMOEBE_TOT;
DrawLevelField(ax, ay);
if (element == EL_AMOEBE_VOLL)
AmoebeUmwandeln(ax, ay);
else if (element == EL_AMOEBE_BD)
- AmoebeUmwandelnBD(ax, ay, level.amoebe_inhalt);
+ AmoebeUmwandelnBD(ax, ay, level.amoeba_content);
}
}
return;
void Ablenk(int x, int y)
{
if (!MovDelay[x][y]) /* next animation frame */
- MovDelay[x][y] = level.dauer_ablenk * FRAMES_PER_SECOND;
+ MovDelay[x][y] = level.time_wheel * FRAMES_PER_SECOND;
if (MovDelay[x][y]) /* wait some time before next frame */
{
stored_player_action[player->index_nr] = 0;
num_stored_actions++;
- if (!player->active || player->gone || tape.pausing)
+ if (!player->active || tape.pausing)
return;
if (player_action)
player_action &= JOY_BUTTON;
stored_player_action[player->index_nr] = player_action;
-
-#if 0
- /* this allows cycled sequences of PlayerActions() */
- if (num_stored_actions >= MAX_PLAYERS)
- {
- TapeRecordAction(stored_player_action);
- num_stored_actions = 0;
- }
-#endif
-
}
else if (tape.playing && snapped)
SnapField(player, 0, 0); /* stop snapping */
}
else
{
+ /* no actions for this player (no input at player's configured device) */
+
DigField(player, 0, 0, 0, 0, DF_NO_PUSH);
SnapField(player, 0, 0);
+ CheckGravityMovement(player);
- /*
- if (++player->frame_reset_delay > MoveSpeed)
- player->Frame = 0;
- */
-
- if (++player->frame_reset_delay > player->move_speed)
+ if (++player->frame_reset_delay > player->move_delay_value)
player->Frame = 0;
}
action_delay_value =
(tape.playing && tape.fast_forward ? FfwdFrameDelay : GameFrameDelay);
- /*
- if (tape.playing && tape.fast_forward)
- {
- char buf[100];
+ /* ---------- main game synchronization point ---------- */
- sprintf(buf, "FFWD: %ld ms", action_delay_value);
- print_debug(buf);
- }
- */
-
-
- /* main game synchronization point */
-
-
-
-
-#if 1
WaitUntilDelayReached(&action_delay, action_delay_value);
-#else
-
- while (!DelayReached(&action_delay, action_delay_value))
- {
- char buf[100];
-
- sprintf(buf, "%ld %ld %ld",
- Counter(), action_delay, action_delay_value);
- print_debug(buf);
- }
- print_debug("done");
-
-#endif
-
-
-
if (network_playing && !network_player_action_received)
{
}
}
-
- /*
- if (tape.pausing || (tape.playing && !TapePlayDelay()))
- return;
- else if (tape.recording)
- TapeRecordDelay();
- */
-
if (tape.pausing)
return;
int actual_player_action = stored_player[i].effective_action;
if (stored_player[i].programmed_action)
- {
- /* this is very bad and need to be fixed!!! */
- unsigned long move_delay = stored_player[i].move_delay;
-
- /*
- if (FrameReached(&move_delay, MoveSpeed))
- */
-
- if (FrameReached(&move_delay, stored_player[i].move_speed))
- {
- actual_player_action = stored_player[i].programmed_action;
- stored_player[i].programmed_action = 0;
- }
- }
+ actual_player_action = stored_player[i].programmed_action;
if (recorded_player_action)
actual_player_action = recorded_player_action[i];
ScrollScreen(NULL, SCROLL_GO_ON);
- /*
- if (tape.pausing || (tape.playing && !TapePlayDelay()))
- return;
- else if (tape.recording)
- TapeRecordDelay();
- */
-
-
-
-
#ifdef DEBUG
- /*
- if (TimeFrames == 0 && !local_player->gone)
+#if 0
+ if (TimeFrames == 0 && local_player->active)
{
extern unsigned int last_RND();
printf("DEBUG: %03d last RND was %d \t [state checksum is %d]\n",
- TimePlayed,
- last_RND(),
- getStateCheckSum(TimePlayed));
+ TimePlayed, last_RND(), getStateCheckSum(TimePlayed));
}
- */
#endif
-
-
+#endif
#ifdef DEBUG
- /*
+#if 0
if (GameFrameDelay >= 500)
printf("FrameCounter == %d\n", FrameCounter);
- */
#endif
-
-
+#endif
Blocked2Moving(x, y, &oldx, &oldy);
if (!IS_MOVING(oldx, oldy))
{
- printf("GameActions(): (BLOCKED=>MOVING) context corrupted!\n");
+ printf("GameActions(): (BLOCKED => MOVING) context corrupted!\n");
printf("GameActions(): BLOCKED: x = %d, y = %d\n", x, y);
printf("GameActions(): !MOVING: oldx = %d, oldy = %d\n", oldx, oldy);
printf("GameActions(): This should never happen!\n");
else if (element == EL_SP_TERMINAL_ACTIVE)
DrawGraphicAnimation(x, y, GFX2_SP_TERMINAL_ACTIVE, 7, 4, ANIM_NORMAL);
- if (SiebAktiv)
+ if (game.magic_wall_active)
{
boolean sieb = FALSE;
int jx = local_player->jx, jy = local_player->jy;
}
}
- if (SiebAktiv)
+ if (game.magic_wall_active)
{
- if (!(SiebCount % 4))
+ if (!(game.magic_wall_time_left % 4))
PlaySoundLevel(sieb_x, sieb_y, SND_MIEP);
- if (SiebCount > 0)
+ if (game.magic_wall_time_left > 0)
{
- SiebCount--;
- if (!SiebCount)
+ game.magic_wall_time_left--;
+ if (!game.magic_wall_time_left)
{
for (y=0; y<lev_fieldy; y++) for (x=0; x<lev_fieldx; x++)
{
}
}
- SiebAktiv = FALSE;
+ game.magic_wall_active = FALSE;
}
}
}
{
int jx = stored_player[i].jx, jy = stored_player[i].jy;
- if (!stored_player[i].active || stored_player[i].gone ||
- &stored_player[i] == player)
+ if (!stored_player[i].active || &stored_player[i] == player)
continue;
min_x = MIN(min_x, jx);
{
int jx = stored_player[i].jx, jy = stored_player[i].jy;
- if (!stored_player[i].active || stored_player[i].gone)
+ if (!stored_player[i].active)
continue;
if (!IN_VIS_FIELD(SCREENX(jx), SCREENY(jy)))
redraw_mask |= REDRAW_FIELD;
}
+static void CheckGravityMovement(struct PlayerInfo *player)
+{
+ if (level.gravity && !player->programmed_action)
+ {
+ int move_dir_vertical = player->action & (MV_UP | MV_DOWN);
+ int move_dir_horizontal = player->action & (MV_LEFT | MV_RIGHT);
+ int move_dir =
+ (player->last_move_dir & (MV_LEFT | MV_RIGHT) ?
+ (move_dir_vertical ? move_dir_vertical : move_dir_horizontal) :
+ (move_dir_horizontal ? move_dir_horizontal : move_dir_vertical));
+ int jx = player->jx, jy = player->jy;
+ int dx = (move_dir & MV_LEFT ? -1 : move_dir & MV_RIGHT ? +1 : 0);
+ int dy = (move_dir & MV_UP ? -1 : move_dir & MV_DOWN ? +1 : 0);
+ int new_jx = jx + dx, new_jy = jy + dy;
+ boolean field_under_player_is_free =
+ (IN_LEV_FIELD(jx, jy + 1) && IS_FREE(jx, jy + 1));
+ boolean player_is_moving_to_valid_field =
+ (IN_LEV_FIELD(new_jx, new_jy) &&
+ (Feld[new_jx][new_jy] == EL_SP_BASE ||
+ Feld[new_jx][new_jy] == EL_ERDREICH));
+
+ if (field_under_player_is_free && !player_is_moving_to_valid_field)
+ player->programmed_action = MV_DOWN;
+ }
+}
+
boolean MoveFigureOneStep(struct PlayerInfo *player,
int dx, int dy, int real_dx, int real_dy)
{
int element;
int can_move;
- if (player->gone || (!dx && !dy))
+ if (!player->active || (!dx && !dy))
return MF_NO_ACTION;
player->MovDir = (dx < 0 ? MV_LEFT :
jy = player->jy = new_jy;
StorePlayer[jx][jy] = player->element_nr;
- /*
- player->MovPos = (dx > 0 || dy > 0 ? -1 : 1) * (TILEX - TILEX / MoveSpeed);
- */
-
player->MovPos =
- (dx > 0 || dy > 0 ? -1 : 1) * (TILEX - TILEX / player->move_speed);
+ (dx > 0 || dy > 0 ? -1 : 1) * (TILEX - TILEX / player->move_delay_value);
ScrollFigure(player, SCROLL_INIT);
int old_jx = jx, old_jy = jy;
int moved = MF_NO_ACTION;
- if (player->gone || (!dx && !dy))
+ if (!player->active || (!dx && !dy))
return FALSE;
- /*
- if (!FrameReached(&player->move_delay, MoveSpeed) && !tape.playing)
+ if (!FrameReached(&player->move_delay, player->move_delay_value) &&
+ !tape.playing)
return FALSE;
- */
- if (!FrameReached(&player->move_delay, player->move_speed) && !tape.playing)
- return FALSE;
+ /* remove the last programmed player action */
+ player->programmed_action = 0;
if (player->MovPos)
{
/* should only happen if pre-1.2 tape recordings are played */
/* this is only for backward compatibility */
- /*
- int old_move_speed = MoveSpeed;
- */
-
- int old_move_speed = player->move_speed;
+ int original_move_delay_value = player->move_delay_value;
#if DEBUG
printf("THIS SHOULD ONLY HAPPEN WITH PRE-1.2 LEVEL TAPES.\n");
#endif
/* scroll remaining steps with finest movement resolution */
-
- /*
- MoveSpeed = 8;
- */
-
- player->move_speed = 8;
+ player->move_delay_value = MOVE_DELAY_NORMAL_SPEED;
while (player->MovPos)
{
BackToFront();
}
- /*
- MoveSpeed = old_move_speed;
- */
-
- player->move_speed = old_move_speed;
-
+ player->move_delay_value = original_move_delay_value;
}
if (player->last_move_dir & (MV_LEFT | MV_RIGHT))
player->last_move_dir = player->MovDir;
}
else
+ {
+ CheckGravityMovement(player);
+
player->last_move_dir = MV_NO_MOVING;
+ }
TestIfHeroHitsBadThing(jx, jy);
- if (player->gone)
+ if (!player->active)
RemoveHero(player);
return moved;
{
int jx = player->jx, jy = player->jy;
int last_jx = player->last_jx, last_jy = player->last_jy;
- int move_stepsize = TILEX / player->move_speed;
+ int move_stepsize = TILEX / player->move_delay_value;
- if (!player->active || player->gone || !player->MovPos)
+ if (!player->active || !player->MovPos)
return;
if (mode == SCROLL_INIT)
if (Feld[last_jx][last_jy] == EL_PLAYER_IS_LEAVING)
Feld[last_jx][last_jy] = EL_LEERRAUM;
-
- /*
- if (!player->MovPos && level.gravity)
- {
- if (player->action == MV_NO_MOVING)
- player->programmed_action = MV_DOWN;
- }
- */
-
+ /* before DrawPlayer() to draw correct player graphic for this case */
+ if (player->MovPos == 0)
+ CheckGravityMovement(player);
DrawPlayer(player);
- if (!player->MovPos)
+ if (player->MovPos == 0)
{
if (IS_QUICK_GATE(Feld[last_jx][last_jy]))
{
- /* continue with normal speed after moving through port */
- /* FIX THIS: what about player already having eaten a speed pill? */
-
- /*
- MoveSpeed = 8;
- ScrollStepSize = TILEX / MoveSpeed;
- */
-
- player->move_speed = 8;
+ /* continue with normal speed after quickly moving through gate */
+ HALVE_PLAYER_SPEED(player);
- /* don't wait for the next move -- the whole move delay stuff
- is worse at the moment; FIX THIS! ;-) */
+ /* be able to make the next move without delay */
player->move_delay = 0;
}
if (mode == SCROLL_INIT)
{
/* set scrolling step size according to actual player's moving speed */
- ScrollStepSize = TILEX / player->move_speed;
+ ScrollStepSize = TILEX / player->move_delay_value;
screen_frame_counter = FrameCounter;
ScreenMovDir = player->MovDir;
{
int jx = player->jx, jy = player->jy;
- if (player->gone)
+ if (!player->active)
return;
if (IS_PFORTE(Feld[jx][jy]))
{
int jx = player->jx, jy = player->jy;
- if (player->gone)
+ if (!player->active)
return;
PlaySoundLevel(jx, jy, SND_AUTSCH);
int jx = player->jx, jy = player->jy;
int i, found = FALSE;
- player->gone = TRUE;
+ player->present = FALSE;
+ player->active = FALSE;
+
StorePlayer[jx][jy] = 0;
for (i=0; i<MAX_PLAYERS; i++)
- if (stored_player[i].active && !stored_player[i].gone)
+ if (stored_player[i].active)
found = TRUE;
if (!found)
case EL_SPEED_PILL:
RemoveField(x, y);
-
- player->move_speed = 4;
-
- /*
- MoveSpeed = 4;
- ScrollStepSize = TILEX / MoveSpeed;
- */
-
+ player->move_delay_value = MOVE_DELAY_HIGH_SPEED;
PlaySoundLevel(x, y, SND_PONG);
break;
case EL_EM_GATE_4:
if (!player->key[element - EL_EM_GATE_1])
return MF_NO_ACTION;
-
if (!IN_LEV_FIELD(x + dx, y + dy) || !IS_FREE(x + dx, y + dy))
return MF_NO_ACTION;
/* automatically move to the next field with double speed */
player->programmed_action = move_direction;
- player->move_speed = 4;
+ DOUBLE_PLAYER_SPEED(player);
break;
case EL_EM_GATE_4X:
if (!player->key[element - EL_EM_GATE_1X])
return MF_NO_ACTION;
-
if (!IN_LEV_FIELD(x + dx, y + dy) || !IS_FREE(x + dx, y + dy))
return MF_NO_ACTION;
/* automatically move to the next field with double speed */
player->programmed_action = move_direction;
- player->move_speed = 4;
+ DOUBLE_PLAYER_SPEED(player);
break;
/* automatically move to the next field with double speed */
player->programmed_action = move_direction;
- player->move_speed = 4;
-
- /*
- MoveSpeed = 4;
- ScrollStepSize = TILEX / MoveSpeed;
- */
+ DOUBLE_PLAYER_SPEED(player);
break;
PlaySoundLevel(x, y, SND_BUING);
- /*
- player->gone = TRUE;
- PlaySoundLevel(x, y, SND_BUING);
-
- if (!local_player->friends_still_needed)
- player->LevelSolved = player->GameOver = TRUE;
- */
-
break;
case EL_BIRNE_AUS:
if (IS_SB_ELEMENT(element) &&
local_player->sokobanfields_still_needed == 0 &&
- game_emulation == EMU_SOKOBAN)
+ game.emulation == EMU_SOKOBAN)
{
player->LevelSolved = player->GameOver = TRUE;
PlaySoundLevel(x, y, SND_BUING);
int jx = player->jx, jy = player->jy;
int x = jx + dx, y = jy + dy;
- if (player->gone || !IN_LEV_FIELD(x, y))
+ if (!player->active || !IN_LEV_FIELD(x, y))
return FALSE;
if (dx && dy)
int jx = player->jx, jy = player->jy;
int element;
- if (player->gone || player->MovPos)
+ if (!player->active || player->MovPos)
return FALSE;
element = Feld[jx][jy];
FS_SMALL, FC_YELLOW);
if (IN_SCR_FIELD(SCREENX(jx), SCREENY(jy)))
{
- if (game_emulation == EMU_SUPAPLEX)
+ if (game.emulation == EMU_SUPAPLEX)
DrawGraphic(SCREENX(jx), SCREENY(jy), GFX_SP_DISK_RED);
else
DrawGraphicThruMask(SCREENX(jx), SCREENY(jy), GFX_DYNAMIT);
volume = PSND_MAX_VOLUME;
#ifndef MSDOS
- stereo = (sx-SCR_FIELDX/2)*12;
+ stereo = (sx - SCR_FIELDX/2) * 12;
#else
- stereo = PSND_MIDDLE+(2*sx-(SCR_FIELDX-1))*5;
- if(stereo > PSND_MAX_RIGHT) stereo = PSND_MAX_RIGHT;
- if(stereo < PSND_MAX_LEFT) stereo = PSND_MAX_LEFT;
+ stereo = PSND_MIDDLE + (2 * sx - (SCR_FIELDX - 1)) * 5;
+ if (stereo > PSND_MAX_RIGHT)
+ stereo = PSND_MAX_RIGHT;
+ if (stereo < PSND_MAX_LEFT)
+ stereo = PSND_MAX_LEFT;
#endif
if (!IN_SCR_FIELD(sx, sy))
{
- int dx = ABS(sx-SCR_FIELDX/2)-SCR_FIELDX/2;
- int dy = ABS(sy-SCR_FIELDY/2)-SCR_FIELDY/2;
+ int dx = ABS(sx - SCR_FIELDX/2) - SCR_FIELDX/2;
+ int dy = ABS(sy - SCR_FIELDY/2) - SCR_FIELDY/2;
- volume -= volume*(dx > dy ? dx : dy)/silence_distance;
+ volume -= volume * (dx > dy ? dx : dy) / silence_distance;
}
PlaySoundExt(sound_nr, volume, stereo, PSND_NO_LOOP);
break;
}
- if (Request("Do you really want to quit the game ?",
+ if (level_editor_test_game ||
+ Request("Do you really want to quit the game ?",
REQ_ASK | REQ_STAY_CLOSED))
{
#ifndef MSDOS