X-Git-Url: https://git.artsoft.org/?a=blobdiff_plain;f=src%2Fgame.c;h=9fb95c23bad7af9d5302e0e2acf891aea88d86df;hb=7b387b9e5e8095a01c18ea041f19d71be83146b9;hp=297efe8502254ba09972f195dbea379219e08713;hpb=74ed6f367314f4b4f373b45f82cedd04595a2608;p=rocksndiamonds.git diff --git a/src/game.c b/src/game.c index 297efe85..9fb95c23 100644 --- a/src/game.c +++ b/src/game.c @@ -87,16 +87,10 @@ #define EX_TYPE_DYNA (1 << 4) #define EX_TYPE_SINGLE_TILE (EX_TYPE_CENTER | EX_TYPE_BORDER) -#if 1 #define PANEL_OFF() (local_player->LevelSolved_PanelOff) #define PANEL_DEACTIVATED(p) ((p)->x < 0 || (p)->y < 0 || PANEL_OFF()) -#define PANEL_XPOS(p) (DX + ALIGNED_MENU_XPOS(p)) -#define PANEL_YPOS(p) (DY + ALIGNED_MENU_YPOS(p)) -#else -#define PANEL_DEACTIVATED(p) ((p).x < 0 || (p).y < 0) -#define PANEL_XPOS(p) (ALIGNED_XPOS((p).x, (p).width, (p).align)) -#define PANEL_YPOS(p) ((p).y) -#endif +#define PANEL_XPOS(p) (DX + ALIGNED_TEXT_XPOS(p)) +#define PANEL_YPOS(p) (DY + ALIGNED_TEXT_YPOS(p)) /* special positions in the game control window (relative to control window) */ #define XX_LEVEL1 (PANEL_XPOS(game.panel.level)) @@ -134,93 +128,105 @@ #define DX_TIME (DX + XX_TIME) #define DY_TIME (DY + YY_TIME) -#if 0 +#if 1 /* game panel display and control definitions */ -#define GAME_CONTROL_LEVEL 0 +#define GAME_CONTROL_LEVEL_NUMBER 0 #define GAME_CONTROL_GEMS 1 -#define GAME_CONTROL_INVENTORY 2 -#define GAME_CONTROL_KEY_1 3 -#define GAME_CONTROL_KEY_2 4 -#define GAME_CONTROL_KEY_3 5 -#define GAME_CONTROL_KEY_4 6 -#define GAME_CONTROL_KEY_5 7 -#define GAME_CONTROL_KEY_6 8 -#define GAME_CONTROL_KEY_7 9 -#define GAME_CONTROL_KEY_8 10 -#define GAME_CONTROL_KEY_WHITE 11 -#define GAME_CONTROL_KEY_WHITE_COUNT 12 -#define GAME_CONTROL_SCORE 13 -#define GAME_CONTROL_TIME 14 -#define GAME_CONTROL_TIME_HH 15 -#define GAME_CONTROL_TIME_MM 16 -#define GAME_CONTROL_TIME_SS 17 -#define GAME_CONTROL_DROP_NEXT_1 18 -#define GAME_CONTROL_DROP_NEXT_2 19 -#define GAME_CONTROL_DROP_NEXT_3 20 -#define GAME_CONTROL_DROP_NEXT_4 21 -#define GAME_CONTROL_DROP_NEXT_5 22 -#define GAME_CONTROL_DROP_NEXT_6 23 -#define GAME_CONTROL_DROP_NEXT_7 24 -#define GAME_CONTROL_DROP_NEXT_8 25 -#define GAME_CONTROL_SHIELD_NORMAL 26 -#define GAME_CONTROL_SHIELD_NORMAL_TIME 27 -#define GAME_CONTROL_SHIELD_DEADLY 28 -#define GAME_CONTROL_SHIELD_DEADLY_TIME 29 -#define GAME_CONTROL_EXIT 30 -#define GAME_CONTROL_EM_EXIT 31 -#define GAME_CONTROL_SP_EXIT 32 -#define GAME_CONTROL_STEEL_EXIT 33 -#define GAME_CONTROL_EM_STEEL_EXIT 34 -#define GAME_CONTROL_EMC_MAGIC_BALL 35 -#define GAME_CONTROL_EMC_MAGIC_BALL_TIME 36 -#define GAME_CONTROL_LIGHT_SWITCH 37 -#define GAME_CONTROL_LIGHT_SWITCH_TIME 38 -#define GAME_CONTROL_TIMEGATE_SWITCH 39 -#define GAME_CONTROL_TIMEGATE_SWITCH_TIME 40 -#define GAME_CONTROL_SWITCHGATE_SWITCH 41 -#define GAME_CONTROL_EMC_LENSES 42 -#define GAME_CONTROL_EMC_LENSES_TIME 43 -#define GAME_CONTROL_EMC_MAGNIFIER 44 -#define GAME_CONTROL_EMC_MAGNIFIER_TIME 45 -#define GAME_CONTROL_BALLOON_SWITCH 46 -#define GAME_CONTROL_DYNABOMB_NUMBER 47 -#define GAME_CONTROL_DYNABOMB_SIZE 48 -#define GAME_CONTROL_DYNABOMB_POWER 49 -#define GAME_CONTROL_PENGUINS 50 -#define GAME_CONTROL_SOKOBAN_OBJECTS 51 -#define GAME_CONTROL_SOKOBAN_FIELDS 52 -#define GAME_CONTROL_ROBOT_WHEEL 53 -#define GAME_CONTROL_CONVEYOR_BELT_1 54 -#define GAME_CONTROL_CONVEYOR_BELT_1_SWITCH 55 -#define GAME_CONTROL_CONVEYOR_BELT_2 56 -#define GAME_CONTROL_CONVEYOR_BELT_2_SWITCH 57 -#define GAME_CONTROL_CONVEYOR_BELT_3 58 -#define GAME_CONTROL_CONVEYOR_BELT_3_SWITCH 59 -#define GAME_CONTROL_CONVEYOR_BELT_4 60 -#define GAME_CONTROL_CONVEYOR_BELT_4_SWITCH 61 -#define GAME_CONTROL_MAGIC_WALL 62 -#define GAME_CONTROL_MAGIC_WALL_TIME 63 -#define GAME_CONTROL_BD_MAGIC_WALL 64 -#define GAME_CONTROL_DC_MAGIC_WALL 65 -#define GAME_CONTROL_PLAYER_NAME 66 -#define GAME_CONTROL_LEVEL_NAME 67 -#define GAME_CONTROL_LEVEL_AUTHOR 68 +#define GAME_CONTROL_INVENTORY_COUNT 2 +#define GAME_CONTROL_INVENTORY_FIRST_1 3 +#define GAME_CONTROL_INVENTORY_FIRST_2 4 +#define GAME_CONTROL_INVENTORY_FIRST_3 5 +#define GAME_CONTROL_INVENTORY_FIRST_4 6 +#define GAME_CONTROL_INVENTORY_FIRST_5 7 +#define GAME_CONTROL_INVENTORY_FIRST_6 8 +#define GAME_CONTROL_INVENTORY_FIRST_7 9 +#define GAME_CONTROL_INVENTORY_FIRST_8 10 +#define GAME_CONTROL_INVENTORY_LAST_1 11 +#define GAME_CONTROL_INVENTORY_LAST_2 12 +#define GAME_CONTROL_INVENTORY_LAST_3 13 +#define GAME_CONTROL_INVENTORY_LAST_4 14 +#define GAME_CONTROL_INVENTORY_LAST_5 15 +#define GAME_CONTROL_INVENTORY_LAST_6 16 +#define GAME_CONTROL_INVENTORY_LAST_7 17 +#define GAME_CONTROL_INVENTORY_LAST_8 18 +#define GAME_CONTROL_KEY_1 19 +#define GAME_CONTROL_KEY_2 20 +#define GAME_CONTROL_KEY_3 21 +#define GAME_CONTROL_KEY_4 22 +#define GAME_CONTROL_KEY_5 23 +#define GAME_CONTROL_KEY_6 24 +#define GAME_CONTROL_KEY_7 25 +#define GAME_CONTROL_KEY_8 26 +#define GAME_CONTROL_KEY_WHITE 27 +#define GAME_CONTROL_KEY_WHITE_COUNT 28 +#define GAME_CONTROL_SCORE 29 +#define GAME_CONTROL_TIME 30 +#define GAME_CONTROL_TIME_HH 31 +#define GAME_CONTROL_TIME_MM 32 +#define GAME_CONTROL_TIME_SS 33 +#define GAME_CONTROL_SHIELD_NORMAL 34 +#define GAME_CONTROL_SHIELD_NORMAL_TIME 35 +#define GAME_CONTROL_SHIELD_DEADLY 36 +#define GAME_CONTROL_SHIELD_DEADLY_TIME 37 +#define GAME_CONTROL_EXIT 38 +#define GAME_CONTROL_EM_EXIT 39 +#define GAME_CONTROL_SP_EXIT 40 +#define GAME_CONTROL_STEEL_EXIT 41 +#define GAME_CONTROL_EM_STEEL_EXIT 42 +#define GAME_CONTROL_EMC_MAGIC_BALL 43 +#define GAME_CONTROL_EMC_MAGIC_BALL_SWITCH 44 +#define GAME_CONTROL_LIGHT_SWITCH 45 +#define GAME_CONTROL_LIGHT_SWITCH_TIME 46 +#define GAME_CONTROL_TIMEGATE_SWITCH 47 +#define GAME_CONTROL_TIMEGATE_SWITCH_TIME 48 +#define GAME_CONTROL_SWITCHGATE_SWITCH 49 +#define GAME_CONTROL_EMC_LENSES 50 +#define GAME_CONTROL_EMC_LENSES_TIME 51 +#define GAME_CONTROL_EMC_MAGNIFIER 52 +#define GAME_CONTROL_EMC_MAGNIFIER_TIME 53 +#define GAME_CONTROL_BALLOON_SWITCH 54 +#define GAME_CONTROL_DYNABOMB_NUMBER 55 +#define GAME_CONTROL_DYNABOMB_SIZE 56 +#define GAME_CONTROL_DYNABOMB_POWER 57 +#define GAME_CONTROL_PENGUINS 58 +#define GAME_CONTROL_SOKOBAN_OBJECTS 59 +#define GAME_CONTROL_SOKOBAN_FIELDS 60 +#define GAME_CONTROL_ROBOT_WHEEL 61 +#define GAME_CONTROL_CONVEYOR_BELT_1 62 +#define GAME_CONTROL_CONVEYOR_BELT_1_SWITCH 63 +#define GAME_CONTROL_CONVEYOR_BELT_2 64 +#define GAME_CONTROL_CONVEYOR_BELT_2_SWITCH 65 +#define GAME_CONTROL_CONVEYOR_BELT_3 66 +#define GAME_CONTROL_CONVEYOR_BELT_3_SWITCH 67 +#define GAME_CONTROL_CONVEYOR_BELT_4 68 +#define GAME_CONTROL_CONVEYOR_BELT_4_SWITCH 69 +#define GAME_CONTROL_MAGIC_WALL 70 +#define GAME_CONTROL_MAGIC_WALL_TIME 71 +#define GAME_CONTROL_BD_MAGIC_WALL 72 +#define GAME_CONTROL_DC_MAGIC_WALL 73 +#define GAME_CONTROL_PLAYER_NAME 74 +#define GAME_CONTROL_LEVEL_NAME 75 +#define GAME_CONTROL_LEVEL_AUTHOR 76 + +#define NUM_GAME_CONTROLS 77 + +int game_control_value[NUM_GAME_CONTROLS]; +int last_game_control_value[NUM_GAME_CONTROLS]; struct GameControlInfo { int nr; - struct TextPosInfo *pos_text; + struct TextPosInfo *pos; int type; - void *ptr; }; static struct GameControlInfo game_controls[] = { { - GAME_CONTROL_LEVEL, - &game.panel.level, + GAME_CONTROL_LEVEL_NUMBER, + &game.panel.level_number, TYPE_INTEGER, }, { @@ -229,139 +235,169 @@ static struct GameControlInfo game_controls[] = TYPE_INTEGER, }, { - GAME_CONTROL_INVENTORY, - &game.panel.inventory, + GAME_CONTROL_INVENTORY_COUNT, + &game.panel.inventory_count, TYPE_INTEGER, }, { - GAME_CONTROL_KEYS, - &game.panel.keys, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_1, + &game.panel.inventory_first_1, + TYPE_ELEMENT, }, { - GAME_CONTROL_SCORE, - &game.panel.score, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_2, + &game.panel.inventory_first_2, + TYPE_ELEMENT, }, { - GAME_CONTROL_TIME, - &game.panel.time, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_3, + &game.panel.inventory_first_3, + TYPE_ELEMENT, }, { - GAME_CONTROL_TIME_HH, - &game.panel.time_hh, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_4, + &game.panel.inventory_first_4, + TYPE_ELEMENT, }, { - GAME_CONTROL_TIME_MM, - &game.panel.time_mm, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_5, + &game.panel.inventory_first_5, + TYPE_ELEMENT, }, { - GAME_CONTROL_TIME_SS, - &game.panel.time_ss, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_6, + &game.panel.inventory_first_6, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_1, - &game.panel.drop_next_1, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_7, + &game.panel.inventory_first_7, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_2, - &game.panel.drop_next_2, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_FIRST_8, + &game.panel.inventory_first_8, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_3, - &game.panel.drop_next_3, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_1, + &game.panel.inventory_last_1, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_4, - &game.panel.drop_next_4, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_2, + &game.panel.inventory_last_2, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_5, - &game.panel.drop_next_5, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_3, + &game.panel.inventory_last_3, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_6, - &game.panel.drop_next_6, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_4, + &game.panel.inventory_last_4, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_7, - &game.panel.drop_next_7, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_5, + &game.panel.inventory_last_5, + TYPE_ELEMENT, }, { - GAME_CONTROL_DROP_NEXT_8, - &game.panel.drop_next_8, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_6, + &game.panel.inventory_last_6, + TYPE_ELEMENT, }, { - GAME_CONTROL_EMC_KEYS, - &game.panel.emc_keys, - TYPE_INTEGER, + GAME_CONTROL_INVENTORY_LAST_7, + &game.panel.inventory_last_7, + TYPE_ELEMENT, + }, + { + GAME_CONTROL_INVENTORY_LAST_8, + &game.panel.inventory_last_8, + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_1, - &game.panel.key_1, - TYPE_INTEGER, + &game.panel.key[0], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_2, - &game.panel.key_2, - TYPE_INTEGER, + &game.panel.key[1], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_3, - &game.panel.key_3, - TYPE_INTEGER, + &game.panel.key[2], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_4, - &game.panel.key_4, - TYPE_INTEGER, + &game.panel.key[3], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_5, - &game.panel.key_5, - TYPE_INTEGER, + &game.panel.key[4], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_6, - &game.panel.key_6, - TYPE_INTEGER, + &game.panel.key[5], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_7, - &game.panel.key_7, - TYPE_INTEGER, + &game.panel.key[6], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_8, - &game.panel.key_8, - TYPE_INTEGER, + &game.panel.key[7], + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_WHITE, &game.panel.key_white, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_KEY_WHITE_COUNT, &game.panel.key_white_count, TYPE_INTEGER, }, + { + GAME_CONTROL_SCORE, + &game.panel.score, + TYPE_INTEGER, + }, + { + GAME_CONTROL_TIME, + &game.panel.time, + TYPE_INTEGER, + }, + { + GAME_CONTROL_TIME_HH, + &game.panel.time_hh, + TYPE_INTEGER, + }, + { + GAME_CONTROL_TIME_MM, + &game.panel.time_mm, + TYPE_INTEGER, + }, + { + GAME_CONTROL_TIME_SS, + &game.panel.time_ss, + TYPE_INTEGER, + }, { GAME_CONTROL_SHIELD_NORMAL, &game.panel.shield_normal, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_SHIELD_NORMAL_TIME, @@ -371,7 +407,7 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_SHIELD_DEADLY, &game.panel.shield_deadly, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_SHIELD_DEADLY_TIME, @@ -381,42 +417,42 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_EXIT, &game.panel.exit, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EM_EXIT, &game.panel.em_exit, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_SP_EXIT, &game.panel.sp_exit, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_STEEL_EXIT, &game.panel.steel_exit, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EM_STEEL_EXIT, &game.panel.em_steel_exit, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EMC_MAGIC_BALL, &game.panel.emc_magic_ball, - TYPE_INTEGER, + TYPE_ELEMENT, }, { - GAME_CONTROL_EMC_MAGIC_BALL_TIME, - &game.panel.emc_magic_ball_time, - TYPE_INTEGER, + GAME_CONTROL_EMC_MAGIC_BALL_SWITCH, + &game.panel.emc_magic_ball_switch, + TYPE_ELEMENT, }, { GAME_CONTROL_LIGHT_SWITCH, &game.panel.light_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_LIGHT_SWITCH_TIME, @@ -426,7 +462,7 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_TIMEGATE_SWITCH, &game.panel.timegate_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_TIMEGATE_SWITCH_TIME, @@ -436,12 +472,12 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_SWITCHGATE_SWITCH, &game.panel.switchgate_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EMC_LENSES, &game.panel.emc_lenses, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EMC_LENSES_TIME, @@ -451,7 +487,7 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_EMC_MAGNIFIER, &game.panel.emc_magnifier, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_EMC_MAGNIFIER_TIME, @@ -461,7 +497,7 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_BALLOON_SWITCH, &game.panel.balloon_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_DYNABOMB_NUMBER, @@ -476,7 +512,7 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_DYNABOMB_POWER, &game.panel.dynabomb_power, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_PENGUINS, @@ -496,52 +532,52 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_ROBOT_WHEEL, &game.panel.robot_wheel, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_1, &game.panel.conveyor_belt_1, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_1_SWITCH, &game.panel.conveyor_belt_1_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_2, &game.panel.conveyor_belt_2, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_2_SWITCH, &game.panel.conveyor_belt_2_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_3, &game.panel.conveyor_belt_3, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_3_SWITCH, &game.panel.conveyor_belt_3_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_4, &game.panel.conveyor_belt_4, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_CONVEYOR_BELT_4_SWITCH, &game.panel.conveyor_belt_4_switch, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_MAGIC_WALL, &game.panel.magic_wall, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_MAGIC_WALL_TIME, @@ -551,34 +587,33 @@ static struct GameControlInfo game_controls[] = { GAME_CONTROL_BD_MAGIC_WALL, &game.panel.bd_magic_wall, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_DC_MAGIC_WALL, &game.panel.dc_magic_wall, - TYPE_INTEGER, + TYPE_ELEMENT, }, { GAME_CONTROL_PLAYER_NAME, &game.panel.player_name, - TYPE_INTEGER, + TYPE_STRING, }, { GAME_CONTROL_LEVEL_NAME, &game.panel.level_name, - TYPE_INTEGER, + TYPE_STRING, }, { GAME_CONTROL_LEVEL_AUTHOR, &game.panel.level_author, - TYPE_INTEGER, + TYPE_STRING, }, { -1, NULL, -1, - NULL } }; #endif @@ -1735,6 +1770,362 @@ static inline void InitField_WithBug2(int x, int y, boolean init_game) #if 1 +static int get_key_element_from_nr(int key_nr) +{ + int key_base_element = (key_nr >= STD_NUM_KEYS ? EL_EMC_KEY_5 - STD_NUM_KEYS : + level.game_engine_type == GAME_ENGINE_TYPE_EM ? + EL_EM_KEY_1 : EL_KEY_1); + + return key_base_element + key_nr; +} + +static int get_next_drop_element(struct PlayerInfo *player) +{ + return (player->inventory_size > 0 ? + player->inventory_element[player->inventory_size - 1] : + player->inventory_infinite_element != EL_UNDEFINED ? + player->inventory_infinite_element : + player->dynabombs_left > 0 ? + EL_DYNABOMB_PLAYER_1_ACTIVE + player->index_nr : + EL_UNDEFINED); +} + +static int get_drop_element_from_pos(struct PlayerInfo *player, int pos) +{ + /* pos >= 0: get element from bottom of the stack; + pos < 0: get element from top of the stack */ + + if (pos < 0) + { + int min_inventory_size = -pos; + int inventory_pos = player->inventory_size - min_inventory_size; + int min_dynabombs_left = min_inventory_size - player->inventory_size; + + return (player->inventory_size >= min_inventory_size ? + player->inventory_element[inventory_pos] : + player->inventory_infinite_element != EL_UNDEFINED ? + player->inventory_infinite_element : + player->dynabombs_left >= min_dynabombs_left ? + EL_DYNABOMB_PLAYER_1_ACTIVE + player->index_nr : + EL_UNDEFINED); + } + else + { + int min_dynabombs_left = pos + 1; + int min_inventory_size = pos + 1 - player->dynabombs_left; + int inventory_pos = pos - player->dynabombs_left; + + return (player->inventory_infinite_element != EL_UNDEFINED ? + player->inventory_infinite_element : + player->dynabombs_left >= min_dynabombs_left ? + EL_DYNABOMB_PLAYER_1_ACTIVE + player->index_nr : + player->inventory_size >= min_inventory_size ? + player->inventory_element[inventory_pos] : + EL_UNDEFINED); + } +} + +void InitGameControlValues() +{ + int i; + + for (i = 0; game_controls[i].nr != -1; i++) + { + int nr = game_controls[i].nr; + int type = game_controls[i].type; + struct TextPosInfo *pos = game_controls[i].pos; + + /* force update of game controls after initialization */ + game_control_value[nr] = last_game_control_value[nr] = -1; + + /* determine panel value width for later calculation of alignment */ + if (type == TYPE_INTEGER || type == TYPE_STRING) + { + pos->width = pos->size * getFontWidth(pos->font); + pos->height = getFontHeight(pos->font); + } + else if (type == TYPE_ELEMENT) + { + pos->width = pos->size; + pos->height = pos->size; + } + } +} + +void UpdateGameControlValues() +{ + int i, k; + int time = (level.time == 0 ? TimePlayed : TimeLeft); + int score = (local_player->LevelSolved ? local_player->score_final : + local_player->score); + + game_control_value[GAME_CONTROL_LEVEL_NUMBER] = level_nr; + game_control_value[GAME_CONTROL_GEMS] = local_player->gems_still_needed; + + game_control_value[GAME_CONTROL_INVENTORY_COUNT] = 0; + for (i = 0; i < MAX_NUM_KEYS; i++) + game_control_value[GAME_CONTROL_KEY_1 + i] = EL_EMPTY; + game_control_value[GAME_CONTROL_KEY_WHITE] = EL_EMPTY; + game_control_value[GAME_CONTROL_KEY_WHITE_COUNT] = 0; + + if (game.centered_player_nr == -1) + { + for (i = 0; i < MAX_PLAYERS; i++) + { + for (k = 0; k < MAX_NUM_KEYS; k++) + if (stored_player[i].key[k]) + game_control_value[GAME_CONTROL_KEY_1 + k] = + get_key_element_from_nr(k); + + game_control_value[GAME_CONTROL_INVENTORY_COUNT] += + stored_player[i].inventory_size; + + if (stored_player[i].num_white_keys > 0) + game_control_value[GAME_CONTROL_KEY_WHITE] = EL_DC_KEY_WHITE; + + game_control_value[GAME_CONTROL_KEY_WHITE_COUNT] += + stored_player[i].num_white_keys; + } + } + else + { + int player_nr = game.centered_player_nr; + + for (k = 0; k < MAX_NUM_KEYS; k++) + if (stored_player[player_nr].key[k]) + game_control_value[GAME_CONTROL_KEY_1 + k] = + get_key_element_from_nr(k); + + game_control_value[GAME_CONTROL_INVENTORY_COUNT] += + stored_player[player_nr].inventory_size; + + if (stored_player[player_nr].num_white_keys > 0) + game_control_value[GAME_CONTROL_KEY_WHITE] = EL_DC_KEY_WHITE; + + game_control_value[GAME_CONTROL_KEY_WHITE_COUNT] += + stored_player[player_nr].num_white_keys; + } + + for (i = 0; i < 8; i++) + { + game_control_value[GAME_CONTROL_INVENTORY_FIRST_1 + i] = + get_drop_element_from_pos(local_player, i); + game_control_value[GAME_CONTROL_INVENTORY_LAST_1 + i] = + get_drop_element_from_pos(local_player, -i - 1); + } + + game_control_value[GAME_CONTROL_SCORE] = score; + + game_control_value[GAME_CONTROL_TIME] = time; + + game_control_value[GAME_CONTROL_TIME_HH] = time / 3600; + game_control_value[GAME_CONTROL_TIME_MM] = (time / 60) % 60; + game_control_value[GAME_CONTROL_TIME_SS] = time % 60; + + game_control_value[GAME_CONTROL_SHIELD_NORMAL] = + (local_player->shield_normal_time_left > 0 ? EL_SHIELD_NORMAL_ACTIVE : + EL_EMPTY); + game_control_value[GAME_CONTROL_SHIELD_NORMAL_TIME] = + local_player->shield_normal_time_left; + game_control_value[GAME_CONTROL_SHIELD_DEADLY] = + (local_player->shield_deadly_time_left > 0 ? EL_SHIELD_DEADLY_ACTIVE : + EL_EMPTY); + game_control_value[GAME_CONTROL_SHIELD_DEADLY_TIME] = + local_player->shield_deadly_time_left; + + if (local_player->gems_still_needed > 0 || + local_player->sokobanfields_still_needed > 0 || + local_player->lights_still_needed > 0) + { + game_control_value[GAME_CONTROL_EXIT] = EL_EXIT_CLOSED; + game_control_value[GAME_CONTROL_EM_EXIT] = EL_EM_EXIT_CLOSED; + game_control_value[GAME_CONTROL_SP_EXIT] = EL_SP_EXIT_CLOSED; + game_control_value[GAME_CONTROL_STEEL_EXIT] = EL_STEEL_EXIT_CLOSED; + game_control_value[GAME_CONTROL_EM_STEEL_EXIT] = EL_EM_STEEL_EXIT_CLOSED; + } + else + { + game_control_value[GAME_CONTROL_EXIT] = EL_EXIT_OPEN; + game_control_value[GAME_CONTROL_EM_EXIT] = EL_EM_EXIT_OPEN; + game_control_value[GAME_CONTROL_SP_EXIT] = EL_SP_EXIT_OPEN; + game_control_value[GAME_CONTROL_STEEL_EXIT] = EL_STEEL_EXIT_OPEN; + game_control_value[GAME_CONTROL_EM_STEEL_EXIT] = EL_EM_STEEL_EXIT_OPEN; + } + + /* !!! TODO !!! */ + game_control_value[GAME_CONTROL_EMC_MAGIC_BALL] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_EMC_MAGIC_BALL_SWITCH] = EL_UNDEFINED; + + game_control_value[GAME_CONTROL_LIGHT_SWITCH] = + (game.light_time_left > 0 ? EL_LIGHT_SWITCH_ACTIVE : EL_LIGHT_SWITCH); + game_control_value[GAME_CONTROL_LIGHT_SWITCH_TIME] = game.light_time_left; + + game_control_value[GAME_CONTROL_TIMEGATE_SWITCH] = + (game.timegate_time_left > 0 ? EL_TIMEGATE_OPEN : EL_TIMEGATE_CLOSED); + game_control_value[GAME_CONTROL_TIMEGATE_SWITCH_TIME] = + game.timegate_time_left; + + /* !!! TODO !!! */ + game_control_value[GAME_CONTROL_SWITCHGATE_SWITCH] = EL_UNDEFINED; + + game_control_value[GAME_CONTROL_EMC_LENSES] = + (game.lenses_time_left > 0 ? EL_EMC_LENSES : EL_EMPTY); + game_control_value[GAME_CONTROL_EMC_LENSES_TIME] = game.lenses_time_left; + + game_control_value[GAME_CONTROL_EMC_MAGNIFIER] = + (game.magnify_time_left > 0 ? EL_EMC_MAGNIFIER : EL_EMPTY); + game_control_value[GAME_CONTROL_EMC_MAGNIFIER_TIME] = game.magnify_time_left; + + game_control_value[GAME_CONTROL_BALLOON_SWITCH] = + (game.wind_direction == MV_LEFT ? EL_BALLOON_SWITCH_LEFT : + game.wind_direction == MV_RIGHT ? EL_BALLOON_SWITCH_RIGHT : + game.wind_direction == MV_UP ? EL_BALLOON_SWITCH_UP : + game.wind_direction == MV_DOWN ? EL_BALLOON_SWITCH_DOWN : + EL_BALLOON_SWITCH_NONE); + + game_control_value[GAME_CONTROL_DYNABOMB_NUMBER] = + local_player->dynabomb_count; + game_control_value[GAME_CONTROL_DYNABOMB_SIZE] = + local_player->dynabomb_size; + game_control_value[GAME_CONTROL_DYNABOMB_POWER] = + (local_player->dynabomb_xl ? EL_DYNABOMB_INCREASE_POWER : EL_EMPTY); + + game_control_value[GAME_CONTROL_PENGUINS] = + local_player->friends_still_needed; + + game_control_value[GAME_CONTROL_SOKOBAN_OBJECTS] = + local_player->sokobanfields_still_needed; + game_control_value[GAME_CONTROL_SOKOBAN_FIELDS] = + local_player->sokobanfields_still_needed; + + /* !!! TODO !!! */ + game_control_value[GAME_CONTROL_ROBOT_WHEEL] = EL_UNDEFINED; + + /* !!! TODO !!! */ + game_control_value[GAME_CONTROL_CONVEYOR_BELT_1] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_1_SWITCH] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_2] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_2_SWITCH] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_3] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_3_SWITCH] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_4] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_CONVEYOR_BELT_4_SWITCH] = EL_UNDEFINED; + + /* !!! TODO !!! */ + game_control_value[GAME_CONTROL_MAGIC_WALL] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_MAGIC_WALL_TIME] = + game.magic_wall_time_left; + game_control_value[GAME_CONTROL_BD_MAGIC_WALL] = EL_UNDEFINED; + game_control_value[GAME_CONTROL_DC_MAGIC_WALL] = EL_UNDEFINED; + + game_control_value[GAME_CONTROL_PLAYER_NAME] = 0; + game_control_value[GAME_CONTROL_LEVEL_NAME] = 0; + game_control_value[GAME_CONTROL_LEVEL_AUTHOR] = 0; +} + +void DisplayGameControlValues() +{ + int i; + + for (i = 0; game_controls[i].nr != -1; i++) + { + int nr = game_controls[i].nr; + int type = game_controls[i].type; + struct TextPosInfo *pos = game_controls[i].pos; + int value = game_control_value[nr]; + int last_value = last_game_control_value[nr]; + int size = pos->size; + int font = pos->font; + + if (value == last_value) + continue; + + last_game_control_value[nr] = value; + +#if 0 + printf("::: value %d changed from %d to %d\n", nr, last_value, value); +#endif + + if (PANEL_DEACTIVATED(pos)) + continue; + + if (type == TYPE_INTEGER) + { + if (nr == GAME_CONTROL_LEVEL_NUMBER || nr == GAME_CONTROL_TIME) + { + boolean use_dynamic_size = (size == -1 ? TRUE : FALSE); + + if (use_dynamic_size) /* use dynamic number of digits */ + { + int value_change = (nr == GAME_CONTROL_LEVEL_NUMBER ? 100 : 1000); + int size1 = (nr == GAME_CONTROL_LEVEL_NUMBER ? 2 : 3); + int size2 = size1 + 1; + int font1 = pos->font; + int font2 = pos->font_alt; + + size = (value < value_change ? size1 : size2); + font = (value < value_change ? font1 : font2); + + /* clear background if value just changed its size (dynamic digits) */ + if ((last_value < value_change) != (value < value_change)) + { + int width1 = size1 * getFontWidth(font1); + int width2 = size2 * getFontWidth(font2); + int max_width = MAX(width1, width2); + int max_height = MAX(getFontHeight(font1), getFontHeight(font2)); + + pos->width = max_width; + + ClearRectangleOnBackground(drawto, PANEL_XPOS(pos), PANEL_YPOS(pos), + max_width, max_height); + } + } + + pos->width = size * getFontWidth(font); + } + + DrawText(PANEL_XPOS(pos), PANEL_YPOS(pos), int2str(value, size), font); + } + else if (type == TYPE_ELEMENT) + { + int dst_x = PANEL_XPOS(pos); + int dst_y = PANEL_YPOS(pos); + + if (value == EL_UNDEFINED || value == EL_EMPTY) + { + int src_x = DOOR_GFX_PAGEX5 + ALIGNED_TEXT_XPOS(pos); + int src_y = DOOR_GFX_PAGEY1 + ALIGNED_TEXT_YPOS(pos); + + BlitBitmap(graphic_info[IMG_GLOBAL_DOOR].bitmap, drawto, src_x, src_y, + size, size, dst_x, dst_y); + } + else + { + int graphic = el2doorimg(value); + + DrawSizedGraphicExt(drawto, dst_x, dst_y, graphic, size); + } + } + else if (type == TYPE_STRING) + { + char *s = (nr == GAME_CONTROL_PLAYER_NAME ? setup.player_name : + nr == GAME_CONTROL_LEVEL_NAME ? level.name : + nr == GAME_CONTROL_LEVEL_AUTHOR ? level.author : NULL); + + if (s != NULL) + { + char *s_cut = getStringCopyN(s, size); + + DrawText(PANEL_XPOS(pos), PANEL_YPOS(pos), s_cut, font); + + free(s_cut); + } + } + + redraw_mask |= REDRAW_DOOR_1; + } +} + void DrawGameValue_Emeralds(int value) { struct TextPosInfo *pos = &game.panel.gems; @@ -1744,7 +2135,11 @@ void DrawGameValue_Emeralds(int value) int font_nr = FONT_TEXT_2; #endif int font_width = getFontWidth(font_nr); - int chars = pos->chars; + int chars = pos->size; + +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif if (PANEL_DEACTIVATED(pos)) return; @@ -1756,14 +2151,18 @@ void DrawGameValue_Emeralds(int value) void DrawGameValue_Dynamite(int value) { - struct TextPosInfo *pos = &game.panel.inventory; + struct TextPosInfo *pos = &game.panel.inventory_count; #if 1 int font_nr = pos->font; #else int font_nr = FONT_TEXT_2; #endif int font_width = getFontWidth(font_nr); - int chars = pos->chars; + int chars = pos->size; + +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif if (PANEL_DEACTIVATED(pos)) return; @@ -1782,7 +2181,11 @@ void DrawGameValue_Score(int value) int font_nr = FONT_TEXT_2; #endif int font_width = getFontWidth(font_nr); - int chars = pos->chars; + int chars = pos->size; + +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif if (PANEL_DEACTIVATED(pos)) return; @@ -1798,7 +2201,7 @@ void DrawGameValue_Time(int value) static int last_value = -1; int chars1 = 3; int chars2 = 4; - int chars = pos->chars; + int chars = pos->size; #if 1 int font1_nr = pos->font; int font2_nr = pos->font_alt; @@ -1809,6 +2212,10 @@ void DrawGameValue_Time(int value) int font_nr = font1_nr; boolean use_dynamic_chars = (chars == -1 ? TRUE : FALSE); +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif + if (PANEL_DEACTIVATED(pos)) return; @@ -1844,7 +2251,7 @@ void DrawGameValue_Level(int value) struct TextPosInfo *pos = &game.panel.level_number; int chars1 = 2; int chars2 = 3; - int chars = pos->chars; + int chars = pos->size; #if 1 int font1_nr = pos->font; int font2_nr = pos->font_alt; @@ -1855,6 +2262,10 @@ void DrawGameValue_Level(int value) int font_nr = font1_nr; boolean use_dynamic_chars = (chars == -1 ? TRUE : FALSE); +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif + if (PANEL_DEACTIVATED(pos)) return; @@ -1879,6 +2290,10 @@ void DrawGameValue_Keys(int key[MAX_NUM_KEYS]) #endif int i; +#if 1 + return; /* !!! USE NEW STUFF !!! */ +#endif + #if 0 if (PANEL_DEACTIVATED(pos)) return; @@ -1903,7 +2318,7 @@ void DrawGameValue_Keys(int key[MAX_NUM_KEYS]) #if 1 struct TextPosInfo *pos = &game.panel.key[i]; #endif - int src_x = DOOR_GFX_PAGEX5 + 18; + int src_x = DOOR_GFX_PAGEX5 + 18 + (i % 4) * MINI_TILEX; int src_y = DOOR_GFX_PAGEY1 + 123; #if 1 int dst_x = PANEL_XPOS(pos); @@ -1984,7 +2399,7 @@ void DrawGameValue_Dynamite(int value) int font_nr = FONT_TEXT_2; int xpos = (3 * 14 - 3 * getFontWidth(font_nr)) / 2; - if (PANEL_DEACTIVATED(game.panel.inventory)) + if (PANEL_DEACTIVATED(game.panel.inventory_count)) return; DrawText(DX_DYNAMITE + xpos, DY_DYNAMITE, int2str(value, 3), font_nr); @@ -2095,6 +2510,12 @@ void DrawAllGameValues(int emeralds, int dynamite, int score, int time, } void DrawGameDoorValues() +{ + UpdateGameControlValues(); + DisplayGameControlValues(); +} + +void DrawGameDoorValues_OLD() { int time_value = (level.time == 0 ? TimePlayed : TimeLeft); int dynamite_value = 0; @@ -2563,6 +2984,13 @@ static void InitGameEngine() recursion_loop_depth = 0; recursion_loop_detected = FALSE; recursion_loop_element = EL_UNDEFINED; + + /* ---------- initialize graphics engine ---------------------------------- */ + game.scroll_delay_value = + (game.forced_scroll_delay_value != -1 ? game.forced_scroll_delay_value : + setup.scroll_delay ? setup.scroll_delay_value : 0); + game.scroll_delay_value = + MIN(MAX(MIN_SCROLL_DELAY, game.scroll_delay_value), MAX_SCROLL_DELAY); } int get_num_special_action(int element, int action_first, int action_last) @@ -2602,12 +3030,15 @@ void InitGame() boolean emulate_bd = TRUE; /* unless non-BOULDERDASH elements found */ boolean emulate_sb = TRUE; /* unless non-SOKOBAN elements found */ boolean emulate_sp = TRUE; /* unless non-SUPAPLEX elements found */ +#if 0 boolean do_fading = (game_status == GAME_MODE_MAIN); +#endif int i, j, x, y; game_status = GAME_MODE_PLAYING; InitGameEngine(); + InitGameControlValues(); /* don't play tapes over network */ network_playing = (options.network && !tape.playing); @@ -3088,7 +3519,8 @@ void InitGame() content = element_info[element].change_page[i].target_element; is_player = ELEM_IS_PLAYER(content); - if (is_player && (found_rating < 3 || element < found_element)) + if (is_player && (found_rating < 3 || + (found_rating == 3 && element < found_element))) { start_x = x; start_y = y; @@ -3105,7 +3537,8 @@ void InitGame() content = element_info[element].content.e[xx][yy]; is_player = ELEM_IS_PLAYER(content); - if (is_player && (found_rating < 2 || element < found_element)) + if (is_player && (found_rating < 2 || + (found_rating == 2 && element < found_element))) { start_x = x + xx - 1; start_y = y + yy - 1; @@ -3125,7 +3558,8 @@ void InitGame() is_player = ELEM_IS_PLAYER(content); - if (is_player && (found_rating < 1 || element < found_element)) + if (is_player && (found_rating < 1 || + (found_rating == 1 && element < found_element))) { start_x = x + xx - 1; start_y = y + yy - 1; @@ -3161,8 +3595,24 @@ void InitGame() if (!game.restart_level) CloseDoor(DOOR_CLOSE_1); +#if 1 + if (level_editor_test_game) + FadeSkipNextFadeIn(); + else + FadeSetEnterScreen(); +#else + if (level_editor_test_game) + fading = fading_none; + else + fading = menu.destination; +#endif + +#if 1 + FadeOut(REDRAW_FIELD); +#else if (do_fading) FadeOut(REDRAW_FIELD); +#endif /* !!! FIX THIS (START) !!! */ if (level.game_engine_type == GAME_ENGINE_TYPE_EM) @@ -3189,10 +3639,14 @@ void InitGame() } /* !!! FIX THIS (END) !!! */ +#if 1 + FadeIn(REDRAW_FIELD); +#else if (do_fading) FadeIn(REDRAW_FIELD); BackToFront(); +#endif if (!game.restart_level) { @@ -3515,8 +3969,15 @@ void GameWon() time = time_final; score = score_final; +#if 1 + game_control_value[GAME_CONTROL_TIME] = time; + game_control_value[GAME_CONTROL_SCORE] = score; + + DisplayGameControlValues(); +#else DrawGameValue_Time(time); DrawGameValue_Score(score); +#endif } if (level.game_engine_type == GAME_ENGINE_TYPE_RND) @@ -3590,8 +4051,15 @@ void GameWon() time += time_count_steps * time_count_dir; score += time_count_steps * level.score[SC_TIME_BONUS]; +#if 1 + game_control_value[GAME_CONTROL_TIME] = time; + game_control_value[GAME_CONTROL_SCORE] = score; + + DisplayGameControlValues(); +#else DrawGameValue_Time(time); DrawGameValue_Score(score); +#endif if (time == time_final) StopSound(SND_GAME_LEVELTIME_BONUS); @@ -3643,14 +4111,20 @@ void GameEnd() { game_status = GAME_MODE_MAIN; +#if 1 + DrawAndFadeInMainMenu(REDRAW_FIELD); +#else DrawMainMenu(); +#endif return; } if (!local_player->LevelSolved_SaveScore) { +#if 1 FadeOut(REDRAW_FIELD); +#endif game_status = GAME_MODE_MAIN; @@ -3682,7 +4156,9 @@ void GameEnd() } else { +#if 1 FadeOut(REDRAW_FIELD); +#endif game_status = GAME_MODE_MAIN; @@ -4163,12 +4639,14 @@ void DrawRelocateScreen(int old_x, int old_y, int x, int y, int move_dir, if (quick_relocation) { - int offset = (setup.scroll_delay ? 3 : 0); + int offset = game.scroll_delay_value; if (!IN_VIS_FIELD(SCREENX(x), SCREENY(y)) || center_screen) { - if (center_screen) + if (!level.shifted_relocation || center_screen) { + /* quick relocation (without scrolling), with centering of screen */ + scroll_x = (x < SBX_Left + MIDPOSX ? SBX_Left : x > SBX_Right + MIDPOSX ? SBX_Right : x - MIDPOSX); @@ -4203,6 +4681,8 @@ void DrawRelocateScreen(int old_x, int old_y, int x, int y, int move_dir, } else { + /* quick relocation (without scrolling), inside visible screen area */ + if ((move_dir == MV_LEFT && scroll_x > x - MIDPOSX + offset) || (move_dir == MV_RIGHT && scroll_x < x - MIDPOSX - offset)) scroll_x = x - MIDPOSX + (scroll_x < x - MIDPOSX ? -offset : +offset); @@ -4224,6 +4704,49 @@ void DrawRelocateScreen(int old_x, int old_y, int x, int y, int move_dir, } else { +#if 1 + int scroll_xx, scroll_yy; + + if (!level.shifted_relocation || center_screen) + { + /* visible relocation (with scrolling), with centering of screen */ + + scroll_xx = (x < SBX_Left + MIDPOSX ? SBX_Left : + x > SBX_Right + MIDPOSX ? SBX_Right : + x - MIDPOSX); + + scroll_yy = (y < SBY_Upper + MIDPOSY ? SBY_Upper : + y > SBY_Lower + MIDPOSY ? SBY_Lower : + y - MIDPOSY); + } + else + { + /* visible relocation (with scrolling), but do not center screen */ + + int center_scroll_x = (old_x < SBX_Left + MIDPOSX ? SBX_Left : + old_x > SBX_Right + MIDPOSX ? SBX_Right : + old_x - MIDPOSX); + + int center_scroll_y = (old_y < SBY_Upper + MIDPOSY ? SBY_Upper : + old_y > SBY_Lower + MIDPOSY ? SBY_Lower : + old_y - MIDPOSY); + + int offset_x = x + (scroll_x - center_scroll_x); + int offset_y = y + (scroll_y - center_scroll_y); + + scroll_xx = (offset_x < SBX_Left + MIDPOSX ? SBX_Left : + offset_x > SBX_Right + MIDPOSX ? SBX_Right : + offset_x - MIDPOSX); + + scroll_yy = (offset_y < SBY_Upper + MIDPOSY ? SBY_Upper : + offset_y > SBY_Lower + MIDPOSY ? SBY_Lower : + offset_y - MIDPOSY); + } + +#else + + /* visible relocation (with scrolling), with centering of screen */ + int scroll_xx = (x < SBX_Left + MIDPOSX ? SBX_Left : x > SBX_Right + MIDPOSX ? SBX_Right : x - MIDPOSX); @@ -4231,6 +4754,7 @@ void DrawRelocateScreen(int old_x, int old_y, int x, int y, int move_dir, int scroll_yy = (y < SBY_Upper + MIDPOSY ? SBY_Upper : y > SBY_Lower + MIDPOSY ? SBY_Lower : y - MIDPOSY); +#endif ScrollScreen(NULL, SCROLL_GO_ON); /* scroll last frame to full tile */ @@ -8969,7 +9493,13 @@ static void ExecuteCustomElementAction(int x, int y, int element, int page) { TimeLeft = action_arg_number_new; +#if 1 + game_control_value[GAME_CONTROL_TIME] = TimeLeft; + + DisplayGameControlValues(); +#else DrawGameValue_Time(TimeLeft); +#endif if (!TimeLeft && setup.time_limit) for (i = 0; i < MAX_PLAYERS; i++) @@ -8983,7 +9513,13 @@ static void ExecuteCustomElementAction(int x, int y, int element, int page) { local_player->score = action_arg_number_new; +#if 1 + game_control_value[GAME_CONTROL_SCORE] = local_player->score; + + DisplayGameControlValues(); +#else DrawGameValue_Score(local_player->score); +#endif break; } @@ -8992,7 +9528,13 @@ static void ExecuteCustomElementAction(int x, int y, int element, int page) { local_player->gems_still_needed = action_arg_number_new; +#if 1 + game_control_value[GAME_CONTROL_GEMS] = local_player->gems_still_needed; + + DisplayGameControlValues(); +#else DrawGameValue_Emeralds(local_player->gems_still_needed); +#endif break; } @@ -10267,7 +10809,13 @@ static void CheckLevelTime() if (TimeLeft <= 10 && setup.time_limit) PlaySound(SND_GAME_RUNNING_OUT_OF_TIME); +#if 1 + game_control_value[GAME_CONTROL_TIME] = TimeLeft; + + DisplayGameControlValues(); +#else DrawGameValue_Time(TimeLeft); +#endif if (!TimeLeft && setup.time_limit) { @@ -10278,8 +10826,17 @@ static void CheckLevelTime() KillPlayer(&stored_player[i]); } } +#if 1 + else if (level.time == 0 && !AllPlayersGone) /* level w/o time limit */ + { + game_control_value[GAME_CONTROL_TIME] = TimePlayed; + + DisplayGameControlValues(); + } +#else else if (level.time == 0 && !AllPlayersGone) /* level w/o time limit */ DrawGameValue_Time(TimePlayed); +#endif level.native_em_level->lev->time = (level.time == 0 ? TimePlayed : TimeLeft); @@ -10288,6 +10845,8 @@ static void CheckLevelTime() if (tape.recording || tape.playing) DrawVideoDisplay(VIDEO_STATE_TIME_ON, TapeTime); } + + DrawGameDoorValues(); } void AdvanceFrameAndPlayerCounters(int player_nr) @@ -11703,7 +12262,7 @@ boolean MovePlayer(struct PlayerInfo *player, int dx, int dy) #endif { int old_scroll_x = scroll_x, old_scroll_y = scroll_y; - int offset = (setup.scroll_delay ? 3 : 0); + int offset = game.scroll_delay_value; if (!IN_VIS_FIELD(SCREENX(jx), SCREENY(jy))) { @@ -12003,14 +12562,29 @@ void ScrollPlayer(struct PlayerInfo *player, int mode) if (TimeLeft <= 10 && setup.time_limit) PlaySound(SND_GAME_RUNNING_OUT_OF_TIME); +#if 1 + game_control_value[GAME_CONTROL_TIME] = TimeLeft; + + DisplayGameControlValues(); +#else DrawGameValue_Time(TimeLeft); +#endif if (!TimeLeft && setup.time_limit) for (i = 0; i < MAX_PLAYERS; i++) KillPlayer(&stored_player[i]); } +#if 1 + else if (level.time == 0 && !AllPlayersGone) /* level w/o time limit */ + { + game_control_value[GAME_CONTROL_TIME] = TimePlayed; + + DisplayGameControlValues(); + } +#else else if (level.time == 0 && !AllPlayersGone) /* level w/o time limit */ DrawGameValue_Time(TimePlayed); +#endif } if (tape.single_step && tape.recording && !tape.pausing && @@ -13059,7 +13633,14 @@ int DigField(struct PlayerInfo *player, else if (element == EL_EXTRA_TIME && level.time > 0) { TimeLeft += level.extra_time; + +#if 1 + game_control_value[GAME_CONTROL_TIME] = TimeLeft; + + DisplayGameControlValues(); +#else DrawGameValue_Time(TimeLeft); +#endif } else if (element == EL_SHIELD_NORMAL || element == EL_SHIELD_DEADLY) { @@ -13138,7 +13719,13 @@ int DigField(struct PlayerInfo *player, if (local_player->gems_still_needed < 0) local_player->gems_still_needed = 0; +#if 1 + game_control_value[GAME_CONTROL_GEMS] = local_player->gems_still_needed; + + DisplayGameControlValues(); +#else DrawGameValue_Emeralds(local_player->gems_still_needed); +#endif } RaiseScoreElement(element); @@ -13382,7 +13969,14 @@ int DigField(struct PlayerInfo *player, if (level.time > 0 || level.use_time_orb_bug) { TimeLeft += level.time_orb_time; + +#if 1 + game_control_value[GAME_CONTROL_TIME] = TimeLeft; + + DisplayGameControlValues(); +#else DrawGameValue_Time(TimeLeft); +#endif } ResetGfxAnimation(x, y); @@ -13554,6 +14148,9 @@ boolean DropElement(struct PlayerInfo *player) int dropx = player->jx, dropy = player->jy; int drop_direction = player->MovDir; int drop_side = drop_direction; +#if 1 + int drop_element = get_next_drop_element(player); +#else int drop_element = (player->inventory_size > 0 ? player->inventory_element[player->inventory_size - 1] : player->inventory_infinite_element != EL_UNDEFINED ? @@ -13561,6 +14158,7 @@ boolean DropElement(struct PlayerInfo *player) player->dynabombs_left > 0 ? EL_DYNABOMB_PLAYER_1_ACTIVE + player->index_nr : EL_UNDEFINED); +#endif player->is_dropping_pressed = TRUE; @@ -14004,7 +14602,13 @@ void RaiseScore(int value) { local_player->score += value; +#if 1 + game_control_value[GAME_CONTROL_SCORE] = local_player->score; + + DisplayGameControlValues(); +#else DrawGameValue_Score(local_player->score); +#endif } void RaiseScoreElement(int element) @@ -14099,13 +14703,31 @@ void RequestQuitGameExt(boolean skip_request, boolean quick_quit, char *message) { if (quick_quit) { +#if 1 + +#if 1 + FadeSkipNextFadeIn(); +#else + fading = fading_none; +#endif + +#else + OpenDoor(DOOR_CLOSE_1); +#endif + game_status = GAME_MODE_MAIN; +#if 1 + DrawAndFadeInMainMenu(REDRAW_FIELD); +#else DrawMainMenu(); +#endif } else { +#if 0 FadeOut(REDRAW_FIELD); +#endif game_status = GAME_MODE_MAIN;