diff --git a/data/background-day.png b/data/background-day.png new file mode 100644 index 0000000..afcb5ec Binary files /dev/null and b/data/background-day.png differ diff --git a/data/yellowbird-midflap.png b/data/yellowbird-midflap.png new file mode 100644 index 0000000..2ca3c2d Binary files /dev/null and b/data/yellowbird-midflap.png differ diff --git a/dependencies/GRRLIB/CMakeLists.txt b/dependencies/GRRLIB/CMakeLists.txt index 4ec456f..e8d8757 100644 --- a/dependencies/GRRLIB/CMakeLists.txt +++ b/dependencies/GRRLIB/CMakeLists.txt @@ -5,7 +5,7 @@ project(GRRLIB) find_package(PkgConfig REQUIRED) pkg_check_modules(PNG REQUIRED libpng) pkg_check_modules(FREETYPE REQUIRED freetype2) - +pkg_check_modules(JPEG REQUIRED libjpeg) set(GRRLIB_DIR ./source/GRRLIB/GRRLIB) set(PNGU_DIR ./source/GRRLIB/lib/pngu) @@ -29,6 +29,7 @@ set(grrlib_sources ${GRRLIB_DIR}/GRRLIB_print.c ${GRRLIB_DIR}/GRRLIB_render.c ${GRRLIB_DIR}/GRRLIB_snapshot.c + ${GRRLIB_DIR}/GRRLIB_texEdit.c ${GRRLIB_DIR}/GRRLIB_ttf.c ) @@ -36,7 +37,10 @@ add_library(GRRLIB ${grrlib_sources}) target_link_libraries(GRRLIB PRIVATE pngu) target_link_libraries(GRRLIB PRIVATE ${FREETYPE_LIBRARIES}) target_link_libraries(GRRLIB PRIVATE fat) +target_link_libraries(GRRLIB PRIVATE ${JPEG_LIBRARIES}) + target_include_directories(GRRLIB PRIVATE ${FREETYPE_INCLUDE_DIRS}) +target_include_directories(GRRLIB PRIVATE ${JPEG_INCLUDE_DIRS}) target_include_directories(GRRLIB PUBLIC ${GRRLIB_DIR}) diff --git a/source/.gitignore b/source/.gitignore index f8f794e..6f9be50 100644 --- a/source/.gitignore +++ b/source/.gitignore @@ -1 +1,2 @@ game.c +data_generated.c diff --git a/source/CMakeLists.txt b/source/CMakeLists.txt index 5a9ef26..7aefc3f 100644 --- a/source/CMakeLists.txt +++ b/source/CMakeLists.txt @@ -1,11 +1,18 @@ add_custom_command( COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/asset_generator.py ${CMAKE_CURRENT_SOURCE_DIR}/game.js ${CMAKE_CURRENT_SOURCE_DIR}/game.c OUTPUT ${CMAKE_CURRENT_SOURCE_DIR}/game.c - DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/game.js + DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/game.js ${CMAKE_CURRENT_SOURCE_DIR}/asset_generator.py COMMENT "Creating game.c from game.js" ) -add_executable(WiiDuktape main.c grrlib_duk.c game.c) +add_custom_command( + COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/data_asset_generator.py ${CMAKE_SOURCE_DIR}/data ${CMAKE_CURRENT_SOURCE_DIR}/data_generated.c + OUTPUT ${CMAKE_CURRENT_SOURCE_DIR}/data_generated.c + DEPENDS ${CMAKE_SOURCE_DIR}/data ${CMAKE_CURRENT_SOURCE_DIR}/data_asset_generator.py + COMMENT "Creating data_generated.c from the data directory" +) + +add_executable(WiiDuktape main.c grrlib_duk.c game.c data_generated.c) target_link_libraries(WiiDuktape duktape) target_link_libraries(WiiDuktape GRRLIB) ogc_create_dol(WiiDuktape) diff --git a/source/data.h b/source/data.h new file mode 100644 index 0000000..04ea762 --- /dev/null +++ b/source/data.h @@ -0,0 +1,5 @@ +#ifndef DATA_H +#define DATA_H +#include +int get_file_pointer(const char* filename, void ** data, size_t * size); +#endif diff --git a/source/data_asset_generator.py b/source/data_asset_generator.py new file mode 100755 index 0000000..88d575f --- /dev/null +++ b/source/data_asset_generator.py @@ -0,0 +1,50 @@ +#!/usr/bin/env python3 +import argparse +from pathlib import Path +from PIL import Image + +parser = argparse.ArgumentParser() +parser.add_argument("input") +parser.add_argument("output") + +args = parser.parse_args() + +input = Path(args.input) +output = Path(args.output) + +if not input.exists(): + print("Input " + str(input.absolute()) + " not found.") + raise SystemExit(1) + +file_array = list() + +for child in Path(input).iterdir(): + if child.is_file(): + file_array.append({"filename": child.name, "data": child.read_bytes()}) + +def generate_data(): + string_list = list() + for index, data in enumerate(file_array): + hexList = list() + for byte in data["data"]: + hexList.append(f"0x{byte:02x}") + string_list.append(f"unsigned char data{index}[] = {{ {','.join(hexList)} }};") + return '\n'.join(string_list) + +def generate_hashmap_init(): + string_list = list() + for index, data in enumerate(file_array): + string_list.append(f"if (strcmp(filename, \"{data["filename"]}\") == 0) {{ *data = &data{index}; *size = sizeof(data{index}); return 1; }}") + return f"""int get_file_pointer(const char* filename, void ** data, size_t * size) {{ +{'\n'.join(string_list)} +return 0; +}}""" + +code = f"""#include \"data.h\" +#include +{generate_data()} +{generate_hashmap_init()} +""" + +with open(output, 'w') as f: + f.write(code) diff --git a/source/game.js b/source/game.js index c68d0a1..d95b03e 100644 --- a/source/game.js +++ b/source/game.js @@ -11,6 +11,7 @@ const PAD_BUTTON_START = 0x1000; const PAD_BUTTON_A = 0x0100; const RED_COLOR = rgba(255, 0, 0, 255); const GREEN_COLOR = rgba(0, 255, 0, 255); +const WHITE_COLOR = rgba(255, 255, 255, 255); function rgba_compare(rgba1, rgba2) { return (rgba1[0] == rgba2[0]) && @@ -20,6 +21,7 @@ function rgba_compare(rgba1, rgba2) { } globalThis.rectangle_color = RED_COLOR; +globalThis.background = null; function swap_colors() { if (rgba_compare(rectangle_color, RED_COLOR)) { @@ -30,6 +32,11 @@ function swap_colors() { } function start() { + const background = wii.get_file("background-day.png"); + const bird = wii.get_file("yellowbird-midflap.png"); + + globalThis.background = wii.grrlib.load_texture(background); + globalThis.bird = wii.grrlib.load_texture(bird); } function update() { @@ -45,6 +52,8 @@ function update() { swap_colors(); } - wii.grrlib.fill_screen(rgba(255, 255, 255, 255)); - wii.grrlib.rectangle(0, 0, 320, 240, rectangle_color, true); + wii.grrlib.fill_screen(WHITE_COLOR); + // wii.grrlib.rectangle(0, 0, 320, 240, rectangle_color, true); + wii.grrlib.draw_img(320, 0, background, 0, 1, 1, WHITE_COLOR); + wii.grrlib.draw_img(0, 0, bird, 0, 1, 1, WHITE_COLOR); } diff --git a/source/grrlib_duk.c b/source/grrlib_duk.c index ea2f197..82c7f0b 100644 --- a/source/grrlib_duk.c +++ b/source/grrlib_duk.c @@ -1,4 +1,6 @@ #include "grrlib_duk.h" +#include "duk_config.h" +#include "duktape.h" #include static unsigned int get_color(duk_context *ctx, duk_idx_t index) { @@ -16,7 +18,6 @@ static duk_ret_t grrlib_fill_screen(duk_context *ctx) { static duk_ret_t grrlib_rectangle(duk_context *ctx) { float x = duk_to_number(ctx, 0); - float y = duk_to_number(ctx, 1); float width = duk_to_number(ctx, 2); float height = duk_to_number(ctx, 3); @@ -29,6 +30,40 @@ static duk_ret_t grrlib_rectangle(duk_context *ctx) { return 0; } +static duk_ret_t grrlib_load_texture(duk_context *ctx) { + void* file_ptr; + duk_push_string(ctx, "file_ptr"); + duk_get_prop(ctx, 0); + file_ptr = duk_get_pointer(ctx, -1); + duk_pop(ctx); + + size_t size; + duk_push_string(ctx, "size"); + duk_get_prop(ctx, 0); + size = duk_get_number(ctx, -1); + duk_pop(ctx); + + GRRLIB_texImg* texture = GRRLIB_LoadTexture(file_ptr); + + duk_push_pointer(ctx, texture); + + return 1; +} + +static duk_ret_t grrlib_draw_img(duk_context *ctx) { + float xPos = duk_to_number(ctx, 0); + float yPos = duk_to_number(ctx, 1); + void * texture = duk_get_pointer(ctx, 2); + float degrees = duk_to_number(ctx, 3); + float scaleX = duk_to_number(ctx, 4); + float scaleY = duk_to_number(ctx, 5); + unsigned int color = get_color(ctx, 6); + + GRRLIB_DrawImg(xPos, yPos, texture, degrees, scaleX, scaleY, color); + + return 0; +} + void define_grrlib_object(duk_context *ctx) { duk_idx_t grrlib_obj = duk_push_object(ctx); @@ -37,4 +72,10 @@ void define_grrlib_object(duk_context *ctx) { duk_push_c_function(ctx, grrlib_rectangle, 6); duk_put_prop_string(ctx, grrlib_obj, "rectangle"); + + duk_push_c_function(ctx, grrlib_load_texture, 1); + duk_put_prop_string(ctx, grrlib_obj, "load_texture"); + + duk_push_c_function(ctx, grrlib_draw_img, 7); + duk_put_prop_string(ctx, grrlib_obj, "draw_img"); } diff --git a/source/main.c b/source/main.c index 5c71b3a..cf2266d 100644 --- a/source/main.c +++ b/source/main.c @@ -1,6 +1,8 @@ #include #include +#include #include "grrlib_duk.h" +#include "data.h" extern const char* program; static bool running = true; @@ -30,6 +32,27 @@ static duk_ret_t pad_buttons_down(duk_context *ctx) { return 1; } +static duk_ret_t get_file(duk_context *ctx) { + const char* filename = duk_to_string(ctx, 0); + + void* ptr; + size_t size; + + if (get_file_pointer(filename, &ptr, &size)) { + duk_idx_t file_obj = duk_push_object(ctx); + + duk_push_number(ctx, size); + duk_put_prop_string(ctx, file_obj, "size"); + + duk_push_pointer(ctx, ptr); + duk_put_prop_string(ctx, file_obj, "file_ptr"); + + return 1; + } + + return duk_error(ctx, DUK_ERR_ERROR, "Error trying to get the file %s.", filename); +} + static void define_pad_object(duk_context *ctx) { duk_idx_t pad_obj = duk_push_object(ctx); @@ -55,8 +78,8 @@ static void define_wii_object(duk_context *ctx) { define_grrlib_object(ctx); duk_put_prop_string(ctx, wii_obj, "grrlib"); - duk_push_boolean(ctx, true); - duk_put_prop_string(ctx, wii_obj, "running"); + duk_push_c_function(ctx, get_file, 1); + duk_put_prop_string(ctx, wii_obj, "get_file"); } int main(int argc, char **argv) {