Game no longer crashes on Dolphin
This commit is contained in:
11
src/duskdolphin/display/texture/CMakeLists.txt
Normal file
11
src/duskdolphin/display/texture/CMakeLists.txt
Normal file
@@ -0,0 +1,11 @@
|
||||
# Copyright (c) 2026 Dominic Masters
|
||||
#
|
||||
# This software is released under the MIT License.
|
||||
# https://opensource.org/licenses/MIT
|
||||
|
||||
# Sources
|
||||
|
||||
target_sources(${DUSK_LIBRARY_TARGET_NAME}
|
||||
PUBLIC
|
||||
texturedolphin.c
|
||||
)
|
||||
188
src/duskdolphin/display/texture/texturedolphin.c
Normal file
188
src/duskdolphin/display/texture/texturedolphin.c
Normal file
@@ -0,0 +1,188 @@
|
||||
/**
|
||||
* Copyright (c) 2026 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#include "display/texture/texture.h"
|
||||
#include "assert/assert.h"
|
||||
|
||||
errorret_t textureInitDolphin(
|
||||
texturedolphin_t *texture,
|
||||
const int32_t width,
|
||||
const int32_t height,
|
||||
const textureformatdolphin_t format,
|
||||
const texturedata_t data
|
||||
) {
|
||||
// switch(format) {
|
||||
// case TEXTURE_FORMAT_RGBA:
|
||||
// assertTrue(
|
||||
// (width % 4) == 0 && (height % 4) == 0,
|
||||
// "RGB5A3 requires w/h multiple of 4 (or pad)"
|
||||
// );
|
||||
|
||||
// // Convert to RGB5A3 format
|
||||
// size_t rgbaSize = width * height * sizeof(u16);
|
||||
// texture->rgba = (u16*)memalign(32, rgbaSize);
|
||||
// assertNotNull(texture->rgba, "Failed to allocate texture RGBA data");
|
||||
|
||||
// for(uint32_t y = 0; y < height; ++y) {
|
||||
// for(uint32_t x = 0; x < width; ++x) {
|
||||
// const int src = y * width + x;
|
||||
|
||||
// const int tileX = x >> 2;
|
||||
// const int tileY = y >> 2;
|
||||
// const int tilesPerRow = width >> 2;
|
||||
// const int tileIndex = tileY * tilesPerRow + tileX;
|
||||
// const int tileBaseWords = tileIndex * 16;
|
||||
// const int inTile = ((y & 3) << 2) + (x & 3);
|
||||
// const int dest = tileBaseWords + inTile;
|
||||
|
||||
// color4b_t col = data.rgba.colors[src];
|
||||
|
||||
// u16 outCol;
|
||||
// if(col.a < 255) {
|
||||
// // 0AAA RRRR GGGG BBBB
|
||||
// outCol = (
|
||||
// (0u << 15) |
|
||||
// ((u16)(col.a >> 5) << 12) |
|
||||
// ((u16)(col.r >> 4) << 8) |
|
||||
// ((u16)(col.g >> 4) << 4) |
|
||||
// ((u16)(col.b >> 4) << 0)
|
||||
// );
|
||||
// } else {
|
||||
// // 1RRRR RRGG GGGB BBBB
|
||||
// outCol = (
|
||||
// (1u << 15) |
|
||||
// ((u16)(col.r >> 3) << 10) |
|
||||
// ((u16)(col.g >> 3) << 5) |
|
||||
// ((u16)(col.b >> 3) << 0)
|
||||
// );
|
||||
// }
|
||||
// texture->rgba[dest] = outCol;
|
||||
// }
|
||||
// }
|
||||
|
||||
// DCFlushRange(texture->rgba, rgbaSize);
|
||||
// GX_InitTexObj(
|
||||
// &texture->texObj,
|
||||
// texture->rgba,
|
||||
// width, height,
|
||||
// GX_TF_RGB5A3,
|
||||
// GX_REPEAT, GX_REPEAT,
|
||||
// GX_FALSE
|
||||
// );
|
||||
|
||||
// DCFlushRange(texture->rgba, rgbaSize);
|
||||
// GX_InvalidateTexAll();
|
||||
|
||||
// GX_InitTexObjLOD(
|
||||
// &texture->texObj,
|
||||
// GX_NEAR, GX_NEAR,
|
||||
// 0.0f, 0.0f, 0.0f,
|
||||
// GX_FALSE,
|
||||
// GX_FALSE,
|
||||
// GX_ANISO_1
|
||||
// );
|
||||
// break;
|
||||
|
||||
// case TEXTURE_FORMAT_ALPHA: {
|
||||
// assertTrue(
|
||||
// (width % 4) == 0 && (height % 4) == 0,
|
||||
// "GX_TF_I8 requires w/h multiple of 4 (or pad)"
|
||||
// );
|
||||
|
||||
// // 1 byte per pixel (I8), GX expects 4x4 tiled layout
|
||||
// const size_t alphaSize = (size_t)width * (size_t)height;
|
||||
|
||||
// texture->alpha = (u8*)memalign(32, alphaSize);
|
||||
// assertNotNull(texture->alpha, "Failed to allocate alpha texture data");
|
||||
|
||||
// const u32 tilesPerRow = ((u32)width) >> 3; // /8
|
||||
|
||||
// for (u32 y = 0; y < (u32)height; ++y) {
|
||||
// const u32 tileY = y >> 2; // /4
|
||||
// const u32 inTileY = (y & 3) << 3; // (y%4)*8
|
||||
|
||||
// for (u32 x = 0; x < (u32)width; ++x) {
|
||||
// const u32 srcI = y * (u32)width + x;
|
||||
// const u8 srcA = data.alpha.data[srcI]; // linear input
|
||||
|
||||
// const u32 tileX = x >> 3; // /8
|
||||
// const u32 tileIndex = tileY * tilesPerRow + tileX;
|
||||
|
||||
// const u32 tileBase = tileIndex * 32; // 8*4*1 = 32 bytes per tile
|
||||
// const u32 inTile = inTileY + (x & 7); // (y%4)*8 + (x%8)
|
||||
|
||||
// texture->alpha[tileBase + inTile] = 0xFF - srcA;// Fixes inverted alpha.
|
||||
// }
|
||||
// }
|
||||
|
||||
// // Flush CPU cache so GX sees the swizzled I8 texture data
|
||||
// DCFlushRange(texture->alpha, alphaSize);
|
||||
|
||||
// // Initialize GX texture object with swizzled data
|
||||
// GX_InitTexObj(
|
||||
// &texture->texObj,
|
||||
// texture->alpha,
|
||||
// width, height,
|
||||
// GX_TF_I8,
|
||||
// GX_REPEAT, GX_REPEAT,
|
||||
// GX_FALSE
|
||||
// );
|
||||
|
||||
// GX_InitTexObjLOD(
|
||||
// &texture->texObj,
|
||||
// GX_NEAR, GX_NEAR,
|
||||
// 0.0f, 0.0f, 0.0f,
|
||||
// GX_FALSE,
|
||||
// GX_FALSE,
|
||||
// GX_ANISO_1
|
||||
// );
|
||||
// break;
|
||||
// }
|
||||
|
||||
// case TEXTURE_FORMAT_PALETTE: {
|
||||
// // Not supported, convert to RGBA using lookup
|
||||
// color_t* formatted = memoryAllocate(width * height * sizeof(color_t));
|
||||
// for(int32_t i = 0; i < width * height; i++) {
|
||||
// uint8_t index = data.palette.data[i];
|
||||
// assertTrue(
|
||||
// index < data.palette.palette->colorCount,
|
||||
// "Palette index out of range"
|
||||
// );
|
||||
// formatted[i] = data.palette.palette->colors[index];
|
||||
// }
|
||||
|
||||
// textureInit(
|
||||
// texture, width, height, TEXTURE_FORMAT_RGBA,
|
||||
// (texturedata_t){
|
||||
// .rgba = { .colors = formatted }
|
||||
// }
|
||||
// );
|
||||
// memoryFree(formatted);
|
||||
// break;
|
||||
// }
|
||||
|
||||
// default:
|
||||
// assertUnreachable("Unsupported texture format for Dolphin");
|
||||
// break;
|
||||
// }
|
||||
|
||||
// texture->ready = true;
|
||||
|
||||
errorOk();
|
||||
}
|
||||
|
||||
errorret_t textureBindDolphin(texturedolphin_t *texture) {
|
||||
errorOk();
|
||||
}
|
||||
|
||||
errorret_t textureDisposeDolphin(texturedolphin_t *texture) {
|
||||
errorOk();
|
||||
}
|
||||
|
||||
void textureDolphinUploadTEV(void) {
|
||||
|
||||
}
|
||||
63
src/duskdolphin/display/texture/texturedolphin.h
Normal file
63
src/duskdolphin/display/texture/texturedolphin.h
Normal file
@@ -0,0 +1,63 @@
|
||||
/**
|
||||
* Copyright (c) 2026 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "dusk.h"
|
||||
|
||||
typedef union texturedata_u texturedata_t;
|
||||
|
||||
typedef enum {
|
||||
TEXTURE_FORMAT_RGBA = GX_TF_RGBA8,
|
||||
TEXTURE_FORMAT_PALETTE = GX_TF_CI8,
|
||||
} textureformatdolphin_t;
|
||||
|
||||
typedef struct {
|
||||
GXTexObj texObj;
|
||||
textureformatdolphin_t format;
|
||||
int32_t width;
|
||||
int32_t height;
|
||||
} texturedolphin_t;
|
||||
|
||||
/**
|
||||
* Initializes a texture.
|
||||
*
|
||||
* @param texture The texture to initialize.
|
||||
* @param width The width of the texture.
|
||||
* @param height The height of the texture.
|
||||
* @param format The format of the texture (e.g., GX_TF_RGBA8, GX_TF_CI8).
|
||||
* @param data The data for the texture, the format changes per format.
|
||||
* @return An error if the texture failed to initialize, otherwise success.
|
||||
*/
|
||||
errorret_t textureInitDolphin(
|
||||
texturedolphin_t *texture,
|
||||
const int32_t width,
|
||||
const int32_t height,
|
||||
const textureformatdolphin_t format,
|
||||
const texturedata_t data
|
||||
);
|
||||
|
||||
/**
|
||||
* Binds a texture for rendering. Providing NULL will unbind any texture.
|
||||
*
|
||||
* @param texture The texture to bind.
|
||||
* @return An error if the texture failed to bind, otherwise success.
|
||||
*/
|
||||
errorret_t textureBindDolphin(texturedolphin_t *texture);
|
||||
|
||||
/**
|
||||
* Disposes a texture.
|
||||
*
|
||||
* @param texture The texture to dispose.
|
||||
* @return An error if the texture failed to dispose, otherwise success.
|
||||
*/
|
||||
errorret_t textureDisposeDolphin(texturedolphin_t *texture);
|
||||
|
||||
/**
|
||||
* Internal method that uploads the texture environment variables to the GPU
|
||||
* for rendering. This is basically uploading the shader information.
|
||||
*/
|
||||
void textureDolphinUploadTEV(void);
|
||||
16
src/duskdolphin/display/texture/textureplatform.h
Normal file
16
src/duskdolphin/display/texture/textureplatform.h
Normal file
@@ -0,0 +1,16 @@
|
||||
/**
|
||||
* Copyright (c) 2026 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "texturedolphin.h"
|
||||
|
||||
typedef textureformatdolphin_t textureformatplatform_t;
|
||||
typedef texturedolphin_t textureplatform_t;
|
||||
|
||||
#define textureInitPlatform textureInitDolphin
|
||||
#define textureBindPlatform textureBindDolphin
|
||||
#define textureDisposePlatform textureDisposeDolphin
|
||||
Reference in New Issue
Block a user