From: Holger Schemel Date: Sun, 25 Oct 2020 18:53:25 +0000 (+0100) Subject: fixed bug with copying color key if surfaces have different format X-Git-Tag: 4.2.0.4~6 X-Git-Url: https://git.artsoft.org/?p=rocksndiamonds.git;a=commitdiff_plain;h=41b805f296b21b950aa8372c2f1792bf301f4ef9 fixed bug with copying color key if surfaces have different format This bug occurs when getting the color key of a surface and setting it as the color key of another surface that has a surface format that differs from that of the first surface. This bug occurs in conjunction with the workaround for the color key bug in SDL 2.0.12 which prevents transparency in graphics files with color palette. (See commit 6b6c9eb2 for that workaround.) Especially, this bug combination occurs on the high score screen of Alan Bond's "Snake Bite" level set, which then only shows a headline on a black screen. (This screen uses a trick to show each line on the screen in a different color by using a background with different colors and an inverted font with transparent characters and opaque black surroundings, so missing transparency leads to "black text on black background".) --- diff --git a/src/libgame/sdl.c b/src/libgame/sdl.c index cbdbdc1c..0325c45f 100644 --- a/src/libgame/sdl.c +++ b/src/libgame/sdl.c @@ -297,6 +297,7 @@ static boolean equalSDLPixelFormat(SDL_PixelFormat *format1, format1->Bmask == format2->Bmask); } +#if 0 static Pixel SDLGetColorKey(SDL_Surface *surface) { Pixel color_key; @@ -306,6 +307,31 @@ static Pixel SDLGetColorKey(SDL_Surface *surface) return color_key; } +#endif + +static void SDLCopyColorKey(SDL_Surface *src_surface, SDL_Surface *dst_surface) +{ + Pixel color_key; + Uint8 r, g, b; + + // check if source surface has a color key + if (SDL_GetColorKey(src_surface, &color_key) == 0) + { + // get RGB values of color key of source surface + SDL_GetRGB(color_key, src_surface->format, &r, &g, &b); + + // get color key from RGB values in destination surface format + color_key = SDL_MapRGB(dst_surface->format, r, g, b); + + // set color key in destination surface + SDL_SetColorKey(dst_surface, SET_TRANSPARENT_PIXEL, color_key); + } + else + { + // unset color key in destination surface + SDL_SetColorKey(dst_surface, UNSET_TRANSPARENT_PIXEL, 0); + } +} static boolean SDLHasColorKey(SDL_Surface *surface) { @@ -366,8 +392,7 @@ SDL_Surface *SDLGetNativeSurface(SDL_Surface *surface) // workaround for a bug in SDL 2.0.12 (which does not convert the color key) if (SDLHasColorKey(surface) && !SDLHasColorKey(new_surface)) - SDL_SetColorKey(new_surface, SET_TRANSPARENT_PIXEL, - SDLGetColorKey(surface)); + SDLCopyColorKey(surface, new_surface); return new_surface; } @@ -2269,8 +2294,7 @@ Bitmap *SDLZoomBitmap(Bitmap *src_bitmap, int dst_width, int dst_height) // set color key for zoomed surface from source surface, if defined if (SDLHasColorKey(src_surface)) - SDL_SetColorKey(dst_surface, SET_TRANSPARENT_PIXEL, - SDLGetColorKey(src_surface)); + SDLCopyColorKey(src_surface, dst_surface); // create native non-transparent surface for opaque blitting dst_bitmap->surface = SDLGetOpaqueSurface(dst_surface);