From c90474ee7143a215ef3b3548024e025ce16ad6d3 Mon Sep 17 00:00:00 2001 From: Paul Duncan Date: Sun, 13 Jan 2019 20:24:06 -0500 Subject: working, with sprites --- src/libsok/sok-ctx.c | 18 +++++++------- src/sdl/color.c | 12 ++++++--- src/sdl/color.h | 2 +- src/sdl/draw.c | 23 +++++------------ src/sdl/draw.h | 5 +++- src/sdl/main.c | 70 ++++++++++++++++++++++++++++++++++++++++++++++------ src/sdl/sprites.c | 69 ++++++++++++++++++++++++++------------------------- src/sdl/sprites.h | 2 +- 8 files changed, 127 insertions(+), 74 deletions(-) diff --git a/src/libsok/sok-ctx.c b/src/libsok/sok-ctx.c index 84fe8ed..e278af1 100644 --- a/src/libsok/sok-ctx.c +++ b/src/libsok/sok-ctx.c @@ -538,15 +538,6 @@ bool sok_ctx_walk( } } - if (cbs->on_home) { - const bool has_goal = tile_is_goal(ctx, ctx->home); - - // emit home - if (!cbs->on_home(ctx, ctx->home, has_goal, data)) { - return false; - } - } - if (cbs->on_walls_start && !cbs->on_walls_start(ctx, data)) { return false; } @@ -597,6 +588,15 @@ bool sok_ctx_walk( return false; } + if (cbs->on_home) { + const bool has_goal = tile_is_goal(ctx, ctx->home); + + // emit home + if (!cbs->on_home(ctx, ctx->home, has_goal, data)) { + return false; + } + } + if (cbs->on_box) { // walk boxes for (size_t i = 0; i < ctx->level.num_boxes; i++) { diff --git a/src/sdl/color.c b/src/sdl/color.c index 1e75cb6..cb94095 100644 --- a/src/sdl/color.c +++ b/src/sdl/color.c @@ -1,5 +1,6 @@ #include #include "color.h" +#include "util.h" static const SDL_Color PALETTE[] = { @@ -14,12 +15,17 @@ PALETTE[] = { { 0, 0, 0, 0 }, // COLOR_LAST }; -bool +void set_color( SDL_Renderer * const renderer, const color_t ofs ) { - // FIXME: check for error? + if (ofs >= COLOR_LAST) { + die("set_color(): invalid color"); + } + const SDL_Color c = PALETTE[ofs]; - return SDL_SetRenderDrawColor(renderer, c.r, c.g, c.b, c.a) < 0; + if (SDL_SetRenderDrawColor(renderer, c.r, c.g, c.b, c.a)) { + die("SDL_SetRenderDrawColor(): %s", SDL_GetError()); + } } diff --git a/src/sdl/color.h b/src/sdl/color.h index 5cff762..6110e6e 100644 --- a/src/sdl/color.h +++ b/src/sdl/color.h @@ -15,6 +15,6 @@ typedef enum { COLOR_LAST, } color_t; -_Bool set_color(SDL_Renderer * const, const color_t); +void set_color(SDL_Renderer * const, const color_t); #endif /* COLOR_H */ diff --git a/src/sdl/draw.c b/src/sdl/draw.c index bf73129..ab4803e 100644 --- a/src/sdl/draw.c +++ b/src/sdl/draw.c @@ -4,7 +4,7 @@ #include "draw.h" #include "sprites.h" -#undef DRAW_SPRITES +#define DRAW_SPRITES static size_t get_cell_size( @@ -34,30 +34,20 @@ draw_cell( const sok_pos_t pos, const sprite_t sprite ) { - const SDL_Rect dst_rect = get_cell_rect(draw_ctx, pos); + const SDL_Rect rect = get_cell_rect(draw_ctx, pos); #ifdef DRAW_SPRITES - const SDL_Rect src_rect = sprites_get_rect(sprite); - -#if 0 - SDL_Log( - "src_rect = { %d, %d, %d, %d }, dst_rect = { %d, %d, %d, %d }", - src_rect.x, src_rect.y, src_rect.w, src_rect.h, - dst_rect.x, dst_rect.y, dst_rect.w, dst_rect.h - ); -#endif /* 0 */ - - if (SDL_RenderCopy(draw_ctx->renderer, draw_ctx->sprites, &src_rect, &dst_rect)) { + SDL_Texture *tex = draw_ctx->sprites[sprite]; + if (SDL_RenderCopy(draw_ctx->renderer, tex, NULL, &rect)) { die("SDL_RenderCopy(): %s", SDL_GetError()); } #else - if (SDL_RenderFillRect(draw_ctx->renderer, &dst_rect)) { + if (SDL_RenderFillRect(draw_ctx->renderer, &rect)) { die("SDL_RenderFillRect(): %s", SDL_GetError()); } #endif /* DRAW_SPRITES */ } - static bool draw_on_size( const sok_ctx_t * const ctx, @@ -189,7 +179,6 @@ draw( // render sok_ctx_walk(draw_ctx->ctx, &DRAW_CBS, draw_ctx); - // flip + // flip SDL_RenderPresent(draw_ctx->renderer); } - diff --git a/src/sdl/draw.h b/src/sdl/draw.h index 7a61e7d..873287a 100644 --- a/src/sdl/draw.h +++ b/src/sdl/draw.h @@ -6,9 +6,12 @@ #include "../libsok/sok.h" #include "../text/levels.h" +// arbitrary +#define MAX_SPRITES 32 + typedef struct { SDL_Renderer * const renderer; - SDL_Texture * const sprites; + SDL_Texture *sprites[MAX_SPRITES]; const sok_ctx_t * const ctx; const size_t * const level_num; diff --git a/src/sdl/main.c b/src/sdl/main.c index 7240d9a..95597f0 100644 --- a/src/sdl/main.c +++ b/src/sdl/main.c @@ -31,6 +31,60 @@ draw_moves( SDL_Log("Solution (%zu moves): %s", ctx->num_moves - skip_moves, buf); } +static void +log_renderer_info( + SDL_Renderer * const renderer +) { + SDL_RendererInfo info; + + // get renderer info + if (SDL_GetRendererInfo(renderer, &info)) { + die("SDL_GetRendererInfo(): %s", SDL_GetError()); + } + + // log renderer info + SDL_Log( + "renderer:\n" + " name = \"%s\"\n" + " flags = %u%s%s%s%s\n" + " num_texture_formats = %u\n" + " max_texture_width = %d\n" + " max_texture_height = %d", + info.name, + info.flags, + info.flags & SDL_RENDERER_SOFTWARE ? ", software" : "", + info.flags & SDL_RENDERER_ACCELERATED ? ", accelerated" : "", + info.flags & SDL_RENDERER_PRESENTVSYNC ? ", presentvsync" : "", + info.flags & SDL_RENDERER_TARGETTEXTURE ? ", targettexture" : "", + info.num_texture_formats, + info.max_texture_width, + info.max_texture_height + ); +} + +static void +log_texture_info( + SDL_Texture * const tex +) { + Uint32 format; + int access, w, h; + + // query texture + if (SDL_QueryTexture(tex, &format, &access, &w, &h)) { + die("SDL_QueryTexture(): %s", SDL_GetError()); + } + + // log information + SDL_Log( + "texture:\n" + " format = %u\n" + " access = %d\n" + " width = %d\n" + " height = %d", + format, access, w, h + ); +} + static void solve_on_error( const char * const err @@ -70,10 +124,12 @@ int main(int argc, char *argv[]) { // create window and renderer SDL_Window *win; SDL_Renderer *renderer; - if (SDL_CreateWindowAndRenderer(800, 600, SDL_RENDERER_ACCELERATED | SDL_WINDOW_RESIZABLE, &win, &renderer)) { + if (SDL_CreateWindowAndRenderer(800, 600, SDL_WINDOW_RESIZABLE, &win, &renderer)) { die("SDL_CreateWindowAndRenderer(): %s", SDL_GetError()); } + log_renderer_info(renderer); + // init draw context draw_ctx_t draw_ctx = { .level_num = &level_num, @@ -81,14 +137,13 @@ int main(int argc, char *argv[]) { .ctx = &ctx, .renderer = renderer, .zoom = &zoom, - .sprites = sprites_init(renderer, sprites_png_path), }; - Uint32 format; - int access, w, h; - if (SDL_QueryTexture(draw_ctx.sprites, &format, &access, &w, &h)) { - die("SDL_QueryTexture(): %s", SDL_GetError()); - } + sprites_init(renderer, sprites_png_path, draw_ctx.sprites); + + log_texture_info(draw_ctx.sprites[0]); + + SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_NONE); bool done = false; SDL_Event ev; @@ -201,7 +256,6 @@ int main(int argc, char *argv[]) { } // fini renderer, window - SDL_DestroyTexture(draw_ctx.sprites); SDL_DestroyRenderer(renderer); SDL_DestroyWindow(win); diff --git a/src/sdl/sprites.c b/src/sdl/sprites.c index cb127aa..9b9b42f 100644 --- a/src/sdl/sprites.c +++ b/src/sdl/sprites.c @@ -6,53 +6,54 @@ #include "util.h" #include "sprites.h" -typedef struct { - const Uint32 r, - g, - b, - a; -} mask_t; - -#if SDL_BYTEORDER == SDL_BIG_ENDIAN -static const mask_t -MASK = { 0xff000000, 0x00ff0000, 0x0000ff00, 0x000000ff }; -#else -static const mask_t -MASK = { 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; -#endif /* SDL_BYTEORDER */ - -SDL_Texture * +void sprites_init( SDL_Renderer * const renderer, - const char * const png_path + const char * const png_path, + SDL_Texture **sprites ) { // load image - int x, y, n; - unsigned char *data = stbi_load(png_path, &x, &y, &n, 4); - if (!data) { - die("stbi_load()"); + int im_w, im_h; + unsigned char *im_data = stbi_load(png_path, &im_w, &im_h, NULL, 4); + if (!im_data) { + die("stbi_load(): %s", stbi_failure_reason()); } // create surface - SDL_Surface * const surface = SDL_CreateRGBSurfaceFrom(data, x, y, 32, 4 * x, MASK.r, MASK.g, MASK.b, MASK.a); - if (!surface) { + SDL_Surface * const src = SDL_CreateRGBSurfaceWithFormatFrom(im_data, im_w, im_h, 32, 4 * im_w, SDL_PIXELFORMAT_RGBA32); + if (!src) { die("SDLCreateRGBSurfaceFrom(): %s", SDL_GetError()); } - // free image data - free(data); + // create sprite textures + for (size_t i = 0; i < SPRITE_LAST; i++) { + // create surface + SDL_Surface *s = SDL_CreateRGBSurfaceWithFormat(0, 32, 32, 32, SDL_PIXELFORMAT_RGBA32); + if (!s) { + die("SDL_CreateRGBSurfaceWithFormat(): %s", SDL_GetError()); + } - // create texture - SDL_Texture *r = SDL_CreateTextureFromSurface(renderer, surface); - if (!r) { - die("SDLCreateTextureFromSurface(): %s", SDL_GetError()); + // copy from main surface + const SDL_Rect src_rect = { i * 32, 0, 32, 32 }; + if (SDL_BlitScaled(src, &src_rect, s, NULL)) { + die("SDL_BlitScaled(): %s", SDL_GetError()); + } + + // create texture + sprites[i] = SDL_CreateTextureFromSurface(renderer, s); + if (!sprites[i]) { + die("SDLCreateTextureFromSurface(): %s", SDL_GetError()); + } + + // free surface + SDL_FreeSurface(s); } - // free surface - SDL_FreeSurface(surface); + // free main surface + SDL_FreeSurface(src); - // return texture - return r; + // free image data + stbi_image_free(im_data); } SDL_Rect @@ -60,5 +61,5 @@ sprites_get_rect( const sprite_t sprite ) { const int x = ((sprite < SPRITE_LAST) ? sprite : SPRITE_NONE) * 32; - return (SDL_Rect) { x, 0, 32, 32 }; + return (SDL_Rect) { .x = x, .y = 0, .w = 32, .h = 32 }; } diff --git a/src/sdl/sprites.h b/src/sdl/sprites.h index a7dbd62..cbbdb89 100644 --- a/src/sdl/sprites.h +++ b/src/sdl/sprites.h @@ -13,7 +13,7 @@ typedef enum { SPRITE_LAST, } sprite_t; -SDL_Texture *sprites_init(SDL_Renderer * const, const char * const); +void sprites_init(SDL_Renderer * const, const char * const, SDL_Texture **); SDL_Rect sprites_get_rect(const sprite_t); -- cgit v1.2.3