From: Tim Goya Date: Fri, 17 Aug 2007 00:18:17 +0000 (+0000) Subject: SDL: use hash table for color cache X-Git-Url: https://git.verplant.org/?a=commitdiff_plain;h=791b577793d178a35031a6585ebc9a73b94f299c;p=supertux.git SDL: use hash table for color cache SVN-Revision: 5140 --- diff --git a/src/video/sdl_texture.cpp b/src/video/sdl_texture.cpp index d5a9d9cf5..917a4df48 100644 --- a/src/video/sdl_texture.cpp +++ b/src/video/sdl_texture.cpp @@ -401,9 +401,9 @@ namespace SDL Texture::Texture(SDL_Surface* image) { texture = SDL_DisplayFormatAlpha(image); - //image->refcount++; - //texture = image; - + //width = texture->w; + //height = texture->h; + int numerator, denominator; float xfactor = (float) config->screenwidth / SCREEN_WIDTH; float yfactor = (float) config->screenheight / SCREEN_HEIGHT; if(xfactor < yfactor) @@ -416,7 +416,7 @@ namespace SDL numerator = config->screenheight; denominator = SCREEN_HEIGHT; } - cache[white][NO_EFFECT] = scale(texture, numerator, denominator); + cache[NO_EFFECT][white] = scale(texture, numerator, denominator); } Texture::~Texture() @@ -426,26 +426,25 @@ namespace SDL SDL_Surface *Texture::get_transform(const Color &color, DrawingEffect effect) { - if(cache.find(color) == cache.end()) - { - cache[color][NO_EFFECT] = colorize(cache[white][NO_EFFECT], color); + if(cache[NO_EFFECT][color] == 0) { + assert(cache[NO_EFFECT][white]); + cache[NO_EFFECT][color] = colorize(cache[NO_EFFECT][white], color); } - if(cache[color][effect] == 0) { - assert(cache[color][NO_EFFECT]); + if(cache[effect][color] == 0) { + assert(cache[NO_EFFECT][color]); switch(effect) { case NO_EFFECT: break; case HORIZONTAL_FLIP: - cache[color][HORIZONTAL_FLIP] = horz_flip(cache[color][NO_EFFECT]); + cache[HORIZONTAL_FLIP][color] = horz_flip(cache[NO_EFFECT][color]); break; case VERTICAL_FLIP: - cache[color][VERTICAL_FLIP] = vert_flip(cache[color][NO_EFFECT]); + cache[VERTICAL_FLIP][color] = vert_flip(cache[NO_EFFECT][color]); break; default: - std::cerr << "Warning: transformation unknown" << std::endl; return 0; } } - return cache[color][effect]; + return cache[effect][color]; } } diff --git a/src/video/sdl_texture.hpp b/src/video/sdl_texture.hpp index 0a8045fca..34479dbca 100644 --- a/src/video/sdl_texture.hpp +++ b/src/video/sdl_texture.hpp @@ -25,8 +25,7 @@ #include #include "texture.hpp" - -class Color; +#include "color.hpp" namespace SDL { @@ -34,11 +33,14 @@ namespace SDL { protected: SDL_Surface *texture; - int numerator; - int denominator; + //unsigned int width; + //unsigned int height; - struct Cache + struct ColorCache { + static const int HASHED_BITS = 3; + static const int CACHE_SIZE = 1 << (HASHED_BITS * 3); + static void ref(SDL_Surface *surface) { if(surface) @@ -47,31 +49,40 @@ namespace SDL } } - SDL_Surface *data[NUM_EFFECTS]; + static int hash(const Color &color) + { + return + ((int) (color.red * ((1 << HASHED_BITS) - 1)) << (HASHED_BITS - 1) * 2) | + ((int) (color.green * ((1 << HASHED_BITS) - 1)) << (HASHED_BITS - 1)) | + ((int) (color.blue * ((1 << HASHED_BITS) - 1)) << 0); + } + + SDL_Surface *data[CACHE_SIZE]; - Cache() + ColorCache() { - memset(data, 0, NUM_EFFECTS * sizeof(SDL_Surface *)); + memset(data, 0, CACHE_SIZE * sizeof(SDL_Surface *)); } - ~Cache() + ~ColorCache() { - std::for_each(data, data + NUM_EFFECTS, SDL_FreeSurface); + std::for_each(data, data + CACHE_SIZE, SDL_FreeSurface); } - void operator = (const Cache &other) + void operator = (const ColorCache &other) { - std::for_each(other.data, other.data + NUM_EFFECTS, ref); - std::for_each(data, data + NUM_EFFECTS, SDL_FreeSurface); - memcpy(data, other.data, sizeof(Cache)); + std::for_each(other.data, other.data + CACHE_SIZE, ref); + std::for_each(data, data + CACHE_SIZE, SDL_FreeSurface); + memcpy(data, other.data, CACHE_SIZE * sizeof(SDL_Surface *)); } - SDL_Surface *&operator [] (DrawingEffect effect) + SDL_Surface *&operator [] (const Color &color) { - return data[effect]; + return data[hash(color)]; } }; - mutable std::map cache; /**< Cache for processed surfaces */ + //typedef std::map ColorCache; + ColorCache cache[NUM_EFFECTS]; public: Texture(SDL_Surface* sdlsurface); @@ -103,6 +114,26 @@ namespace SDL { return texture->h; } + + /*unsigned int get_texture_width() const + { + return width; + } + + unsigned int get_texture_height() const + { + return height; + } + + unsigned int get_image_width() const + { + return width; + } + + unsigned int get_image_height() const + { + return height; + }*/ }; }