Prog on fixing psp alpha textures
All checks were successful
Build Dusk / run-tests (push) Successful in 1m20s
Build Dusk / build-linux (push) Successful in 1m39s
Build Dusk / build-psp (push) Successful in 1m51s
Build Dusk / build-dolphin (push) Successful in 2m36s

This commit is contained in:
2026-02-07 15:29:29 -06:00
parent cbe51cc8d0
commit 14f3f464c7
8 changed files with 133 additions and 97 deletions

View File

@@ -118,7 +118,7 @@ elseif(DUSK_TARGET_SYSTEM STREQUAL "psp")
elseif(DUSK_TARGET_SYSTEM STREQUAL "gamecube" OR DUSK_TARGET_SYSTEM STREQUAL "wii")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-rtti -fno-exceptions")
configure_file(opengl.pc.in opengl.pc @ONLY)
# configure_file(opengl.pc.in opengl.pc @ONLY)
find_package(PkgConfig REQUIRED)
pkg_check_modules(zip IMPORTED_TARGET libzip)
target_compile_definitions(${DUSK_LIBRARY_TARGET_NAME} PUBLIC

View File

@@ -17,19 +17,18 @@ if PLATFORM == "psp" then
inputBind("lstick_left", INPUT_ACTION_LEFT)
inputBind("lstick_right", INPUT_ACTION_RIGHT)
elseif PLATFORM == "gamecube" then
-- inputBind("start", INPUT_ACTION_RAGEQUIT)
-- inputBind("dpad_up", INPUT_ACTION_UP)
-- inputBind("dpad_down", INPUT_ACTION_DOWN)
-- inputBind("dpad_left", INPUT_ACTION_LEFT)
-- inputBind("dpad_right", INPUT_ACTION_RIGHT)
-- inputBind("button_b", INPUT_ACTION_CANCEL)
-- inputBind("button_a", INPUT_ACTION_ACCEPT)
-- inputBind("button_start", INPUT_ACTION_RAGEQUIT)
-- inputBind("lstick_up", INPUT_ACTION_UP)
-- inputBind("lstick_down", INPUT_ACTION_DOWN)
-- inputBind("lstick_left", INPUT_ACTION_LEFT)
-- inputBind("lstick_right", INPUT_ACTION_RIGHT)
elseif DOLPHIN then
inputBind("up", INPUT_ACTION_UP)
inputBind("down", INPUT_ACTION_DOWN)
inputBind("left", INPUT_ACTION_LEFT)
inputBind("right", INPUT_ACTION_RIGHT)
inputBind("circle", INPUT_ACTION_CANCEL)
inputBind("cross", INPUT_ACTION_ACCEPT)
inputBind("z", INPUT_ACTION_RAGEQUIT)
inputBind("lstick_up", INPUT_ACTION_UP)
inputBind("lstick_down", INPUT_ACTION_DOWN)
inputBind("lstick_left", INPUT_ACTION_LEFT)
inputBind("lstick_right", INPUT_ACTION_RIGHT)
else
if INPUT_KEYBOARD then

View File

@@ -3,5 +3,5 @@
# This software is released under the MIT License.
# https://opensource.org/licenses/MIT
# add_asset(TILESET minogram.png type=ALPHA tileWidth=6 tileHeight=10 columns=16 rows=6)
add_asset(TILESET minogram.png type=PALETTIZED tileWidth=6 tileHeight=10 columns=16 rows=6)# Fixes PSP rendering
add_asset(TILESET minogram.png type=ALPHA tileWidth=6 tileHeight=10 columns=16 rows=6)
# add_asset(TILESET minogram.png type=PALETTIZED tileWidth=6 tileHeight=10 columns=16 rows=6)# Fixes PSP rendering

View File

@@ -1,10 +0,0 @@
prefix=@CMAKE_INSTALL_PREFIX@
libdir=${prefix}/lib
includedir=${prefix}/include
Name: OpenGL
Description: OpenGL (without GLX) library and headers.
Version: @PROJECT_VERSION@
Libs.private: -lstdc++ -logc -lm
Libs: -L${libdir} -lopengx
Cflags: -I${includedir}

View File

@@ -26,6 +26,7 @@ void textureInit(
memoryZero(texture, sizeof(texture_t));
texture->width = width;
texture->height = height;
texture->format = format;
#if PSP
assertTrue(
@@ -50,20 +51,83 @@ void textureInit(
);
break;
case TEXTURE_FORMAT_ALPHA:
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
// RGB = vertex color
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_PRIMARY_COLOR);
// A = texture alpha
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_TEXTURE);
case TEXTURE_FORMAT_ALPHA: {
assertNotNull(data.alpha.data, "Alpha texture data cannot be NULL");
#if PSP
// PSP kinda broken with alpha textures, so we convert it to paletted
// texture here.
uint8_t colorCount = 0;
uint8_t alphas[UINT8_MAX] = { 0 };
uint8_t colorIndex[width * height];
for(int32_t i = 0; i < width * height; i++) {
uint8_t alpha = data.alpha.data[i];
glTexImage2D(
GL_TEXTURE_2D, 0, format, width, height, 0,
format, GL_UNSIGNED_BYTE, (void*)data.alpha.data
);
// Already in the palette?
bool_t exists = false;
uint8_t j = 0;
for(j = 0; j < colorCount; j++) {
if(alphas[j] != alpha) continue;
exists = true;
break;
}
// if found use existing index, otherwise add to palette
if(exists) {
colorIndex[i] = j;
continue;
}
// Should never happen given the format, but just in case:
assertTrue(
colorCount < UINT8_MAX,
"Too many unique alpha values for paletted texture"
);
colorIndex[i] = colorCount;
alphas[colorCount] = alpha;
colorCount++;
}
// Pad color count to power of two for PSP
uint8_t paddedColorCount = mathNextPowTwo(colorCount);
printf(
"Converted alpha texture to paletted format with %u unique alpha values (padded to %u)\n",
colorCount, paddedColorCount
);
// Create a palette with the unique alpha values
texture->palette = (color4b_t*)memoryAllocate(
sizeof(color4b_t) * paddedColorCount
);
memoryZero(texture->palette, sizeof(color4b_t) * paddedColorCount);
for(uint8_t i = 0; i < colorCount; i++) {
texture->palette[i].r = 0;
texture->palette[i].g = 0;
texture->palette[i].b = 0;
texture->palette[i].a = alphas[i];
}
printf("Uploading paletted texture to GPU\n");
texture->format = TEXTURE_FORMAT_PALETTE;
glTexImage2D(
GL_TEXTURE_2D,
0, GL_COLOR_INDEX8_EXT,
width, height,
0, GL_COLOR_INDEX8_EXT,
GL_UNSIGNED_BYTE, (void*)colorIndex
);
glColorTableEXT(
GL_TEXTURE_2D, GL_RGBA, paddedColorCount, GL_RGBA,
GL_UNSIGNED_BYTE, (const void*)texture->palette
);
#else
glTexImage2D(
GL_TEXTURE_2D, 0, format, width, height, 0,
format, GL_UNSIGNED_BYTE, (void*)data.alpha.data
);
#endif
break;
}
case TEXTURE_FORMAT_PALETTE:
assertNotNull(data.palette.data, "Palette texture data cannot be NULL");
@@ -155,7 +219,6 @@ void textureInit(
texture->ready = true;
#elif DOLPHIN
texture->format = format;
switch(format) {
case TEXTURE_FORMAT_RGBA:
@@ -330,6 +393,12 @@ void textureDispose(texture_t *texture) {
#if DISPLAY_SDL2
glDeleteTextures(1, &texture->id);
#if PSP
if(texture->palette) {
memoryFree(texture->palette);
texture->palette = NULL;
}
#endif
#elif DOLPHIN
switch(texture->format) {
case TEXTURE_FORMAT_RGBA:

View File

@@ -24,15 +24,18 @@ typedef enum {
typedef struct {
#if DISPLAY_SDL2
GLuint id;
#if PSP
color4b_t *palette;
#endif
#elif DOLPHIN
GXTexObj texObj;
textureformat_t format;
union {
u16 *rgba;
u8 *alpha;
};
#endif
textureformat_t format;
bool_t ready;
int32_t width;
int32_t height;

View File

@@ -27,10 +27,10 @@ inputbuttondata_t INPUT_BUTTON_DATA[] = {
{ .name = "l", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = SDL_CONTROLLER_BUTTON_LEFTSHOULDER } },
{ .name = "r", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = SDL_CONTROLLER_BUTTON_RIGHTSHOULDER } },
{ .name = "lstick_positive_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTX, .positive = true } } },
{ .name = "lstick_negative_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTX, .positive = false } } },
{ .name = "lstick_positive_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTY, .positive = true } } },
{ .name = "lstick_negative_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTY, .positive = false } } },
{ .name = "lstick_down", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTX, .positive = true } } },
{ .name = "lstick_up", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTX, .positive = false } } },
{ .name = "lstick_right", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTY, .positive = true } } },
{ .name = "lstick_left", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = SDL_CONTROLLER_AXIS_LEFTY, .positive = false } } },
#endif
#endif
@@ -173,58 +173,30 @@ inputbuttondata_t INPUT_BUTTON_DATA[] = {
#endif
#elif DOLPHIN
#if WII
#if INPUT_GAMEPAD == 1
{ .name = "a", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_A } },
{ .name = "b", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_B } },
{ .name = "x", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_X } },
{ .name = "y", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_Y } },
{ .name = "start", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_START } },
{ .name = "dpad_up", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_UP } },
{ .name = "dpad_down", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_DOWN } },
{ .name = "dpad_left", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_LEFT } },
{ .name = "dpad_right", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_RIGHT } },
{ .name = "l", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_L } },
{ .name = "r", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_R } },
{ .name = "z", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_Z } },
{ .name = "menu", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_MENU } },
{ .name = "lstick_positive_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = true } } },
{ .name = "lstick_negative_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = false } } },
{ .name = "lstick_positive_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = true } } },
{ .name = "lstick_negative_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = false } } },
{ .name = "cstick_positive_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = true } } },
{ .name = "cstick_negative_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = false } } },
{ .name = "cstick_positive_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = true } } },
{ .name = "cstick_negative_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = false } } },
{ .name = "ltrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_LEFT, .positive = true } } },
{ .name = "rtrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_RIGHT, .positive = true } } },
#endif
#elif GAMECUBE
#if INPUT_GAMEPAD == 1
{ .name = "a", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_A } },
{ .name = "b", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_B } },
{ .name = "x", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_X } },
{ .name = "y", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_Y } },
{ .name = "start", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_START } },
{ .name = "dpad_up", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_UP } },
{ .name = "dpad_down", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_DOWN } },
{ .name = "dpad_left", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_LEFT } },
{ .name = "dpad_right", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_RIGHT } },
{ .name = "l", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_L } },
{ .name = "r", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_R } },
{ .name = "z", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_Z } },
{ .name = "menu", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_MENU } },
{ .name = "lstick_positive_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = true } } },
{ .name = "lstick_negative_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = false } } },
{ .name = "lstick_positive_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = true } } },
{ .name = "lstick_negative_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = false } } },
{ .name = "cstick_positive_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = true } } },
{ .name = "cstick_negative_x", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = false } } },
{ .name = "cstick_positive_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = true } } },
{ .name = "cstick_negative_y", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = false } } },
{ .name = "ltrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_LEFT, .positive = true } } },
{ .name = "rtrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_RIGHT, .positive = true } } },
#endif
#if INPUT_GAMEPAD == 1
{ .name = "a", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_A } },
{ .name = "b", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_B } },
{ .name = "x", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_X } },
{ .name = "y", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_Y } },
{ .name = "start", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_START } },
{ .name = "up", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_UP } },
{ .name = "down", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_DOWN } },
{ .name = "left", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_LEFT } },
{ .name = "right", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_RIGHT } },
{ .name = "l", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_L } },
{ .name = "r", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_R } },
{ .name = "z", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_TRIGGER_Z } },
{ .name = "menu", { .type = INPUT_BUTTON_TYPE_GAMEPAD, .gpButton = PAD_BUTTON_MENU } },
{ .name = "lstick_up", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = true } } },
{ .name = "lstick_down", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_X, .positive = false } } },
{ .name = "lstick_left", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = true } } },
{ .name = "lstick_right", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_LEFT_Y, .positive = false } } },
{ .name = "rstick_up", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = true } } },
{ .name = "rstick_down", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_X, .positive = false } } },
{ .name = "rstick_left", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = true } } },
{ .name = "rstick_right", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_C_Y, .positive = false } } },
{ .name = "ltrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_LEFT, .positive = true } } },
{ .name = "rtrigger", { .type = INPUT_BUTTON_TYPE_GAMEPAD_AXIS, .gpAxis = { .axis = INPUT_GAMEPAD_AXIS_TRIGGER_RIGHT, .positive = true } } },
#endif
#endif

View File

@@ -19,4 +19,7 @@ void modulePlatform(scriptcontext_t *ctx) {
assertNotNull(ctx, "Script context cannot be NULL");
scriptContextExec(ctx, PLATFORM_VALUE);
#if DOLPHIN
scriptContextExec(ctx, "DOLPHIN = true");
#endif
}