Added ASSERT_RETURN and RETURN_ERROR as well as WARNING variants of each
This commit is contained in:
parent
a841fa7c92
commit
783258e086
34
src/assets.c
34
src/assets.c
|
@ -110,9 +110,7 @@ asset_id store_asset(void* asset, AssetDestructor destructor) {
|
||||||
|
|
||||||
static
|
static
|
||||||
AssetData* _internal_get_by_id(asset_id id) {
|
AssetData* _internal_get_by_id(asset_id id) {
|
||||||
if(id == 0) {
|
ASSERT_RETURN_WARN(id != 0, NULL, "Cannot get element with id 0");
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(size_t i = 0; i < _assets_len; ++i) {
|
for(size_t i = 0; i < _assets_len; ++i) {
|
||||||
if(_assets[i].id == id) {
|
if(_assets[i].id == id) {
|
||||||
|
@ -120,16 +118,14 @@ AssetData* _internal_get_by_id(asset_id id) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return NULL;
|
RETURN_WARNING(NULL, "Failed to find requested asset with id %zu", id);
|
||||||
}
|
}
|
||||||
|
|
||||||
void* get_asset(asset_id id) {
|
void* get_asset(asset_id id) {
|
||||||
AssetData* found = _internal_get_by_id(id);
|
AssetData* found = _internal_get_by_id(id);
|
||||||
if(found != NULL) {
|
ASSERT_RETURN(found != NULL, NULL, "Failed to find asset with id %zu.", id);
|
||||||
return found->asset;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
return found;
|
||||||
}
|
}
|
||||||
|
|
||||||
asset_id get_asset_id(void* asset) {
|
asset_id get_asset_id(void* asset) {
|
||||||
|
@ -139,15 +135,13 @@ asset_id get_asset_id(void* asset) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
RETURN_WARNING(NULL, "Failed to find asset referencing %p", asset);
|
||||||
}
|
}
|
||||||
|
|
||||||
void free_asset(asset_id id) {
|
void free_asset(asset_id id) {
|
||||||
AssetData* found = _internal_get_by_id(id);
|
AssetData* found = _internal_get_by_id(id);
|
||||||
|
|
||||||
if(found == NULL) {
|
ASSERT_RETURN(found != NULL,, "Attempt to free nonexistent asset.");
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
found->destructor(found->asset);
|
found->destructor(found->asset);
|
||||||
|
|
||||||
|
@ -159,31 +153,23 @@ void free_asset(asset_id id) {
|
||||||
|
|
||||||
cJSON* load_json_from_file(const char* filename) {
|
cJSON* load_json_from_file(const char* filename) {
|
||||||
FILE* fp = fopen(filename, "r");
|
FILE* fp = fopen(filename, "r");
|
||||||
if(fp == NULL) {
|
ASSERT_RETURN(fp != NULL, NULL, "Failed to open file %s.", filename);
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t len = file_length(fp);
|
size_t len = file_length(fp);
|
||||||
char* buffer = malloc(len + 1);
|
char* buffer = malloc(len + 1);
|
||||||
if(buffer == NULL) {
|
ASSERT_RETURN(buffer != NULL, NULL, "Failed to allocate buffer for json string.");
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
read_file(fp, buffer, len);
|
read_file(fp, buffer, len);
|
||||||
cJSON* out = cJSON_Parse(buffer);
|
cJSON* out = cJSON_Parse(buffer);
|
||||||
free(buffer);
|
free(buffer);
|
||||||
|
|
||||||
if(out == NULL) {
|
ASSERT_RETURN(out != NULL, NULL, "Failed to parse json from file %s.", filename);
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t json_array_len(cJSON* json) {
|
size_t json_array_len(cJSON* json) {
|
||||||
if(!cJSON_IsArray(json)) {
|
ASSERT_RETURN(!cJSON_IsArray(json), 0, "Tried to get the length of a non-array json element.");
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
size_t len = 0;
|
size_t len = 0;
|
||||||
cJSON* itr;
|
cJSON* itr;
|
||||||
cJSON_ArrayForEach(itr, json) {
|
cJSON_ArrayForEach(itr, json) {
|
||||||
|
|
38
src/debug.h
38
src/debug.h
|
@ -6,20 +6,48 @@
|
||||||
extern int g_debug_error_abort;
|
extern int g_debug_error_abort;
|
||||||
|
|
||||||
#define LOG_INFO(...) do {\
|
#define LOG_INFO(...) do {\
|
||||||
printf("[%s:%d] ", __FILE__, __LINE__);\
|
printf("[%s:%d] INFO | ", __FILE__, __LINE__);\
|
||||||
printf("INFO | ");\
|
|
||||||
printf(__VA_ARGS__);\
|
printf(__VA_ARGS__);\
|
||||||
printf("\n");\
|
printf("\n");\
|
||||||
fflush(stdout);\
|
|
||||||
} while(0)
|
} while(0)
|
||||||
|
|
||||||
#define LOG_ERROR(...) do {\
|
#define LOG_ERROR(...) do {\
|
||||||
printf("[%s:%d] ", __FILE__, __LINE__);\
|
printf("[%s:%d] ERROR | ", __FILE__, __LINE__);\
|
||||||
printf("ERROR | ");\
|
|
||||||
printf(__VA_ARGS__);\
|
printf(__VA_ARGS__);\
|
||||||
printf("\n");\
|
printf("\n");\
|
||||||
fflush(stdout);\
|
fflush(stdout);\
|
||||||
if(g_debug_error_abort != 0) abort();\
|
if(g_debug_error_abort != 0) abort();\
|
||||||
} while(0)
|
} while(0)
|
||||||
|
|
||||||
|
#define LOG_WARNING(...) do {\
|
||||||
|
printf("[%s:%d] WARNING | ", __FILE__, __LINE__);\
|
||||||
|
printf(__VA_ARGS__);\
|
||||||
|
printf("\n");\
|
||||||
|
} while(0)
|
||||||
|
|
||||||
|
|
||||||
|
#define RETURN_ERROR(__VALUE, ...) do {\
|
||||||
|
LOG_ERROR(__VA_ARGS__);\
|
||||||
|
return __VALUE;\
|
||||||
|
} while(0)
|
||||||
|
|
||||||
|
#define RETURN_WARNING(__VALUE, ...) do {\
|
||||||
|
LOG_WARNING(__VA_ARGS__);\
|
||||||
|
return __VALUE;\
|
||||||
|
} while(0)
|
||||||
|
|
||||||
|
#define ASSERT_RETURN(__ASSERT, __RETURN, ...) do {\
|
||||||
|
if(!(__ASSERT)) {\
|
||||||
|
LOG_ERROR(__VA_ARGS__);\
|
||||||
|
return __RETURN;\
|
||||||
|
}\
|
||||||
|
} while(0)
|
||||||
|
|
||||||
|
#define ASSERT_RETURN_WARN(__ASSERT, __RETURN, ...) do {\
|
||||||
|
if(!(__ASSERT)) {\
|
||||||
|
LOG_WARNING(__VA_ARGS__);\
|
||||||
|
return __RETURN;\
|
||||||
|
}\
|
||||||
|
} while(0)
|
||||||
|
|
||||||
#endif // !_fencer_debug_h
|
#endif // !_fencer_debug_h
|
||||||
|
|
10
src/level.c
10
src/level.c
|
@ -54,12 +54,7 @@ size_t _count_layers(cJSON* layers, size_t* entities, size_t* automap) {
|
||||||
Level* level_from_json(cJSON* json) {
|
Level* level_from_json(cJSON* json) {
|
||||||
// allocate a new level struct
|
// allocate a new level struct
|
||||||
Level* self = malloc(sizeof(Level));
|
Level* self = malloc(sizeof(Level));
|
||||||
|
ASSERT_RETURN(self != NULL, NULL, "Failed to allocate level object.");
|
||||||
// ensure allocations succeeded and initialize
|
|
||||||
if(self == NULL) {
|
|
||||||
LOG_ERROR("Failed to allocate level");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
*self = (Level) {
|
*self = (Level) {
|
||||||
.asset_id = store_asset(self, &_deallocate_level),
|
.asset_id = store_asset(self, &_deallocate_level),
|
||||||
.transform = IdentityTransform
|
.transform = IdentityTransform
|
||||||
|
@ -109,9 +104,8 @@ Level* level_load(const char* level_id) {
|
||||||
cJSON* level = load_json_from_file(filename);
|
cJSON* level = load_json_from_file(filename);
|
||||||
|
|
||||||
if(level == NULL) {
|
if(level == NULL) {
|
||||||
LOG_ERROR("Failed to load level file %s", filename);
|
|
||||||
free(filename);
|
free(filename);
|
||||||
return NULL;
|
RETURN_ERROR(NULL, "Failed to load level from '%s'.", filename);
|
||||||
}
|
}
|
||||||
free(filename);
|
free(filename);
|
||||||
|
|
||||||
|
|
|
@ -22,10 +22,7 @@ struct Sprite {
|
||||||
Sprite* sprite_from_spritesheet(Spritesheet* sheet, size_t initial_frame) {
|
Sprite* sprite_from_spritesheet(Spritesheet* sheet, size_t initial_frame) {
|
||||||
Sprite* self = malloc(sizeof(Sprite));
|
Sprite* self = malloc(sizeof(Sprite));
|
||||||
|
|
||||||
if(self == NULL) {
|
ASSERT_RETURN(self != NULL, NULL, "Failed to allocate memory for new sprite.");
|
||||||
LOG_ERROR("Failed to allocate memory for new sprite");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
self->spritesheet = sheet;
|
self->spritesheet = sheet;
|
||||||
self->origin = (Vector){0.5f, 1.0f};
|
self->origin = (Vector){0.5f, 1.0f};
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
#include "spritesheet.h"
|
#include "spritesheet.h"
|
||||||
#include "assets.h"
|
#include "assets.h"
|
||||||
#include "render.h"
|
#include "render.h"
|
||||||
|
#include "debug.h"
|
||||||
#include <SDL2/SDL_render.h>
|
#include <SDL2/SDL_render.h>
|
||||||
#include <SDL2/SDL_image.h>
|
#include <SDL2/SDL_image.h>
|
||||||
|
|
||||||
|
@ -32,18 +33,14 @@ void _spritesheet_destroy_asset(void* self_void) {
|
||||||
|
|
||||||
Spritesheet* spritesheet_load(const char* texture_name, IVector frame_resolution) {
|
Spritesheet* spritesheet_load(const char* texture_name, IVector frame_resolution) {
|
||||||
SDL_Texture* texture = IMG_LoadTexture(g_renderer, texture_name);
|
SDL_Texture* texture = IMG_LoadTexture(g_renderer, texture_name);
|
||||||
if(texture == NULL)
|
ASSERT_RETURN(texture != NULL, NULL, "Failed to load texture from file %s.", texture_name);
|
||||||
return NULL;
|
return spritesheet_from_texture(texture, frame_resolution);
|
||||||
else
|
|
||||||
return spritesheet_from_texture(texture, frame_resolution);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Spritesheet* spritesheet_from_texture(SDL_Texture* texture, IVector frame_resolution) {
|
Spritesheet* spritesheet_from_texture(SDL_Texture* texture, IVector frame_resolution) {
|
||||||
Spritesheet* self = malloc(sizeof(Spritesheet));
|
Spritesheet* self = malloc(sizeof(Spritesheet));
|
||||||
|
|
||||||
if(self == NULL) {
|
ASSERT_RETURN(self != NULL, NULL, "Failed to allocate spritesheet.");
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
self->asset_id = store_asset(self, _spritesheet_destroy_asset);
|
self->asset_id = store_asset(self, _spritesheet_destroy_asset);
|
||||||
|
|
||||||
|
|
|
@ -26,31 +26,19 @@ struct Tilemap {
|
||||||
|
|
||||||
Tilemap* tilemap_from_autolayer(cJSON* json) {
|
Tilemap* tilemap_from_autolayer(cJSON* json) {
|
||||||
cJSON* const tileset = cJSON_GetObjectItem(json, "__tilesetDefUid");
|
cJSON* const tileset = cJSON_GetObjectItem(json, "__tilesetDefUid");
|
||||||
if(tileset == NULL || !cJSON_IsNumber(tileset)) {
|
ASSERT_RETURN(tileset != NULL && cJSON_IsNumber(tileset), NULL, "Could not find __tilesetDefUid while loading tilemap");
|
||||||
// no tileset means we cannot point at tile definitions later
|
|
||||||
LOG_ERROR("Could not find __tilesetDefUid while loading tilemap");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
cJSON* const tiles = cJSON_GetObjectItem(json, "autoLayerTiles");
|
cJSON* const tiles = cJSON_GetObjectItem(json, "autoLayerTiles");
|
||||||
if(tiles == NULL || !cJSON_IsArray(tiles)) {
|
ASSERT_RETURN(tiles != NULL && cJSON_IsArray(tiles), NULL, "Could not find autoLayerTiles while loading tilemap");
|
||||||
LOG_ERROR("Could not find autoLayerTiles while loading tilemap");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
cJSON* const wid = cJSON_GetObjectItem(json, "__cWid");
|
cJSON* const wid = cJSON_GetObjectItem(json, "__cWid");
|
||||||
|
ASSERT_RETURN(wid != NULL && cJSON_IsNumber(wid), NULL, "Could not find __cWid while loading tilemap");
|
||||||
|
|
||||||
cJSON* const hei = cJSON_GetObjectItem(json, "__cHei");
|
cJSON* const hei = cJSON_GetObjectItem(json, "__cHei");
|
||||||
if(wid == NULL || hei == NULL || !cJSON_IsNumber(wid) || !cJSON_IsNumber(hei)) {
|
ASSERT_RETURN(hei != NULL && cJSON_IsNumber(hei), NULL, "Could not find __cHei while loading tilemap");
|
||||||
// no width and height mean we cannot allocate the tile map
|
|
||||||
LOG_ERROR("Could not find __cWid or __cHei while loading tilemap");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
cJSON* const grid = cJSON_GetObjectItem(json, "__gridSize");
|
cJSON* const grid = cJSON_GetObjectItem(json, "__gridSize");
|
||||||
if(grid == NULL || !cJSON_IsNumber(grid)) {
|
ASSERT_RETURN(grid != NULL && cJSON_IsNumber(grid), NULL, "Could not find __gridSize while loading tilemap");
|
||||||
// can't know how to scale sprites
|
|
||||||
LOG_ERROR("Could not find __gridSize while loading tilemap");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
// the minimum requirements for a valid tilemap are met
|
// the minimum requirements for a valid tilemap are met
|
||||||
|
|
||||||
|
@ -69,8 +57,7 @@ Tilemap* tilemap_from_autolayer(cJSON* json) {
|
||||||
if(self->map == NULL) {
|
if(self->map == NULL) {
|
||||||
tileset_destroy(self->set);
|
tileset_destroy(self->set);
|
||||||
free(self);
|
free(self);
|
||||||
LOG_ERROR("Failed to allocate map memory");
|
RETURN_ERROR(NULL, "Failed to allocate map memory");
|
||||||
return NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const double px_to_ws = 1.0 / grid->valuedouble;
|
const double px_to_ws = 1.0 / grid->valuedouble;
|
||||||
|
|
|
@ -3,12 +3,13 @@
|
||||||
#include "spritesheet.h"
|
#include "spritesheet.h"
|
||||||
#include "assets.h"
|
#include "assets.h"
|
||||||
#include "render.h"
|
#include "render.h"
|
||||||
|
#include "shape.h"
|
||||||
#include "SDL2/SDL_image.h"
|
#include "SDL2/SDL_image.h"
|
||||||
|
|
||||||
struct TileDef {
|
struct TileDef {
|
||||||
size_t tid;
|
size_t tid;
|
||||||
Sprite* sprite;
|
Sprite* sprite;
|
||||||
// Shape* collision;
|
Shape* collision;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct Tileset {
|
struct Tileset {
|
||||||
|
@ -77,37 +78,31 @@ void _tileset_store(Tileset* self) {
|
||||||
|
|
||||||
Tileset* tileset_from_json(cJSON* json) {
|
Tileset* tileset_from_json(cJSON* json) {
|
||||||
cJSON* uid = cJSON_GetObjectItem(json, "uid");
|
cJSON* uid = cJSON_GetObjectItem(json, "uid");
|
||||||
if(uid == NULL || !cJSON_IsNumber(uid)) {
|
ASSERT_RETURN(uid != NULL && cJSON_IsNumber(uid), NULL, "Failed to find uid while loading tileset");
|
||||||
LOG_ERROR("Failed to find uid while loading tileset");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
cJSON* path = cJSON_GetObjectItem(json, "relPath");
|
cJSON* path = cJSON_GetObjectItem(json, "relPath");
|
||||||
if(path == NULL || !cJSON_IsString(path)) {
|
ASSERT_RETURN(path != NULL && cJSON_IsString(path), NULL, "Failed to find relPath while loading tileset");
|
||||||
LOG_ERROR("Failed to find relPath while loading tileset");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
cJSON* gridsize = cJSON_GetObjectItem(json, "tileGridSize");
|
cJSON* gridsize = cJSON_GetObjectItem(json, "tileGridSize");
|
||||||
if(gridsize == NULL || !cJSON_IsNumber(gridsize)) {
|
ASSERT_RETURN(gridsize != NULL && cJSON_IsNumber(gridsize), NULL, "Failed to find tileGridSize while loading tileset");
|
||||||
LOG_ERROR("Failed to find tileGridSize while loading tileset");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
SDL_Surface* atlas_surface = IMG_Load(path->valuestring);
|
SDL_Surface* atlas_surface = IMG_Load(path->valuestring);
|
||||||
if(atlas_surface == NULL) {
|
ASSERT_RETURN(atlas_surface != NULL, NULL, "Failed to load atlas image while loading tileset");
|
||||||
LOG_ERROR("Failed to load atlas image while loading tileset");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
Tileset* self = malloc(sizeof(Tileset));
|
Tileset* self = malloc(sizeof(Tileset));
|
||||||
|
if(self != NULL) {
|
||||||
|
SDL_FreeSurface(atlas_surface);
|
||||||
|
RETURN_ERROR(NULL, "Failed to allocate space for new tileset.");
|
||||||
|
}
|
||||||
|
|
||||||
SDL_Texture* texture = SDL_CreateTextureFromSurface(g_renderer, atlas_surface);
|
SDL_Texture* texture = SDL_CreateTextureFromSurface(g_renderer, atlas_surface);
|
||||||
|
if(texture == NULL) {
|
||||||
|
free(self);
|
||||||
|
SDL_FreeSurface(atlas_surface);
|
||||||
|
RETURN_ERROR(NULL, "Failed to convert atlas surface to texture");
|
||||||
|
}
|
||||||
IVector grid = {gridsize->valueint, gridsize->valueint};
|
IVector grid = {gridsize->valueint, gridsize->valueint};
|
||||||
|
|
||||||
if(self == NULL) {
|
|
||||||
LOG_ERROR("Failed to allocate space for Tileset");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
_tileset_store(self);
|
_tileset_store(self);
|
||||||
*self = (Tileset) {
|
*self = (Tileset) {
|
||||||
.uid = uid->valueint,
|
.uid = uid->valueint,
|
||||||
|
@ -143,15 +138,10 @@ Tileset* tileset_load(size_t uid) {
|
||||||
}
|
}
|
||||||
|
|
||||||
cJSON* defs = cJSON_GetObjectItem(g_levels_json, "defs");
|
cJSON* defs = cJSON_GetObjectItem(g_levels_json, "defs");
|
||||||
if(defs == NULL) {
|
ASSERT_RETURN(defs != NULL, NULL, "Failed to find defs element in levels json.");
|
||||||
LOG_ERROR("Failed to find defs element in levels json");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
cJSON* tilesets = cJSON_GetObjectItem(defs, "tilesets");
|
cJSON* tilesets = cJSON_GetObjectItem(defs, "tilesets");
|
||||||
if(tilesets == NULL) {
|
ASSERT_RETURN(tilesets != NULL, NULL, "Failed to find tileset defs region in levels json");
|
||||||
LOG_ERROR("Failed to find tilesets def region in levels json");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
cJSON* tileset = NULL;
|
cJSON* tileset = NULL;
|
||||||
cJSON_ArrayForEach(tileset, tilesets) {
|
cJSON_ArrayForEach(tileset, tilesets) {
|
||||||
|
@ -163,10 +153,7 @@ Tileset* tileset_load(size_t uid) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(tileset == NULL) {
|
ASSERT_RETURN(tileset != NULL, NULL, "Failed to find a tileset with the uid matching %zu", uid);
|
||||||
LOG_ERROR("Failed to find a tileset with the uid matching %zu", uid);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
return tileset_from_json(tileset);
|
return tileset_from_json(tileset);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue