X-Git-Url: https://git.artsoft.org/?a=blobdiff_plain;f=src%2Fgame.c;h=1b16a6f995ad6f7313d1aebb0de762f5cbd299b4;hb=bddf6c22480ed7f7fca83b7d6c4f9dc10d19f57a;hp=fa1682053736b0e197c2e9b5b910dcef4dc90217;hpb=d959ed0d8d9cadec525853c2ab584f8d1ab079ae;p=rocksndiamonds.git diff --git a/src/game.c b/src/game.c index fa168205..1b16a6f9 100644 --- a/src/game.c +++ b/src/game.c @@ -4503,7 +4503,11 @@ void InitGame(void) scroll_y = game.forced_scroll_y; // !!! FIX THIS (START) !!! - if (level.game_engine_type == GAME_ENGINE_TYPE_EM) + if (level.game_engine_type == GAME_ENGINE_TYPE_BD) + { + InitGameEngine_BD(); + } + else if (level.game_engine_type == GAME_ENGINE_TYPE_EM) { InitGameEngine_EM(); } @@ -4968,7 +4972,8 @@ void GameWon(void) } // if not counting score after game, immediately update game panel values - if (level_editor_test_game || !setup.count_score_after_game) + if (level_editor_test_game || !setup.count_score_after_game || + level.game_engine_type == GAME_ENGINE_TYPE_BD) { time = time_final; score = score_final; @@ -11704,6 +11709,10 @@ static void CheckLevelSolved(void) static void PlayTimeoutSound(int seconds_left) { + // will be played directly by BD engine (for classic bonus time sounds) + if (level.game_engine_type == GAME_ENGINE_TYPE_BD && checkBonusTime_BD()) + return; + // try to use individual "running out of time" sound for each second left int sound = SND_GAME_RUNNING_OUT_OF_TIME_0 - seconds_left; @@ -11750,9 +11759,24 @@ static void CheckLevelTime_StepCounter(void) static void CheckLevelTime(void) { + int frames_per_second = FRAMES_PER_SECOND; int i; - if (TimeFrames >= FRAMES_PER_SECOND) + if (level.game_engine_type == GAME_ENGINE_TYPE_BD) + { + // level time may be running slower in native BD engine + frames_per_second = getFramesPerSecond_BD(); + + // if native engine time changed, force main engine time change + if (getTimeLeft_BD() < TimeLeft) + TimeFrames = frames_per_second; + + // if last second running, wait for native engine time to exactly reach zero + if (getTimeLeft_BD() == 1 && TimeLeft == 1) + TimeFrames = frames_per_second - 1; + } + + if (TimeFrames >= frames_per_second) { TimeFrames = 0; @@ -11787,11 +11811,20 @@ static void CheckLevelTime(void) if (!TimeLeft && game.time_limit) { - if (level.game_engine_type == GAME_ENGINE_TYPE_EM) + if (level.game_engine_type == GAME_ENGINE_TYPE_BD) + { + if (game_bd.game->cave->player_state == GD_PL_LIVING) + game_bd.game->cave->player_state = GD_PL_TIMEOUT; + } + else if (level.game_engine_type == GAME_ENGINE_TYPE_EM) + { game_em.lev->killed_out_of_time = TRUE; + } else + { for (i = 0; i < MAX_PLAYERS; i++) KillPlayer(&stored_player[i]); + } } } else if (game.no_level_time_limit && !game.all_players_gone) @@ -11822,10 +11855,20 @@ void AdvanceFrameAndPlayerCounters(int player_nr) { int i; + // handle game and tape time differently for native BD game engine + + // tape time is running in native BD engine even if player is not hatched yet + if (!checkGameRunning()) + return; + // advance frame counters (global frame counter and tape time frame counter) FrameCounter++; TapeTimeFrames++; + // level time is running in native BD engine after player is being hatched + if (!checkGamePlaying()) + return; + // advance time frame counter (used to control available time to solve level) TimeFrames++; @@ -12176,7 +12219,11 @@ static void GameActionsExt(void) game.snapshot.last_action[i] = stored_player[i].effective_action; } - if (level.game_engine_type == GAME_ENGINE_TYPE_EM) + if (level.game_engine_type == GAME_ENGINE_TYPE_BD) + { + GameActions_BD_Main(); + } + else if (level.game_engine_type == GAME_ENGINE_TYPE_EM) { GameActions_EM_Main(); } @@ -12243,6 +12290,17 @@ void GameActions(void) GameActions_CheckSaveEngineSnapshot(); } +void GameActions_BD_Main(void) +{ + byte effective_action[MAX_PLAYERS]; + int i; + + for (i = 0; i < MAX_PLAYERS; i++) + effective_action[i] = stored_player[i].effective_action; + + GameActions_BD(effective_action); +} + void GameActions_EM_Main(void) { byte effective_action[MAX_PLAYERS]; @@ -15479,56 +15537,81 @@ static int getSoundAction_BD(int sample) { switch (sample) { - case GD_S_STONE: - case GD_S_NUT: - case GD_S_DIRT_BALL: - case GD_S_NITRO: - case GD_S_FALLING_WALL: + case GD_S_STONE_PUSHING: + case GD_S_MEGA_STONE_PUSHING: + case GD_S_FLYING_STONE_PUSHING: + case GD_S_WAITING_STONE_PUSHING: + case GD_S_CHASING_STONE_PUSHING: + case GD_S_NUT_PUSHING: + case GD_S_NITRO_PACK_PUSHING: + case GD_S_BLADDER_PUSHING: + case GD_S_BOX_PUSHING: + return ACTION_PUSHING; + + case GD_S_STONE_FALLING: + case GD_S_MEGA_STONE_FALLING: + case GD_S_FLYING_STONE_FALLING: + case GD_S_NUT_FALLING: + case GD_S_DIRT_BALL_FALLING: + case GD_S_DIRT_LOOSE_FALLING: + case GD_S_NITRO_PACK_FALLING: + case GD_S_FALLING_WALL_FALLING: + return ACTION_FALLING; + + case GD_S_STONE_IMPACT: + case GD_S_MEGA_STONE_IMPACT: + case GD_S_FLYING_STONE_IMPACT: + case GD_S_NUT_IMPACT: + case GD_S_DIRT_BALL_IMPACT: + case GD_S_DIRT_LOOSE_IMPACT: + case GD_S_NITRO_PACK_IMPACT: + case GD_S_FALLING_WALL_IMPACT: return ACTION_IMPACT; - case GD_S_NUT_CRACK: + case GD_S_NUT_CRACKING: return ACTION_BREAKING; case GD_S_EXPANDING_WALL: - case GD_S_WALL_REAPPEAR: + case GD_S_WALL_REAPPEARING: case GD_S_SLIME: case GD_S_LAVA: - case GD_S_ACID_SPREAD: + case GD_S_ACID_SPREADING: return ACTION_GROWING; - case GD_S_DIAMOND_COLLECT: - case GD_S_SKELETON_COLLECT: - case GD_S_PNEUMATIC_COLLECT: - case GD_S_BOMB_COLLECT: - case GD_S_CLOCK_COLLECT: - case GD_S_SWEET_COLLECT: - case GD_S_KEY_COLLECT: - case GD_S_DIAMOND_KEY_COLLECT: + case GD_S_DIAMOND_COLLECTING: + case GD_S_FLYING_DIAMOND_COLLECTING: + case GD_S_SKELETON_COLLECTING: + case GD_S_PNEUMATIC_COLLECTING: + case GD_S_BOMB_COLLECTING: + case GD_S_CLOCK_COLLECTING: + case GD_S_SWEET_COLLECTING: + case GD_S_KEY_COLLECTING: + case GD_S_DIAMOND_KEY_COLLECTING: return ACTION_COLLECTING; - case GD_S_BOMB_PLACE: + case GD_S_BOMB_PLACING: case GD_S_REPLICATOR: return ACTION_DROPPING; - case GD_S_BLADDER_MOVE: + case GD_S_BLADDER_MOVING: return ACTION_MOVING; case GD_S_BLADDER_SPENDER: - case GD_S_BLADDER_CONVERT: - case GD_S_GRAVITY_CHANGE: + case GD_S_BLADDER_CONVERTING: + case GD_S_GRAVITY_CHANGING: return ACTION_CHANGING; - case GD_S_BITER_EAT: + case GD_S_BITER_EATING: return ACTION_EATING; - case GD_S_DOOR_OPEN: - case GD_S_CRACK: + case GD_S_DOOR_OPENING: + case GD_S_CRACKING: return ACTION_OPENING; - case GD_S_WALK_EARTH: + case GD_S_DIRT_WALKING: return ACTION_DIGGING; - case GD_S_WALK_EMPTY: + case GD_S_EMPTY_WALKING: return ACTION_WALKING; case GD_S_SWITCH_BITER: @@ -15540,36 +15623,59 @@ static int getSoundAction_BD(int sample) case GD_S_STIRRING: return ACTION_ACTIVATING; - case GD_S_BOX_PUSH: - return ACTION_PUSHING; - case GD_S_TELEPORTER: return ACTION_PASSING; - case GD_S_EXPLOSION: - case GD_S_BOMB_EXPLOSION: - case GD_S_GHOST_EXPLOSION: - case GD_S_VOODOO_EXPLOSION: - case GD_S_NITRO_EXPLOSION: + case GD_S_EXPLODING: + case GD_S_BOMB_EXPLODING: + case GD_S_GHOST_EXPLODING: + case GD_S_VOODOO_EXPLODING: + case GD_S_NITRO_PACK_EXPLODING: return ACTION_EXPLODING; - case GD_S_COVER: + case GD_S_COVERING: case GD_S_AMOEBA: - case GD_S_AMOEBA_MAGIC: case GD_S_MAGIC_WALL: case GD_S_PNEUMATIC_HAMMER: case GD_S_WATER: return ACTION_ACTIVE; - case GD_S_DIAMOND_RANDOM: - case GD_S_DIAMOND_1: - case GD_S_DIAMOND_2: - case GD_S_DIAMOND_3: - case GD_S_DIAMOND_4: - case GD_S_DIAMOND_5: - case GD_S_DIAMOND_6: - case GD_S_DIAMOND_7: - case GD_S_DIAMOND_8: + case GD_S_DIAMOND_FALLING_RANDOM: + case GD_S_DIAMOND_FALLING_1: + case GD_S_DIAMOND_FALLING_2: + case GD_S_DIAMOND_FALLING_3: + case GD_S_DIAMOND_FALLING_4: + case GD_S_DIAMOND_FALLING_5: + case GD_S_DIAMOND_FALLING_6: + case GD_S_DIAMOND_FALLING_7: + case GD_S_DIAMOND_FALLING_8: + case GD_S_DIAMOND_IMPACT_RANDOM: + case GD_S_DIAMOND_IMPACT_1: + case GD_S_DIAMOND_IMPACT_2: + case GD_S_DIAMOND_IMPACT_3: + case GD_S_DIAMOND_IMPACT_4: + case GD_S_DIAMOND_IMPACT_5: + case GD_S_DIAMOND_IMPACT_6: + case GD_S_DIAMOND_IMPACT_7: + case GD_S_DIAMOND_IMPACT_8: + case GD_S_FLYING_DIAMOND_FALLING_RANDOM: + case GD_S_FLYING_DIAMOND_FALLING_1: + case GD_S_FLYING_DIAMOND_FALLING_2: + case GD_S_FLYING_DIAMOND_FALLING_3: + case GD_S_FLYING_DIAMOND_FALLING_4: + case GD_S_FLYING_DIAMOND_FALLING_5: + case GD_S_FLYING_DIAMOND_FALLING_6: + case GD_S_FLYING_DIAMOND_FALLING_7: + case GD_S_FLYING_DIAMOND_FALLING_8: + case GD_S_FLYING_DIAMOND_IMPACT_RANDOM: + case GD_S_FLYING_DIAMOND_IMPACT_1: + case GD_S_FLYING_DIAMOND_IMPACT_2: + case GD_S_FLYING_DIAMOND_IMPACT_3: + case GD_S_FLYING_DIAMOND_IMPACT_4: + case GD_S_FLYING_DIAMOND_IMPACT_5: + case GD_S_FLYING_DIAMOND_IMPACT_6: + case GD_S_FLYING_DIAMOND_IMPACT_7: + case GD_S_FLYING_DIAMOND_IMPACT_8: case GD_S_TIMEOUT_0: case GD_S_TIMEOUT_1: case GD_S_TIMEOUT_2: @@ -15582,10 +15688,12 @@ static int getSoundAction_BD(int sample) case GD_S_TIMEOUT_9: case GD_S_TIMEOUT_10: case GD_S_BONUS_LIFE: - // kludge to prevent playing as loop sound + // trigger special post-processing (and force sound to be non-looping) return ACTION_OTHER; + case GD_S_AMOEBA_MAGIC: case GD_S_FINISHED: + // trigger special post-processing (and force sound to be looping) return ACTION_DEFAULT; default: @@ -15604,24 +15712,75 @@ static int getSoundEffect_BD(int element_bd, int sample) sound_action != ACTION_DEFAULT) return sound_effect; - // special sounds + // special post-processing for some sounds switch (sample) { - case GD_S_DIAMOND_RANDOM: - nr = GetSimpleRandom(8); - sound_effect = SND_BD_DIAMOND_IMPACT_RANDOM_1 + nr; + case GD_S_DIAMOND_FALLING_RANDOM: + case GD_S_DIAMOND_FALLING_1: + case GD_S_DIAMOND_FALLING_2: + case GD_S_DIAMOND_FALLING_3: + case GD_S_DIAMOND_FALLING_4: + case GD_S_DIAMOND_FALLING_5: + case GD_S_DIAMOND_FALLING_6: + case GD_S_DIAMOND_FALLING_7: + case GD_S_DIAMOND_FALLING_8: + nr = (sample == GD_S_DIAMOND_FALLING_RANDOM ? GetSimpleRandom(8) : + sample - GD_S_DIAMOND_FALLING_1); + sound_effect = SND_BD_DIAMOND_FALLING_RANDOM_1 + nr; + + if (getSoundInfoEntryFilename(sound_effect) == NULL) + sound_effect = SND_BD_DIAMOND_FALLING; break; - case GD_S_DIAMOND_1: - case GD_S_DIAMOND_2: - case GD_S_DIAMOND_3: - case GD_S_DIAMOND_4: - case GD_S_DIAMOND_5: - case GD_S_DIAMOND_6: - case GD_S_DIAMOND_7: - case GD_S_DIAMOND_8: - nr = sample - GD_S_DIAMOND_1; + case GD_S_DIAMOND_IMPACT_RANDOM: + case GD_S_DIAMOND_IMPACT_1: + case GD_S_DIAMOND_IMPACT_2: + case GD_S_DIAMOND_IMPACT_3: + case GD_S_DIAMOND_IMPACT_4: + case GD_S_DIAMOND_IMPACT_5: + case GD_S_DIAMOND_IMPACT_6: + case GD_S_DIAMOND_IMPACT_7: + case GD_S_DIAMOND_IMPACT_8: + nr = (sample == GD_S_DIAMOND_IMPACT_RANDOM ? GetSimpleRandom(8) : + sample - GD_S_DIAMOND_IMPACT_1); sound_effect = SND_BD_DIAMOND_IMPACT_RANDOM_1 + nr; + + if (getSoundInfoEntryFilename(sound_effect) == NULL) + sound_effect = SND_BD_DIAMOND_IMPACT; + break; + + case GD_S_FLYING_DIAMOND_FALLING_RANDOM: + case GD_S_FLYING_DIAMOND_FALLING_1: + case GD_S_FLYING_DIAMOND_FALLING_2: + case GD_S_FLYING_DIAMOND_FALLING_3: + case GD_S_FLYING_DIAMOND_FALLING_4: + case GD_S_FLYING_DIAMOND_FALLING_5: + case GD_S_FLYING_DIAMOND_FALLING_6: + case GD_S_FLYING_DIAMOND_FALLING_7: + case GD_S_FLYING_DIAMOND_FALLING_8: + nr = (sample == GD_S_FLYING_DIAMOND_FALLING_RANDOM ? GetSimpleRandom(8) : + sample - GD_S_FLYING_DIAMOND_FALLING_1); + sound_effect = SND_BD_FLYING_DIAMOND_FALLING_RANDOM_1 + nr; + + if (getSoundInfoEntryFilename(sound_effect) == NULL) + sound_effect = SND_BD_FLYING_DIAMOND_FALLING; + break; + + case GD_S_FLYING_DIAMOND_IMPACT_RANDOM: + case GD_S_FLYING_DIAMOND_IMPACT_1: + case GD_S_FLYING_DIAMOND_IMPACT_2: + case GD_S_FLYING_DIAMOND_IMPACT_3: + case GD_S_FLYING_DIAMOND_IMPACT_4: + case GD_S_FLYING_DIAMOND_IMPACT_5: + case GD_S_FLYING_DIAMOND_IMPACT_6: + case GD_S_FLYING_DIAMOND_IMPACT_7: + case GD_S_FLYING_DIAMOND_IMPACT_8: + nr = (sample == GD_S_FLYING_DIAMOND_IMPACT_RANDOM ? GetSimpleRandom(8) : + sample - GD_S_FLYING_DIAMOND_IMPACT_1); + sound_effect = SND_BD_FLYING_DIAMOND_IMPACT_RANDOM_1 + nr; + + if (getSoundInfoEntryFilename(sound_effect) == NULL) + sound_effect = SND_BD_FLYING_DIAMOND_IMPACT; break; case GD_S_TIMEOUT_0: @@ -15642,14 +15801,18 @@ static int getSoundEffect_BD(int element_bd, int sample) sound_effect = SND_GAME_RUNNING_OUT_OF_TIME; break; - case GD_S_FINISHED: - sound_effect = SND_GAME_LEVELTIME_BONUS; - break; - case GD_S_BONUS_LIFE: sound_effect = SND_GAME_HEALTH_BONUS; break; + case GD_S_AMOEBA_MAGIC: + sound_effect = SND_BD_AMOEBA_OTHER; + break; + + case GD_S_FINISHED: + sound_effect = SND_GAME_LEVELTIME_BONUS; + break; + default: sound_effect = SND_UNDEFINED; break; @@ -15668,7 +15831,14 @@ void PlayLevelSound_BD(int xx, int yy, int element_bd, int sample) int x = xx - offset; int y = yy - offset; - if (sound_action == ACTION_OTHER) + // some sound actions are always looping in native BD game engine + if (sound_action == ACTION_DEFAULT) + is_loop_sound = TRUE; + + // some sound actions are always non-looping in native BD game engine + if (sound_action == ACTION_FALLING || + sound_action == ACTION_MOVING || + sound_action == ACTION_OTHER) is_loop_sound = FALSE; if (sound_effect != SND_UNDEFINED) @@ -16156,6 +16326,17 @@ boolean checkGameRunning(void) return TRUE; } +boolean checkGamePlaying(void) +{ + if (game_status != GAME_MODE_PLAYING) + return FALSE; + + if (level.game_engine_type == GAME_ENGINE_TYPE_BD && !checkGamePlaying_BD()) + return FALSE; + + return TRUE; +} + boolean checkGameSolved(void) { // set for all game engines if level was solved