Palettized image test.
This commit is contained in:
@@ -8,4 +8,7 @@ target_sources(${DUSK_TARGET_NAME}
|
||||
PRIVATE
|
||||
asset.c
|
||||
assetmanager.c
|
||||
)
|
||||
)
|
||||
|
||||
# Subdirs
|
||||
add_subdirectory(type)
|
@@ -11,6 +11,10 @@
|
||||
#include "assert/assert.h"
|
||||
#include "console/console.h"
|
||||
|
||||
assetdef_t ASSET_DEFINITIONS[ASSET_TYPE_COUNT] = {
|
||||
[ASSET_TYPE_PALETTE_IMAGE] = { "DPI", assetPaletteImageLoad },
|
||||
};
|
||||
|
||||
errorret_t assetInit(asset_t *asset, const char_t *filename) {
|
||||
assertNotNull(asset, "Asset cannot be NULL.");
|
||||
assertNotNull(filename, "Filename cannot be NULL.");
|
||||
@@ -27,10 +31,101 @@ errorret_t assetInit(asset_t *asset, const char_t *filename) {
|
||||
ASSET_REFERENCE_COUNT_MAX
|
||||
);
|
||||
|
||||
// Test the file can be opened. In future I may make the handle stay open for
|
||||
// a while to see if it increases performance and stops disk thrashing.
|
||||
asset->file = zip_fopen(ASSET_MANAGER.zip, filename, 0);
|
||||
if(asset->file == NULL) errorThrow("Failed to open asset file: %s", filename);
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
|
||||
consolePrint("Initialized asset: %s", filename);
|
||||
|
||||
errorOk();
|
||||
}
|
||||
|
||||
ref_t assetLock(asset_t *asset) {
|
||||
assertNotNull(asset, "Asset cannot be NULL.");
|
||||
|
||||
return refListLock(&asset->refList);
|
||||
}
|
||||
|
||||
void assetUnlock(asset_t *asset, const ref_t ref) {
|
||||
assertNotNull(asset, "Asset cannot be NULL.");
|
||||
assertTrue(ref > 0, "Reference must be greater than 0.");
|
||||
|
||||
// Just unlock the reference in the reference list.
|
||||
refListUnlock(&asset->refList, ref);
|
||||
}
|
||||
|
||||
errorret_t assetLoad(asset_t *asset) {
|
||||
assertNotNull(asset, "Asset cannot be NULL.");
|
||||
assertTrue(
|
||||
asset->state == ASSET_STATE_NOT_LOADED,
|
||||
"Asset is already loaded or loading."
|
||||
);
|
||||
|
||||
// Mark as loading.
|
||||
asset->state = ASSET_STATE_LOADING;
|
||||
|
||||
// Open the file.
|
||||
if(asset->file == NULL) {
|
||||
asset->file = zip_fopen(ASSET_MANAGER.zip, asset->filename, 0);
|
||||
if(asset->file == NULL) {
|
||||
asset->state = ASSET_STATE_ERROR;
|
||||
errorThrow("Failed to open asset file: %s", asset->filename);
|
||||
}
|
||||
}
|
||||
|
||||
// Read header.
|
||||
char_t header[ASSET_HEADER_SIZE + 1];
|
||||
memoryZero(header, ASSET_HEADER_SIZE + 1);
|
||||
zip_int64_t bytesRead = zip_fread(asset->file, header, ASSET_HEADER_SIZE);
|
||||
if(bytesRead != ASSET_HEADER_SIZE) {
|
||||
asset->state = ASSET_STATE_ERROR;
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
errorThrow("Failed to read asset header for: %s", asset->filename);
|
||||
}
|
||||
|
||||
// Check header.
|
||||
if(strlen(header) != ASSET_HEADER_SIZE) {
|
||||
asset->state = ASSET_STATE_ERROR;
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
errorThrow("Invalid asset header for: %s", asset->filename);
|
||||
}
|
||||
|
||||
// Get the asset definition based on the header.
|
||||
assetdef_t *def;
|
||||
for(uint_fast8_t i = 0; i < ASSET_TYPE_COUNT; i++) {
|
||||
if(strcmp(header, ASSET_DEFINITIONS[i].header) == 0) {
|
||||
def = &ASSET_DEFINITIONS[i];
|
||||
asset->type = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
assertNotNull(def, "Failed to find asset definition for header.");
|
||||
|
||||
// Load the asset
|
||||
errorret_t ret = def->load(asset);
|
||||
if(ret.code != ERROR_OK) {
|
||||
asset->state = ASSET_STATE_ERROR;
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
errorChain(ret);
|
||||
}
|
||||
|
||||
// Finished loading.
|
||||
asset->state = ASSET_STATE_LOADED;
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
errorOk();
|
||||
}
|
||||
|
||||
void assetDispose(asset_t *asset) {
|
||||
assertNotNull(asset, "Asset cannot be NULL.");
|
||||
|
||||
if(asset->file) {
|
||||
zip_fclose(asset->file);
|
||||
asset->file = NULL;
|
||||
}
|
||||
}
|
@@ -6,14 +6,19 @@
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "assetpaletteimage.h"
|
||||
#include "error/error.h"
|
||||
#include "util/reflist.h"
|
||||
#include <zip.h>
|
||||
|
||||
#include "asset/type/assetpaletteimage.h"
|
||||
|
||||
#define ASSET_HEADER_SIZE 3
|
||||
#define ASSET_REFERENCE_COUNT_MAX 8
|
||||
|
||||
typedef struct {
|
||||
void (*load)();
|
||||
} assetcallback_t;
|
||||
|
||||
typedef enum {
|
||||
ASSET_STATE_NOT_LOADED,
|
||||
ASSET_STATE_LOADING,
|
||||
@@ -24,18 +29,30 @@ typedef enum {
|
||||
typedef enum {
|
||||
ASSET_TYPE_UNKNOWN,
|
||||
ASSET_TYPE_PALETTE_IMAGE,
|
||||
|
||||
ASSET_TYPE_COUNT
|
||||
} assettype_t;
|
||||
|
||||
typedef struct {
|
||||
const char_t filename[FILENAME_MAX];
|
||||
typedef struct asset_s {
|
||||
char_t filename[FILENAME_MAX];
|
||||
ref_t refListArray[ASSET_REFERENCE_COUNT_MAX];
|
||||
reflist_t refList;
|
||||
assetstate_t state;
|
||||
assettype_t type;
|
||||
void *data;
|
||||
zip_file_t *file;
|
||||
|
||||
union {
|
||||
assetpaletteimage_t paletteImage;
|
||||
};
|
||||
} asset_t;
|
||||
|
||||
typedef struct {
|
||||
const char_t header[ASSET_HEADER_SIZE + 1];
|
||||
errorret_t (*load)(asset_t *asset);
|
||||
} assetdef_t;
|
||||
|
||||
extern assetdef_t ASSET_DEFINITIONS[ASSET_TYPE_COUNT];
|
||||
|
||||
/**
|
||||
* Initializes an asset structure. This should be called by the asset manager
|
||||
* only.
|
||||
@@ -44,4 +61,40 @@ typedef struct {
|
||||
* @param filename The filename of the asset.
|
||||
* @return An error code.
|
||||
*/
|
||||
errorret_t assetInit(asset_t *asset, const char_t *filename);
|
||||
errorret_t assetInit(asset_t *asset, const char_t *filename);
|
||||
|
||||
/**
|
||||
* Requests a lock on the given asset. This will increase the reference count
|
||||
* of the asset, and prevent it from being unloaded until all locks are
|
||||
* released.
|
||||
*
|
||||
* @param asset The asset to lock.
|
||||
* @return A unique reference ID for the lock.
|
||||
*/
|
||||
ref_t assetLock(asset_t *asset);
|
||||
|
||||
/**
|
||||
* Releases a lock on the given asset. This will decrease the reference count
|
||||
* of the asset, and allow it to be unloaded if there are no more locks.
|
||||
*
|
||||
* @param asset The asset to unlock.
|
||||
* @param ref The reference ID of the lock to release.
|
||||
*/
|
||||
void assetUnlock(asset_t *asset, const ref_t ref);
|
||||
|
||||
/**
|
||||
* Permission has been granted to load the asset data from disk. This should
|
||||
* only be called by the asset manager.
|
||||
*
|
||||
* @param asset The asset to load.
|
||||
* @return An error code.
|
||||
*/
|
||||
errorret_t assetLoad(asset_t *asset);
|
||||
|
||||
/**
|
||||
* Disposes of the asset, freeing any allocated memory and closing any open
|
||||
* file handles. This should only be called by the asset manager.
|
||||
*
|
||||
* @param asset The asset to dispose of.
|
||||
*/
|
||||
void assetDispose(asset_t *asset);
|
@@ -44,7 +44,18 @@ errorret_t assetManagerInit(void) {
|
||||
}
|
||||
|
||||
void assetManagerUpdate(void) {
|
||||
|
||||
// Update all assets
|
||||
asset_t *asset = ASSET_MANAGER.assets;
|
||||
while(asset < &ASSET_MANAGER.assets[ASSET_MANAGER.assetCount]) {
|
||||
if(asset->state == ASSET_STATE_LOADING) {
|
||||
// Check if the asset is loaded
|
||||
if(asset->file != NULL) {
|
||||
asset->state = ASSET_STATE_LOADED;
|
||||
consolePrint("Asset loaded: %s", asset->filename);
|
||||
}
|
||||
}
|
||||
++asset;
|
||||
}
|
||||
}
|
||||
|
||||
errorret_t assetManagerGetAsset(const char_t *filename, asset_t **outAsset) {
|
||||
@@ -71,6 +82,7 @@ errorret_t assetManagerGetAsset(const char_t *filename, asset_t **outAsset) {
|
||||
|
||||
// Pop an asset off the struct
|
||||
asset = &ASSET_MANAGER.assets[ASSET_MANAGER.assetCount++];
|
||||
*outAsset = asset;
|
||||
errorChain(assetInit(asset, filename));
|
||||
errorOk();
|
||||
}
|
||||
|
@@ -18,7 +18,7 @@
|
||||
|
||||
static const char_t ASSET_MANAGER_SEARCH_PATHS[][FILENAME_MAX] = {
|
||||
"%s/%s",
|
||||
"./%s",
|
||||
"%s",
|
||||
"../%s",
|
||||
"../../%s",
|
||||
"data/%s",
|
||||
@@ -50,7 +50,8 @@ void assetManagerUpdate(void);
|
||||
|
||||
/**
|
||||
* Get an asset by filename. This will return NULL if the asset does not exist.
|
||||
* This will not lock the asset, you must do that separately.
|
||||
* This will not lock the asset, you must do that separately. If you do not
|
||||
* lock the asset there is no guarantee the asset pointer will remain valid.
|
||||
*
|
||||
* @param filename The filename of the asset to get.
|
||||
* @param outAsset The output asset pointer.
|
||||
|
@@ -1,17 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2025 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "dusk.h"
|
||||
|
||||
#define ASSET_PALETTE_IMAGE_SIZE_MAX (256*256)
|
||||
|
||||
typedef struct {
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
uint8_t data[ASSET_PALETTE_IMAGE_SIZE_MAX];
|
||||
} assetpaletteimage_t;
|
10
src/asset/type/CMakeLists.txt
Normal file
10
src/asset/type/CMakeLists.txt
Normal file
@@ -0,0 +1,10 @@
|
||||
# Copyright (c) 2025 Dominic Masters
|
||||
#
|
||||
# This software is released under the MIT License.
|
||||
# https://opensource.org/licenses/MIT
|
||||
|
||||
# Sources
|
||||
target_sources(${DUSK_TARGET_NAME}
|
||||
PRIVATE
|
||||
assetpaletteimage.c
|
||||
)
|
57
src/asset/type/assetpaletteimage.c
Normal file
57
src/asset/type/assetpaletteimage.c
Normal file
@@ -0,0 +1,57 @@
|
||||
/**
|
||||
* Copyright (c) 2025 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#include "asset/asset.h"
|
||||
#include "display/palette/palettelist.h"
|
||||
|
||||
errorret_t assetPaletteImageLoad(asset_t *asset) {
|
||||
// Read entire palettized image.
|
||||
assetpaletteimageraw_t raw;
|
||||
zip_int64_t bytesRead = zip_fread(asset->file, &raw, sizeof(raw));
|
||||
|
||||
if(bytesRead < sizeof(raw.width) + sizeof(raw.height)) {
|
||||
errorThrow("Failed to read palette image dimensions.");
|
||||
}
|
||||
|
||||
if(raw.width <= 0 || raw.width > ASSET_PALETTE_IMAGE_WIDTH_MAX) {
|
||||
errorThrow("Invalid palette image width.");
|
||||
}
|
||||
|
||||
if(raw.height <= 0 || raw.height > ASSET_PALETTE_IMAGE_HEIGHT_MAX) {
|
||||
errorThrow("Invalid palette image height.");
|
||||
}
|
||||
|
||||
if(raw.paletteIndex >= PALETTE_LIST_COUNT) {
|
||||
errorThrow("Invalid palette index.");
|
||||
}
|
||||
|
||||
printf("Palette image dimensions: %ux%u\n", raw.width, raw.height);
|
||||
zip_int64_t expecting = (
|
||||
sizeof(raw.width) +
|
||||
sizeof(raw.height) +
|
||||
sizeof(raw.paletteIndex) +
|
||||
(raw.width * raw.height * sizeof(uint8_t))
|
||||
);
|
||||
if(bytesRead != expecting) {
|
||||
errorThrow("Incorrect palette filesize.");
|
||||
}
|
||||
|
||||
textureInit(
|
||||
&asset->paletteImage.texture,
|
||||
(int32_t)raw.width,
|
||||
(int32_t)raw.height,
|
||||
TEXTURE_FORMAT_PALETTE,
|
||||
(texturedata_t){
|
||||
.palette = {
|
||||
.palette = raw.paletteIndex,
|
||||
.data = raw.palette
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
errorOk();
|
||||
}
|
40
src/asset/type/assetpaletteimage.h
Normal file
40
src/asset/type/assetpaletteimage.h
Normal file
@@ -0,0 +1,40 @@
|
||||
/**
|
||||
* Copyright (c) 2025 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "error/error.h"
|
||||
#include "display/texture/texture.h"
|
||||
|
||||
#define ASSET_PALETTE_IMAGE_WIDTH_MAX 256
|
||||
#define ASSET_PALETTE_IMAGE_HEIGHT_MAX 256
|
||||
#define ASSET_PALETTE_IMAGE_SIZE_MAX ( \
|
||||
ASSET_PALETTE_IMAGE_WIDTH_MAX * ASSET_PALETTE_IMAGE_HEIGHT_MAX \
|
||||
)
|
||||
|
||||
typedef struct asset_s asset_t;
|
||||
|
||||
#pragma pack(push, 1)
|
||||
typedef struct {
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
uint8_t paletteIndex;
|
||||
uint8_t palette[ASSET_PALETTE_IMAGE_SIZE_MAX];
|
||||
} assetpaletteimageraw_t;
|
||||
#pragma pack(pop)
|
||||
|
||||
typedef struct {
|
||||
texture_t texture;
|
||||
} assetpaletteimage_t;
|
||||
|
||||
/**
|
||||
* Loads a palette image asset from the given asset structure. The asset must
|
||||
* be of type ASSET_TYPE_PALETTE_IMAGE and must be loaded.
|
||||
*
|
||||
* @param asset The asset to load the palette image from.
|
||||
* @return An error code.
|
||||
*/
|
||||
errorret_t assetPaletteImageLoad(asset_t *asset);
|
@@ -11,8 +11,10 @@
|
||||
#include "display/framebuffer/framebuffer.h"
|
||||
#include "display/scene/scenemanager.h"
|
||||
#include "display/mesh/quad.h"
|
||||
#include "asset/assetmanager.h"
|
||||
|
||||
camera_t SCENE_OVERWORLD_CAMERA;
|
||||
asset_t *testAsset;
|
||||
|
||||
void sceneOverworldInit(void) {
|
||||
cameraInit(&SCENE_OVERWORLD_CAMERA);
|
||||
@@ -20,6 +22,10 @@ void sceneOverworldInit(void) {
|
||||
|
||||
scene_t *scene = &SCENE_MANAGER_SCENES[SCENE_TYPE_OVERWORLD];
|
||||
scene->flags |= SCENE_FLAG_ACTIVE | SCENE_FLAG_VISIBLE;
|
||||
|
||||
assetManagerGetAsset("entities.dpi", &testAsset);
|
||||
ref_t lock = assetLock(testAsset);
|
||||
assetLoad(testAsset);
|
||||
}
|
||||
|
||||
void sceneOverworldUpdate(void) {
|
||||
@@ -35,7 +41,7 @@ void sceneOverworldRender(void) {
|
||||
// Draw overlay layer.
|
||||
|
||||
spriteBatchPush(
|
||||
NULL,
|
||||
&testAsset->paletteImage.texture,
|
||||
0.0f, 0.0f, 12.0f, 12.0f,
|
||||
0xFF, 0x00, 0x00, 0xFF,
|
||||
0.0f, 0.0f, 1.0f, 1.0f
|
||||
|
@@ -9,6 +9,7 @@
|
||||
#include "assert/assert.h"
|
||||
#include "util/memory.h"
|
||||
#include "util/math.h"
|
||||
#include "display/palette/palettelist.h"
|
||||
|
||||
const texture_t *TEXTURE_BOUND = NULL;
|
||||
|
||||
@@ -17,7 +18,7 @@ void textureInit(
|
||||
const int32_t width,
|
||||
const int32_t height,
|
||||
const textureformat_t format,
|
||||
const void *data
|
||||
const texturedata_t data
|
||||
) {
|
||||
assertNotNull(texture, "Texture cannot be NULL");
|
||||
assertTrue(width > 0 && height > 0, "width/height must be greater than 0");
|
||||
@@ -40,15 +41,96 @@ void textureInit(
|
||||
#if DISPLAY_SDL2
|
||||
glGenTextures(1, &texture->id);
|
||||
glBindTexture(GL_TEXTURE_2D, texture->id);
|
||||
glTexImage2D(
|
||||
GL_TEXTURE_2D, 0, format, width, height, 0,
|
||||
format, GL_UNSIGNED_BYTE, data
|
||||
);
|
||||
|
||||
switch(format) {
|
||||
case TEXTURE_FORMAT_RGBA:
|
||||
assertNotNull(data.rgba.colors, "RGBA texture data cannot be NULL");
|
||||
glTexImage2D(
|
||||
GL_TEXTURE_2D, 0, format, width, height, 0,
|
||||
format, GL_UNSIGNED_BYTE, (void*)data.rgba.colors
|
||||
);
|
||||
break;
|
||||
|
||||
case TEXTURE_FORMAT_ALPHA:
|
||||
assertNotNull(data.alpha.data, "Alpha texture data cannot be NULL");
|
||||
glTexImage2D(
|
||||
GL_TEXTURE_2D, 0, format, width, height, 0,
|
||||
format, GL_UNSIGNED_BYTE, (void*)data.alpha.data
|
||||
);
|
||||
break;
|
||||
|
||||
case TEXTURE_FORMAT_PALETTE:
|
||||
assertNotNull(data.palette.data, "Palette texture data cannot be NULL");
|
||||
assertTrue(
|
||||
data.palette.palette < PALETTE_LIST_COUNT,
|
||||
"Palette index out of range"
|
||||
);
|
||||
|
||||
const palette_t *pal = PALETTE_LIST[data.palette.palette];
|
||||
assertNotNull(pal, "Palette cannot be NULL");
|
||||
GLenum err = glGetError();
|
||||
if (err != GL_NO_ERROR) {
|
||||
assertUnreachable("GL Error before setting color table");
|
||||
}
|
||||
|
||||
// Do we support paletted textures?
|
||||
bool_t havePalTex = false;
|
||||
GLint mask = 0;
|
||||
glGetIntegerv(GL_CONTEXT_PROFILE_MASK, &mask);
|
||||
if(mask & GL_CONTEXT_CORE_PROFILE_BIT) {
|
||||
GLint n=0; glGetIntegerv(GL_NUM_EXTENSIONS, &n);
|
||||
for (GLint i=0; i<n; ++i) {
|
||||
const char* e = (const char*)glGetStringi(GL_EXTENSIONS, i);
|
||||
if (e && strcmp(e, "GL_EXT_paletted_texture")==0) { havePalTex = true; break; }
|
||||
}
|
||||
} else {
|
||||
const char* ext = (const char*)glGetString(GL_EXTENSIONS);
|
||||
havePalTex = ext && strstr(ext, "GL_EXT_paletted_texture");
|
||||
}
|
||||
|
||||
if(!havePalTex) {
|
||||
// Not supported, convert to RGBA using lookup
|
||||
color_t formatted[width * height];
|
||||
for(int32_t i = 0; i < width * height; i++) {
|
||||
uint8_t index = data.palette.data[i];
|
||||
assertTrue(
|
||||
index < pal->colorCount,
|
||||
"Palette index out of range"
|
||||
);
|
||||
formatted[i] = pal->colors[index];
|
||||
}
|
||||
glTexImage2D(
|
||||
GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0,
|
||||
GL_RGBA, GL_UNSIGNED_BYTE, (void*)formatted
|
||||
);
|
||||
} else {
|
||||
// Supported.
|
||||
glColorTableEXT(
|
||||
GL_TEXTURE_2D, GL_RGBA, pal->colorCount, GL_RGBA,
|
||||
GL_UNSIGNED_BYTE, (const void*)pal->colors
|
||||
);
|
||||
glTexImage2D(
|
||||
GL_TEXTURE_2D,
|
||||
0, GL_COLOR_INDEX8_EXT,
|
||||
width, height,
|
||||
0, GL_COLOR_INDEX8_EXT,
|
||||
GL_UNSIGNED_BYTE, (void*)data.palette.data
|
||||
);
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
assertUnreachable("Unknown texture format");
|
||||
break;
|
||||
}
|
||||
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_BASE_LEVEL, 0);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, 0);
|
||||
#endif
|
||||
|
@@ -13,6 +13,7 @@ typedef enum {
|
||||
#if DISPLAY_SDL2
|
||||
TEXTURE_FORMAT_RGBA = GL_RGBA,
|
||||
TEXTURE_FORMAT_ALPHA = GL_ALPHA,
|
||||
TEXTURE_FORMAT_PALETTE = GL_COLOR_INDEX8_EXT,
|
||||
#endif
|
||||
} textureformat_t;
|
||||
|
||||
@@ -25,6 +26,21 @@ typedef struct {
|
||||
int32_t height;
|
||||
} texture_t;
|
||||
|
||||
typedef union {
|
||||
struct {
|
||||
color_t *colors;
|
||||
} rgba;
|
||||
|
||||
struct {
|
||||
uint8_t palette;
|
||||
uint8_t *data;
|
||||
} palette;
|
||||
|
||||
struct {
|
||||
uint8_t *data;
|
||||
} alpha;
|
||||
} texturedata_t;
|
||||
|
||||
extern const texture_t *TEXTURE_BOUND;
|
||||
|
||||
/**
|
||||
@@ -34,14 +50,14 @@ extern const texture_t *TEXTURE_BOUND;
|
||||
* @param width The width of the texture.
|
||||
* @param height The height of the texture.
|
||||
* @param format The format of the texture (e.g., GL_RGBA, GL_ALPHA).
|
||||
* @param data The pixel data for the texture.
|
||||
* @param data The data for the texture, the format changes per format.
|
||||
*/
|
||||
void textureInit(
|
||||
texture_t *texture,
|
||||
const int32_t width,
|
||||
const int32_t height,
|
||||
const textureformat_t format,
|
||||
const void *data
|
||||
const texturedata_t data
|
||||
);
|
||||
|
||||
/**
|
||||
|
@@ -15,7 +15,6 @@
|
||||
|
||||
engine_t ENGINE;
|
||||
|
||||
asset_t *testAsset;
|
||||
|
||||
errorret_t engineInit(void) {
|
||||
memoryZero(&ENGINE, sizeof(engine_t));
|
||||
@@ -28,8 +27,6 @@ errorret_t engineInit(void) {
|
||||
errorChain(displayInit());
|
||||
rpgInit();
|
||||
|
||||
errorChain(assetManagerGetAsset("entities.dpi", &testAsset));
|
||||
|
||||
errorOk();
|
||||
}
|
||||
|
||||
|
@@ -30,7 +30,7 @@ ref_t refListLock(reflist_t *list) {
|
||||
assertFalse(refListIsFull(list), "Reference list is full");
|
||||
|
||||
ref_t ref = list->refNext++;
|
||||
assertTrue(ref > 0, "Reference ID overflow");
|
||||
assertTrue(ref >= 0, "Reference ID overflow");
|
||||
assertTrue(ref < UINT16_MAX, "Reference ID too large.");
|
||||
|
||||
bool_t empty = list->onNotEmpty && refListIsEmpty(list);
|
||||
|
Reference in New Issue
Block a user