X-Git-Url: https://git.artsoft.org/?p=rocksndiamonds.git;a=blobdiff_plain;f=src%2Finit.c;h=62a5d0ff860865ef4d203e8b71f2b30da8b23ff7;hp=079ece2f796b6f6071b82fb5e413329393cf90ab;hb=HEAD;hpb=3a9fc7d57928ecf8fbd12c525bcd2cb74dd5fc2d diff --git a/src/init.c b/src/init.c index 079ece2f..62a5d0ff 100644 --- a/src/init.c +++ b/src/init.c @@ -34,11 +34,28 @@ #define CONFIG_TOKEN_FONT_INITIAL "font.initial" +#define CONFIG_TOKEN_GLOBAL_BUSY_INITIAL "global.busy_initial" #define CONFIG_TOKEN_GLOBAL_BUSY "global.busy" +#define CONFIG_TOKEN_GLOBAL_BUSY_PLAYFIELD "global.busy_playfield" +#define CONFIG_TOKEN_BACKGROUND "background" +#define CONFIG_TOKEN_BACKGROUND_LOADING_INITIAL "background.LOADING_INITIAL" +#define CONFIG_TOKEN_BACKGROUND_LOADING "background.LOADING" + +#define INITIAL_IMG_GLOBAL_BUSY_INITIAL 0 +#define INITIAL_IMG_GLOBAL_BUSY 1 +#define INITIAL_IMG_GLOBAL_BUSY_PLAYFIELD 2 + +#define NUM_INITIAL_IMAGES_BUSY 3 + +#define INITIAL_IMG_BACKGROUND 3 +#define INITIAL_IMG_BACKGROUND_LOADING_INITIAL 4 +#define INITIAL_IMG_BACKGROUND_LOADING 5 + +#define NUM_INITIAL_IMAGES 6 static struct FontBitmapInfo font_initial[NUM_INITIAL_FONTS]; -static struct GraphicInfo anim_initial; +static struct GraphicInfo image_initial[NUM_INITIAL_IMAGES]; static int copy_properties[][5] = { @@ -93,38 +110,75 @@ static int copy_properties[][5] = static int get_graphic_parameter_value(char *, char *, int); -static void DrawInitAnim(void) +static int getLoadingBackgroundImage(int graphic) +{ + return getImageFromGraphicOrDefault(graphic, INITIAL_IMG_BACKGROUND); +} + +static void SetLoadingWindowBackgroundImage(int graphic) +{ + SetBackgroundImage(getLoadingBackgroundImage(graphic), REDRAW_ALL); +} + +static void SetLoadingBackgroundImage(void) { struct GraphicInfo *graphic_info_last = graphic_info; - int graphic = 0; - static unsigned int action_delay = 0; - unsigned int action_delay_value = GameFrameDelay; + int background_image = (game_status_last_screen == -1 ? + INITIAL_IMG_BACKGROUND_LOADING_INITIAL : + INITIAL_IMG_BACKGROUND_LOADING); + + graphic_info = image_initial; + + SetDrawDeactivationMask(REDRAW_NONE); + SetDrawBackgroundMask(REDRAW_ALL); + + SetLoadingWindowBackgroundImage(background_image); + + graphic_info = graphic_info_last; +} + +static void DrawInitAnim(boolean only_when_loading) +{ + struct GraphicInfo *graphic_info_last = graphic_info; + int graphic = (game_status_last_screen == -1 ? + INITIAL_IMG_GLOBAL_BUSY_INITIAL : + game_status == GAME_MODE_LOADING ? + INITIAL_IMG_GLOBAL_BUSY : + INITIAL_IMG_GLOBAL_BUSY_PLAYFIELD); + struct MenuPosInfo *busy = (game_status_last_screen == -1 ? + &init_last.busy_initial : + game_status == GAME_MODE_LOADING ? + &init_last.busy : + &init_last.busy_playfield); + static DelayCounter action_delay = { 0 }; int sync_frame = FrameCounter; int x, y; + action_delay.value = GameFrameDelay; + // prevent OS (Windows) from complaining about program not responding CheckQuitEvent(); - if (game_status != GAME_MODE_LOADING) + if (game_status != GAME_MODE_LOADING && only_when_loading) return; - if (anim_initial.bitmap == NULL || window == NULL) + if (image_initial[graphic].bitmap == NULL || window == NULL) return; - if (!DelayReached(&action_delay, action_delay_value)) + if (!DelayReached(&action_delay)) return; - if (init_last.busy.x == -1) - init_last.busy.x = WIN_XSIZE / 2; - if (init_last.busy.y == -1) - init_last.busy.y = WIN_YSIZE / 2; + if (busy->x == -1) + busy->x = (game_status == GAME_MODE_LOADING ? WIN_XSIZE / 2 : SXSIZE / 2); + if (busy->y == -1) + busy->y = (game_status == GAME_MODE_LOADING ? WIN_YSIZE / 2 : SYSIZE / 2); - x = ALIGNED_TEXT_XPOS(&init_last.busy); - y = ALIGNED_TEXT_YPOS(&init_last.busy); + x = (game_status == GAME_MODE_LOADING ? 0 : SX) + ALIGNED_TEXT_XPOS(busy); + y = (game_status == GAME_MODE_LOADING ? 0 : SY) + ALIGNED_TEXT_YPOS(busy); - graphic_info = &anim_initial; // graphic == 0 => anim_initial + graphic_info = image_initial; - if (sync_frame % anim_initial.anim_delay == 0) + if (sync_frame % image_initial[graphic].anim_delay == 0) { Bitmap *src_bitmap; int src_x, src_y; @@ -132,8 +186,12 @@ static void DrawInitAnim(void) int height = graphic_info[graphic].height; int frame = getGraphicAnimationFrame(graphic, sync_frame); + ClearRectangleOnBackground(drawto, x, y, width, height); + getFixedGraphicSource(graphic, frame, &src_bitmap, &src_x, &src_y); - BlitBitmap(src_bitmap, window, src_x, src_y, width, height, x, y); + BlitBitmapMasked(src_bitmap, drawto, src_x, src_y, width, height, x, y); + + BlitBitmap(drawto, window, x, y, width, height, x, y); } graphic_info = graphic_info_last; @@ -323,7 +381,7 @@ void InitImageTextures(void) CreateImageTextures(texture_graphics[i]); } -static int getFontBitmapID(int font_nr) +static int getFontSpecialSuffix(void) { int special = -1; @@ -336,6 +394,13 @@ static int getFontBitmapID(int font_nr) else if (game_status == GAME_MODE_PSEUDO_TYPENAMES) special = GFX_SPECIAL_ARG_NAMES; + return special; +} + +static int getFontBitmapID(int font_nr) +{ + int special = getFontSpecialSuffix(); + if (special != -1) return font_info[font_nr].special_bitmap_id[special]; else @@ -353,6 +418,22 @@ static int getFontFromToken(char *token) return FONT_INITIAL_1; } +static char *getTokenFromFont(int font_nr) +{ + static char *token = NULL; + int special = getFontSpecialSuffix(); + + checked_free(token); + + if (special != -1) + token = getStringCat2(font_info[font_nr].token_name, + special_suffix_info[special].suffix); + else + token = getStringCopy(font_info[font_nr].token_name); + + return token; +} + static void InitFontGraphicInfo(void) { static struct FontBitmapInfo *font_bitmap_info = NULL; @@ -364,7 +445,7 @@ static void InitFontGraphicInfo(void) if (graphic_info == NULL) // still at startup phase { InitFontInfo(font_initial, NUM_INITIAL_FONTS, - getFontBitmapID, getFontFromToken); + getFontBitmapID, getFontFromToken, getTokenFromFont); return; } @@ -589,7 +670,7 @@ static void InitFontGraphicInfo(void) } InitFontInfo(font_bitmap_info, num_font_bitmaps, - getFontBitmapID, getFontFromToken); + getFontBitmapID, getFontFromToken, getTokenFromFont); } static void InitGlobalAnimGraphicInfo(void) @@ -1256,19 +1337,27 @@ static int get_graphic_parameter_value(char *value_raw, char *suffix, int type) return -1; } -static int get_scaled_graphic_width(int graphic) +static int get_scaled_graphic_width(Bitmap *src_bitmap, int graphic) { int original_width = getOriginalImageWidthFromImageID(graphic); int scale_up_factor = graphic_info[graphic].scale_up_factor; + // only happens when loaded outside artwork system (like "global.busy") + if (graphic_info == image_initial && src_bitmap) + original_width = src_bitmap->width; + return original_width * scale_up_factor; } -static int get_scaled_graphic_height(int graphic) +static int get_scaled_graphic_height(Bitmap *src_bitmap, int graphic) { int original_height = getOriginalImageHeightFromImageID(graphic); int scale_up_factor = graphic_info[graphic].scale_up_factor; + // only happens when loaded outside artwork system (like "global.busy") + if (graphic_info == image_initial && src_bitmap) + original_height = src_bitmap->height; + return original_height * scale_up_factor; } @@ -1323,6 +1412,7 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, g->sort_priority = 0; // default for title screens g->class = 0; g->style = STYLE_DEFAULT; + g->alpha = -1; g->bitmaps = src_bitmaps; g->bitmap = src_bitmap; @@ -1352,8 +1442,8 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, if (g->use_image_size) { // set new default bitmap size (with scaling, but without small images) - g->width = get_scaled_graphic_width(graphic); - g->height = get_scaled_graphic_height(graphic); + g->width = get_scaled_graphic_width(src_bitmap, graphic); + g->height = get_scaled_graphic_height(src_bitmap, graphic); } // optional width and height of each animation frame @@ -1400,15 +1490,8 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, if (src_bitmap) { // get final bitmap size (with scaling, but without small images) - int src_image_width = get_scaled_graphic_width(graphic); - int src_image_height = get_scaled_graphic_height(graphic); - - if (src_image_width == 0 || src_image_height == 0) - { - // only happens when loaded outside artwork system (like "global.busy") - src_image_width = src_bitmap->width; - src_image_height = src_bitmap->height; - } + int src_image_width = get_scaled_graphic_width(src_bitmap, graphic); + int src_image_height = get_scaled_graphic_height(src_bitmap, graphic); if (parameter[GFX_ARG_TILE_SIZE] != ARG_UNDEFINED_VALUE) { @@ -1503,6 +1586,9 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, // animation synchronized with global frame counter, not move position g->anim_global_sync = parameter[GFX_ARG_GLOBAL_SYNC]; + // animation synchronized with global anim frame counter, not move position + g->anim_global_anim_sync = parameter[GFX_ARG_GLOBAL_ANIM_SYNC]; + // optional element for cloning crumble graphics if (parameter[GFX_ARG_CRUMBLED_LIKE] != ARG_UNDEFINED_VALUE) g->crumbled_like = parameter[GFX_ARG_CRUMBLED_LIKE]; @@ -1563,7 +1649,7 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, g->draw_yoffset = parameter[GFX_ARG_DRAW_YOFFSET]; // use a different default value for global animations and toons - if ((graphic >= IMG_GFX_GLOBAL_ANIM_1 && graphic <= IMG_GFX_GLOBAL_ANIM_8) || + if ((graphic >= IMG_GFX_GLOBAL_ANIM_1 && graphic <= IMG_GFX_GLOBAL_ANIM_32) || (graphic >= IMG_TOON_1 && graphic <= IMG_TOON_20)) g->draw_masked = TRUE; @@ -1601,12 +1687,20 @@ static void set_graphic_parameters_ext(int graphic, int *parameter, g->class = parameter[GFX_ARG_CLASS]; if (parameter[GFX_ARG_STYLE] != ARG_UNDEFINED_VALUE) g->style = parameter[GFX_ARG_STYLE]; + if (parameter[GFX_ARG_ALPHA] != ARG_UNDEFINED_VALUE) + g->alpha = parameter[GFX_ARG_ALPHA]; // this is only used for drawing menu buttons and text g->active_xoffset = parameter[GFX_ARG_ACTIVE_XOFFSET]; g->active_yoffset = parameter[GFX_ARG_ACTIVE_YOFFSET]; g->pressed_xoffset = parameter[GFX_ARG_PRESSED_XOFFSET]; g->pressed_yoffset = parameter[GFX_ARG_PRESSED_YOFFSET]; + + // this is only used for drawing stacked global animations + g->stacked_xfactor = parameter[GFX_ARG_STACKED_XFACTOR]; + g->stacked_yfactor = parameter[GFX_ARG_STACKED_YFACTOR]; + g->stacked_xoffset = parameter[GFX_ARG_STACKED_XOFFSET]; + g->stacked_yoffset = parameter[GFX_ARG_STACKED_YOFFSET]; } static void set_graphic_parameters(int graphic) @@ -1694,6 +1788,8 @@ static void InitGraphicInfo(void) IMG_BACKGROUND_REQUEST, IMG_BACKGROUND, + IMG_BACKGROUND_LOADING_INITIAL, + IMG_BACKGROUND_LOADING, IMG_BACKGROUND_TITLE_INITIAL, IMG_BACKGROUND_TITLE, IMG_BACKGROUND_MAIN, @@ -1701,6 +1797,7 @@ static void InitGraphicInfo(void) IMG_BACKGROUND_LEVELS, IMG_BACKGROUND_LEVELNR, IMG_BACKGROUND_SCORES, + IMG_BACKGROUND_SCOREINFO, IMG_BACKGROUND_EDITOR, IMG_BACKGROUND_INFO, IMG_BACKGROUND_INFO_ELEMENTS, @@ -1882,6 +1979,16 @@ static void InitGraphicCompatibilityInfo(void) // process all images which default to same image as "global.door" if (strEqual(fi->default_filename, fi_global_door->default_filename)) { + // skip all images that are cloned from images that default to same + // image as "global.door", but that are redefined to something else + if (graphic_info[i].clone_from != -1) + { + int cloned_graphic = graphic_info[i].clone_from; + + if (getImageListEntryFromImageID(cloned_graphic)->redefined) + continue; + } + #if 0 Debug("init:InitGraphicCompatibilityInfo", "special treatment needed for token '%s'", fi->token); @@ -1894,6 +2001,70 @@ static void InitGraphicCompatibilityInfo(void) } } + // special compatibility handling for "Snake Bite" graphics set + if (strPrefix(leveldir_current->identifier, "snake_bite")) + { + Bitmap *bitmap = graphic_info[IMG_BACKGROUND_SCORES].bitmap; + + BlitBitmap(bitmap, bitmap, 18, 66, 32, 480, 50, 66); + BlitBitmap(bitmap, bitmap, 466, 66, 32, 480, 434, 66); + + ClearRectangle(bitmap, 2, 66, 32, 480); + ClearRectangle(bitmap, 514, 66, 32, 480); + } + + // special compatibility handling for "Jue" graphics sets (2007 and 2019) + boolean supports_score_info = (menu.draw_xoffset[GAME_MODE_SCOREINFO] != 0); + if (strPrefix(artwork.gfx_current_identifier, "jue") && !supports_score_info) + { + int font_title[] = + { + FONT_TITLE_1, + FONT_TITLE_2, + + -1 + }; + int font_text[] = + { + FONT_TEXT_1, + FONT_TEXT_2, + FONT_TEXT_3, + FONT_TEXT_4, + + -1 + }; + int mode_old = GAME_MODE_SCORES; + int mode_new = GAME_MODE_SCOREINFO; + int i, j; + + // adjust title screens on score info page + for (i = 0; font_title[i] != -1; i++) + { + struct FontInfo *fi = &font_info[font_title[i]]; + + fi->special_graphic[mode_new] = fi->special_graphic[mode_old]; + fi->special_bitmap_id[mode_new] = fi->special_bitmap_id[mode_old]; + } + + // adjust vertical text and button positions on scores page + for (i = 0; font_text[i] != -1; i++) + { + for (j = 0; j < 2; j++) + { + boolean jue0 = strEqual(artwork.gfx_current_identifier, "jue0"); + int font_nr = (j == 0 ? font_text[i] : FONT_ACTIVE(font_text[i])); + int font_bitmap_id = font_info[font_nr].special_bitmap_id[mode_old]; + int font_yoffset = (jue0 ? 10 : 5); + + gfx.font_bitmap_info[font_bitmap_id].draw_yoffset = font_yoffset; + } + } + + // adjust page offsets on score info page + menu.draw_xoffset[mode_new] = menu.draw_xoffset[mode_old]; + menu.draw_yoffset[mode_new] = menu.draw_yoffset[mode_old]; + } + InitGraphicCompatibilityInfo_Doors(); } @@ -2112,6 +2283,11 @@ static void InitSoundInfo(void) } set_sound_parameters(i, sound->parameter); + +#if 0 + Debug("init:InitSoundInfo", "loop mode: %d ['%s']", + sound_info[i].loop, sound->token); +#endif } free(sound_effect_properties); @@ -2276,11 +2452,6 @@ static void ReinitializeGraphics(void) InitGraphicCompatibilityInfo(); print_timestamp_time("InitGraphicCompatibilityInfo"); - SetMainBackgroundImage(IMG_BACKGROUND); - print_timestamp_time("SetMainBackgroundImage"); - SetDoorBackgroundImage(IMG_BACKGROUND_DOOR); - print_timestamp_time("SetDoorBackgroundImage"); - InitGadgets(); print_timestamp_time("InitGadgets"); InitDoors(); @@ -4107,6 +4278,7 @@ void InitElementPropertiesStatic(void) EL_BD_AMOEBA, EL_EMC_MAGIC_BALL, EL_EMC_ANDROID, + EL_MM_GRAY_BALL, -1 }; @@ -4869,6 +5041,9 @@ static void InitGlobal(void) global_anim_info[i].token_name = global_anim_name_info[i].token_name; } + // create hash to store URLs for global animations + anim_url_hash = newSetupFileHash(); + // create hash from image config list image_config_hash = newSetupFileHash(); for (i = 0; image_config[i].token != NULL; i++) @@ -5305,6 +5480,12 @@ static void InitSetup(void) if (setup.options.verbose) options.verbose = TRUE; + if (setup.options.debug) + options.debug = TRUE; + + if (!strEqual(setup.options.debug_mode, ARG_UNDEFINED_STRING)) + options.debug_mode = getStringCopy(setup.options.debug_mode); + if (setup.debug.show_frames_per_second) global.show_frames_per_second = TRUE; } @@ -5312,10 +5493,7 @@ static void InitSetup(void) static void InitGameInfo(void) { game.restart_level = FALSE; - game.restart_game_message = NULL; - game.request_active = FALSE; - game.request_active_or_moving = FALSE; game.use_masked_elements_initial = FALSE; } @@ -5518,7 +5696,6 @@ void InitGfxBuffers(void) } ReCreateBitmap(&bitmap_db_field, FXSIZE, FYSIZE); - ReCreateBitmap(&bitmap_db_panel, DXSIZE, DYSIZE); ReCreateBitmap(&bitmap_db_door_1, 3 * DXSIZE, DYSIZE); ReCreateBitmap(&bitmap_db_door_2, 3 * VXSIZE, VYSIZE); @@ -5538,15 +5715,32 @@ void InitGfxBuffers(void) InitGfxBuffers_EM(); InitGfxBuffers_SP(); + InitGfxBuffers_MM(); } static void InitGfx(void) { struct GraphicInfo *graphic_info_last = graphic_info; char *filename_font_initial = NULL; - char *filename_anim_initial = NULL; + char *filename_image_initial[NUM_INITIAL_IMAGES] = { NULL }; + char *image_token[NUM_INITIAL_IMAGES] = + { + CONFIG_TOKEN_GLOBAL_BUSY_INITIAL, + CONFIG_TOKEN_GLOBAL_BUSY, + CONFIG_TOKEN_GLOBAL_BUSY_PLAYFIELD, + CONFIG_TOKEN_BACKGROUND, + CONFIG_TOKEN_BACKGROUND_LOADING_INITIAL, + CONFIG_TOKEN_BACKGROUND_LOADING + }; + struct MenuPosInfo *init_busy[NUM_INITIAL_IMAGES_BUSY] = + { + &init.busy_initial, + &init.busy, + &init.busy_playfield + }; Bitmap *bitmap_font_initial = NULL; - int i, j; + int parameter[NUM_INITIAL_IMAGES][NUM_GFX_ARGS]; + int i, j, k; // determine settings for initial font (for displaying startup messages) for (i = 0; image_config[i].token != NULL; i++) @@ -5560,7 +5754,9 @@ static void InitGfx(void) len_font_token = strlen(font_token); if (strEqual(image_config[i].token, font_token)) + { filename_font_initial = image_config[i].value; + } else if (strlen(image_config[i].token) > len_font_token && strncmp(image_config[i].token, font_token, len_font_token) == 0) { @@ -5589,6 +5785,8 @@ static void InitGfx(void) InitGfxCustomArtworkInfo(); InitGfxOtherSettings(); + InitGfxTileSizeInfo(TILESIZE, TILESIZE); + bitmap_font_initial = LoadCustomImage(filename_font_initial); for (j = 0; j < NUM_INITIAL_FONTS; j++) @@ -5596,21 +5794,17 @@ static void InitGfx(void) InitFontGraphicInfo(); - DrawProgramInfo(); - - DrawInitTextHead("Loading graphics"); - - // initialize settings for busy animation with default values - int parameter[NUM_GFX_ARGS]; - for (i = 0; i < NUM_GFX_ARGS; i++) - parameter[i] = get_graphic_parameter_value(image_config_suffix[i].value, - image_config_suffix[i].token, - image_config_suffix[i].type); + InitMenuDesignSettings_Static(); - char *anim_token = CONFIG_TOKEN_GLOBAL_BUSY; - int len_anim_token = strlen(anim_token); + // initialize settings for initial images with default values + for (i = 0; i < NUM_INITIAL_IMAGES; i++) + for (j = 0; j < NUM_GFX_ARGS; j++) + parameter[i][j] = + get_graphic_parameter_value(image_config_suffix[j].value, + image_config_suffix[j].token, + image_config_suffix[j].type); - // read settings for busy animation from default custom artwork config + // read settings for initial images from default custom artwork config char *gfx_config_filename = getPath3(options.graphics_directory, GFX_DEFAULT_SUBDIR, GRAPHICSINFO_FILENAME); @@ -5621,79 +5815,110 @@ static void InitGfx(void) if (setup_file_hash) { - char *filename = getHashEntry(setup_file_hash, anim_token); - - if (filename) + for (i = 0; i < NUM_INITIAL_IMAGES; i++) { - filename_anim_initial = getStringCopy(filename); + char *filename = getHashEntry(setup_file_hash, image_token[i]); - for (j = 0; image_config_suffix[j].token != NULL; j++) + if (filename) { - int type = image_config_suffix[j].type; - char *suffix = image_config_suffix[j].token; - char *token = getStringCat2(anim_token, suffix); - char *value = getHashEntry(setup_file_hash, token); + filename_image_initial[i] = getStringCopy(filename); - checked_free(token); + for (j = 0; image_config_suffix[j].token != NULL; j++) + { + int type = image_config_suffix[j].type; + char *suffix = image_config_suffix[j].token; + char *token = getStringCat2(image_token[i], suffix); + char *value = getHashEntry(setup_file_hash, token); + + checked_free(token); - if (value) - parameter[j] = get_graphic_parameter_value(value, suffix, type); + if (value) + parameter[i][j] = + get_graphic_parameter_value(value, suffix, type); + } } } + // read values from custom graphics config file + InitMenuDesignSettings_FromHash(setup_file_hash, FALSE); + freeSetupFileHash(setup_file_hash); } } - if (filename_anim_initial == NULL) + for (i = 0; i < NUM_INITIAL_IMAGES; i++) { - // read settings for busy animation from static default artwork config - for (i = 0; image_config[i].token != NULL; i++) + if (filename_image_initial[i] == NULL) { - if (strEqual(image_config[i].token, anim_token)) - filename_anim_initial = getStringCopy(image_config[i].value); - else if (strlen(image_config[i].token) > len_anim_token && - strncmp(image_config[i].token, anim_token, len_anim_token) == 0) + int len_token = strlen(image_token[i]); + + // read settings for initial images from static default artwork config + for (j = 0; image_config[j].token != NULL; j++) { - for (j = 0; image_config_suffix[j].token != NULL; j++) + if (strEqual(image_config[j].token, image_token[i])) + { + filename_image_initial[i] = getStringCopy(image_config[j].value); + } + else if (strlen(image_config[j].token) > len_token && + strncmp(image_config[j].token, image_token[i], len_token) == 0) { - if (strEqual(&image_config[i].token[len_anim_token], - image_config_suffix[j].token)) - parameter[j] = - get_graphic_parameter_value(image_config[i].value, - image_config_suffix[j].token, - image_config_suffix[j].type); + for (k = 0; image_config_suffix[k].token != NULL; k++) + { + if (strEqual(&image_config[j].token[len_token], + image_config_suffix[k].token)) + parameter[i][k] = + get_graphic_parameter_value(image_config[j].value, + image_config_suffix[k].token, + image_config_suffix[k].type); + } } } } } - if (filename_anim_initial == NULL) // should not happen - Fail("cannot get filename for '%s'", CONFIG_TOKEN_GLOBAL_BUSY); + for (i = 0; i < NUM_INITIAL_IMAGES; i++) + { + if (filename_image_initial[i] == NULL) // should not happen + Fail("cannot get filename for '%s'", image_token[i]); + + image_initial[i].bitmaps = + checked_calloc(sizeof(Bitmap *) * NUM_IMG_BITMAP_POINTERS); - anim_initial.bitmaps = - checked_calloc(sizeof(Bitmap *) * NUM_IMG_BITMAP_POINTERS); + if (!strEqual(filename_image_initial[i], UNDEFINED_FILENAME)) + image_initial[i].bitmaps[IMG_BITMAP_STANDARD] = + LoadCustomImage(filename_image_initial[i]); - anim_initial.bitmaps[IMG_BITMAP_STANDARD] = - LoadCustomImage(filename_anim_initial); + checked_free(filename_image_initial[i]); + } - checked_free(filename_anim_initial); + for (i = 0; i < NUM_INITIAL_IMAGES; i++) + image_initial[i].use_image_size = TRUE; - graphic_info = &anim_initial; // graphic == 0 => anim_initial + graphic_info = image_initial; // graphic == 0 => image_initial - set_graphic_parameters_ext(0, parameter, anim_initial.bitmaps); + for (i = 0; i < NUM_INITIAL_IMAGES; i++) + set_graphic_parameters_ext(i, parameter[i], image_initial[i].bitmaps); graphic_info = graphic_info_last; - init.busy.width = anim_initial.width; - init.busy.height = anim_initial.height; + for (i = 0; i < NUM_INITIAL_IMAGES_BUSY; i++) + { + // set image size for busy animations + init_busy[i]->width = image_initial[i].width; + init_busy[i]->height = image_initial[i].height; + } - InitMenuDesignSettings_Static(); + SetLoadingBackgroundImage(); + + ClearRectangleOnBackground(window, 0, 0, WIN_XSIZE, WIN_YSIZE); + + DrawProgramInfo(); InitGfxDrawBusyAnimFunction(DrawInitAnim); InitGfxDrawGlobalAnimFunction(DrawGlobalAnimations); InitGfxDrawGlobalBorderFunction(DrawMaskedBorderToTarget); InitGfxDrawTileCursorFunction(DrawTileCursor); + InitGfxDrawEnvelopeRequestFunction(DrawEnvelopeRequestToScreen); gfx.fade_border_source_status = global.border_status; gfx.fade_border_target_status = global.border_status; @@ -5801,17 +6026,14 @@ static void InitImages(void) print_timestamp_done("InitImages"); } -static void InitSound(char *identifier) +static void InitSound(void) { print_timestamp_init("InitSound"); - if (identifier == NULL) - identifier = artwork.snd_current->identifier; - // set artwork path to send it to the sound server process setLevelArtworkDir(artwork.snd_first); - InitReloadCustomSounds(identifier); + InitReloadCustomSounds(); print_timestamp_time("InitReloadCustomSounds"); ReinitializeSounds(); @@ -5820,17 +6042,14 @@ static void InitSound(char *identifier) print_timestamp_done("InitSound"); } -static void InitMusic(char *identifier) +static void InitMusic(void) { print_timestamp_init("InitMusic"); - if (identifier == NULL) - identifier = artwork.mus_current->identifier; - // set artwork path to send it to the sound server process setLevelArtworkDir(artwork.mus_first); - InitReloadCustomMusic(identifier); + InitReloadCustomMusic(); print_timestamp_time("InitReloadCustomMusic"); ReinitializeMusic(); @@ -6019,12 +6238,12 @@ static void InitOverrideArtwork(void) #endif } -static char *getNewArtworkIdentifier(int type) +static char *setNewArtworkIdentifier(int type) { static char *last_leveldir_identifier[3] = { NULL, NULL, NULL }; static char *last_artwork_identifier[3] = { NULL, NULL, NULL }; static boolean last_override_level_artwork[3] = { FALSE, FALSE, FALSE }; - static boolean last_has_level_artwork_set[3] = { FALSE, FALSE, FALSE }; + static boolean last_has_custom_artwork_set[3] = { FALSE, FALSE, FALSE }; static boolean initialized[3] = { FALSE, FALSE, FALSE }; TreeInfo *artwork_first_node = ARTWORK_FIRST_NODE(artwork, type); boolean setup_override_artwork = GFX_OVERRIDE_ARTWORK(type); @@ -6033,6 +6252,9 @@ static char *getNewArtworkIdentifier(int type) // !!! setLevelArtworkDir() should be moved to an earlier stage !!! char *leveldir_artwork_set = setLevelArtworkDir(artwork_first_node); boolean has_level_artwork_set = (leveldir_artwork_set != NULL); + TreeInfo *custom_artwork_set = + getTreeInfoFromIdentifier(artwork_first_node, leveldir_identifier); + boolean has_custom_artwork_set = (custom_artwork_set != NULL); char *artwork_current_identifier; char *artwork_new_identifier = NULL; // default: nothing has changed @@ -6050,9 +6272,9 @@ static char *getNewArtworkIdentifier(int type) if (setup_override_artwork) artwork_current_identifier = setup_artwork_set; - else if (leveldir_artwork_set != NULL) + else if (has_level_artwork_set) artwork_current_identifier = leveldir_artwork_set; - else if (getTreeInfoFromIdentifier(artwork_first_node, leveldir_identifier)) + else if (has_custom_artwork_set) artwork_current_identifier = leveldir_identifier; else artwork_current_identifier = setup_artwork_set; @@ -6062,11 +6284,11 @@ static char *getNewArtworkIdentifier(int type) // ---------- reload if level set and also artwork set has changed ---------- if (last_leveldir_identifier[type] != leveldir_identifier && - (last_has_level_artwork_set[type] || has_level_artwork_set)) + (last_has_custom_artwork_set[type] || has_custom_artwork_set)) artwork_new_identifier = artwork_current_identifier; last_leveldir_identifier[type] = leveldir_identifier; - last_has_level_artwork_set[type] = has_level_artwork_set; + last_has_custom_artwork_set[type] = has_custom_artwork_set; // ---------- reload if "override artwork" setting has changed -------------- if (last_override_level_artwork[type] != setup_override_artwork) @@ -6081,6 +6303,7 @@ static char *getNewArtworkIdentifier(int type) // (we cannot compare string pointers here, so copy string content itself) setString(&last_artwork_identifier[type], artwork_current_identifier); + // ---------- set new artwork identifier ---------- *(ARTWORK_CURRENT_IDENTIFIER_PTR(artwork, type)) = artwork_current_identifier; // ---------- do not reload directly after starting ------------------------- @@ -6092,6 +6315,13 @@ static char *getNewArtworkIdentifier(int type) return artwork_new_identifier; } +static void InitArtworkIdentifier(void) +{ + setNewArtworkIdentifier(ARTWORK_TYPE_GRAPHICS); + setNewArtworkIdentifier(ARTWORK_TYPE_SOUNDS); + setNewArtworkIdentifier(ARTWORK_TYPE_MUSIC); +} + void ReloadCustomArtwork(int force_reload) { int last_game_status = game_status; // save current game status @@ -6108,9 +6338,9 @@ void ReloadCustomArtwork(int force_reload) AdjustGraphicsForEMC(); AdjustSoundsForEMC(); - gfx_new_identifier = getNewArtworkIdentifier(ARTWORK_TYPE_GRAPHICS); - snd_new_identifier = getNewArtworkIdentifier(ARTWORK_TYPE_SOUNDS); - mus_new_identifier = getNewArtworkIdentifier(ARTWORK_TYPE_MUSIC); + gfx_new_identifier = setNewArtworkIdentifier(ARTWORK_TYPE_GRAPHICS); + snd_new_identifier = setNewArtworkIdentifier(ARTWORK_TYPE_SOUNDS); + mus_new_identifier = setNewArtworkIdentifier(ARTWORK_TYPE_MUSIC); reload_needed = (gfx_new_identifier != NULL || force_reload_gfx || snd_new_identifier != NULL || force_reload_snd || @@ -6125,11 +6355,17 @@ void ReloadCustomArtwork(int force_reload) FadeOut(REDRAW_ALL); - ClearRectangle(drawto, 0, 0, WIN_XSIZE, WIN_YSIZE); - print_timestamp_time("ClearRectangle"); + SetLoadingBackgroundImage(); + + ClearRectangleOnBackground(drawto, 0, 0, WIN_XSIZE, WIN_YSIZE); + print_timestamp_time("ClearRectangleOnBackground"); FadeIn(REDRAW_ALL); + UPDATE_BUSY_STATE(); + + InitMissingFileHash(); + if (gfx_new_identifier != NULL || force_reload_gfx) { #if 0 @@ -6147,13 +6383,13 @@ void ReloadCustomArtwork(int force_reload) if (snd_new_identifier != NULL || force_reload_snd) { - InitSound(snd_new_identifier); + InitSound(); print_timestamp_time("InitSound"); } if (mus_new_identifier != NULL || force_reload_mus) { - InitMusic(mus_new_identifier); + InitMusic(); print_timestamp_time("InitMusic"); } @@ -6161,8 +6397,6 @@ void ReloadCustomArtwork(int force_reload) SetGameStatus(last_game_status); // restore current game status - init_last = init; // switch to new busy animation - FadeOut(REDRAW_ALL); RedrawGlobalBorder(); @@ -6230,7 +6464,7 @@ void DisplayExitMessage(char *format, va_list ap) sy += 3 * font_height; num_lines_printed = - DrawTextBuffer(sx, sy, program.log_filename[LOG_ERR_ID], font_2, + DrawTextBuffer(sx, sy, program.log_filename, font_2, line_length, line_length, max_lines, 0, BLIT_ON_BACKGROUND, TRUE, TRUE, FALSE); @@ -6243,8 +6477,8 @@ void DisplayExitMessage(char *format, va_list ap) BackToFront(); - // deactivate toons on error message screen - setup.toons = FALSE; + // deactivate toons and global animations on error message screen + setup.global_animations = FALSE; WaitForEventToContinue(); } @@ -6268,6 +6502,8 @@ void OpenAll(void) InitSimpleRandom(NEW_RANDOMIZE); InitBetterRandom(NEW_RANDOMIZE); + InitMissingFileHash(); + print_timestamp_time("[init global stuff]"); InitSetup(); @@ -6335,13 +6571,16 @@ void OpenAll(void) InitOverrideArtwork(); // needs to know current level directory print_timestamp_time("InitOverrideArtwork"); + InitArtworkIdentifier(); // needs to know current level directory + print_timestamp_time("InitArtworkIdentifier"); + InitImages(); // needs to know current level directory print_timestamp_time("InitImages"); - InitSound(NULL); // needs to know current level directory + InitSound(); // needs to know current level directory print_timestamp_time("InitSound"); - InitMusic(NULL); // needs to know current level directory + InitMusic(); // needs to know current level directory print_timestamp_time("InitMusic"); InitArtworkDone(); @@ -6426,14 +6665,13 @@ void OpenAll(void) static boolean WaitForApiThreads(void) { - unsigned int thread_delay = 0; - unsigned int thread_delay_value = 10000; + DelayCounter thread_delay = { 10000 }; if (program.api_thread_count == 0) return TRUE; // deactivate global animations (not accessible in game state "loading") - setup.toons = FALSE; + setup.global_animations = FALSE; // set game state to "loading" to be able to show busy animation SetGameStatus(GAME_MODE_LOADING); @@ -6443,7 +6681,7 @@ static boolean WaitForApiThreads(void) // wait for threads to finish (and fail on timeout) while (program.api_thread_count > 0) { - if (DelayReached(&thread_delay, thread_delay_value)) + if (DelayReached(&thread_delay)) { Error("failed waiting for threads - TIMEOUT");