Skip to content

Commit

Permalink
Add game engine example to Run view
Browse files Browse the repository at this point in the history
  • Loading branch information
jblanked committed Dec 12, 2024
1 parent 4429df3 commit b240f0a
Show file tree
Hide file tree
Showing 6 changed files with 173 additions and 55 deletions.
2 changes: 2 additions & 0 deletions alloc/alloc.c
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ FlipWorldApp *flip_world_app_alloc()
return NULL;
}

view_dispatcher_set_custom_event_callback(app->view_dispatcher, flip_world_custom_event_callback);

// Submenu
if (!easy_flipper_set_submenu(&app->submenu, FlipWorldViewSubmenu, VERSION_TAG, callback_exit_app, &app->view_dispatcher))
{
Expand Down
9 changes: 8 additions & 1 deletion application.fam
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,13 @@ App(
stack_size=4 * 1024,
fap_icon="app.png",
fap_category="GPIO",
fap_icon_assets="assets",
fap_description="Open World Multiplayer game, best played with the VGM."
fap_icon_assets="assets",
fap_file_assets="assets", # Do not touch this and the next line, it is needed to generate sprites
fap_extbuild=(
ExtFile(
path="${FAP_SRC_DIR}/assets",
command="${PYTHON3} ${FAP_SRC_DIR}/engine/scripts/sprite_builder.py ${FAP_SRC_DIR.abspath}/sprites ${TARGET.abspath}/sprites",
),
),
)
97 changes: 96 additions & 1 deletion callback/callback.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,68 @@
#include <callback/callback.h>

static void frame_cb(GameEngine *engine, Canvas *canvas, InputState input, void *context)
{
UNUSED(engine);
GameManager *game_manager = context;
game_manager_input_set(game_manager, input);
game_manager_update(game_manager);
game_manager_render(game_manager, canvas);
}

int32_t game_app(void *p)
{
UNUSED(p);
GameManager *game_manager = game_manager_alloc();
if (!game_manager)
{
FURI_LOG_E("Game", "Failed to allocate game manager");
return -1;
}
GameEngineSettings settings = game_engine_settings_init();
settings.target_fps = game.target_fps;
settings.show_fps = game.show_fps;
settings.always_backlight = game.always_backlight;
settings.frame_callback = frame_cb;
settings.context = game_manager;

GameEngine *engine = game_engine_alloc(settings);
if (!engine)
{
FURI_LOG_E("Game", "Failed to allocate game engine");
game_manager_free(game_manager);
return -1;
}
game_manager_engine_set(game_manager, engine);

void *game_context = NULL;
if (game.context_size > 0)
{
game_context = malloc(game.context_size);
game_manager_game_context_set(game_manager, game_context);
}
game.start(game_manager, game_context);

game_engine_run(engine);
game_engine_free(engine);

game_manager_free(game_manager);

game.stop(game_context);
if (game_context)
{
free(game_context);
}

int32_t entities = entities_get_count();
if (entities != 0)
{
FURI_LOG_E("Game", "Memory leak detected: %ld entities still allocated", entities);
return -1;
}

return 0;
}

static bool alloc_about_view(void *context);
static bool alloc_main_view(void *context);
static bool alloc_text_input_view(void *context, char *title);
Expand Down Expand Up @@ -271,6 +334,37 @@ void free_all_views(void *context, bool should_free_variable_item_list)
free_text_input_view(app);
}

static void flip_world_loader_process_callback(void *context)
{
FlipWorldApp *app = (FlipWorldApp *)context;
if (!app)
{
FURI_LOG_E(TAG, "FlipWorldApp is NULL");
return;
}

// load game
game_app(NULL);
}

bool flip_world_custom_event_callback(void *context, uint32_t index)
{
if (!context)
{
FURI_LOG_E(TAG, "context is NULL");
return false;
}
switch (index)
{
case FlipWorldCustomEventPlay:
// free_all_views(app, true);
flip_world_loader_process_callback(context);
return true;
default:
return false;
}
}

void callback_submenu_choices(void *context, uint32_t index)
{
FlipWorldApp *app = (FlipWorldApp *)context;
Expand All @@ -288,7 +382,8 @@ void callback_submenu_choices(void *context, uint32_t index)
FURI_LOG_E(TAG, "Failed to allocate main view");
return;
}
view_dispatcher_switch_to_view(app->view_dispatcher, FlipWorldViewMain);
// view_dispatcher_switch_to_view(app->view_dispatcher, FlipWorldViewMain);
view_dispatcher_send_custom_event(app->view_dispatcher, FlipWorldCustomEventPlay);
break;
case FlipWorldSubmenuIndexAbout:
free_all_views(app, true);
Expand Down
9 changes: 9 additions & 0 deletions callback/callback.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,14 @@
#include <flip_world.h>
#include <flip_storage/storage.h>

//
#include <furi.h>
#include "engine/engine.h"
#include "engine/game_engine.h"
#include "engine/game_manager_i.h"
#include "engine/level_i.h"
#include "engine/entity_i.h"

void free_all_views(void *context, bool free_variable_item_list);
bool flip_world_custom_event_callback(void *context, uint32_t index);
void callback_submenu_choices(void *context, uint32_t index);
104 changes: 52 additions & 52 deletions engine/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,55 +5,55 @@
#include "level_i.h"
#include "entity_i.h"

static void frame_cb(GameEngine *engine, Canvas *canvas, InputState input, void *context)
{
UNUSED(engine);
GameManager *game_manager = context;
game_manager_input_set(game_manager, input);
game_manager_update(game_manager);
game_manager_render(game_manager, canvas);
}

int32_t game_app(void *p)
{
UNUSED(p);
GameManager *game_manager = game_manager_alloc();

GameEngineSettings settings = game_engine_settings_init();
settings.target_fps = game.target_fps;
settings.show_fps = game.show_fps;
settings.always_backlight = game.always_backlight;
settings.frame_callback = frame_cb;
settings.context = game_manager;

GameEngine *engine = game_engine_alloc(settings);
game_manager_engine_set(game_manager, engine);

void *game_context = NULL;
if (game.context_size > 0)
{
game_context = malloc(game.context_size);
game_manager_game_context_set(game_manager, game_context);
}
game.start(game_manager, game_context);

game_engine_run(engine);
game_engine_free(engine);

game_manager_free(game_manager);

game.stop(game_context);
if (game_context)
{
free(game_context);
}

int32_t entities = entities_get_count();
if (entities != 0)
{
FURI_LOG_E("Game", "Memory leak detected: %ld entities still allocated", entities);
return -1;
}

return 0;
}
// static void frame_cb(GameEngine *engine, Canvas *canvas, InputState input, void *context)
// {
// UNUSED(engine);
// GameManager *game_manager = context;
// game_manager_input_set(game_manager, input);
// game_manager_update(game_manager);
// game_manager_render(game_manager, canvas);
// }

// int32_t game_app(void *p)
// {
// UNUSED(p);
// GameManager *game_manager = game_manager_alloc();

// GameEngineSettings settings = game_engine_settings_init();
// settings.target_fps = game.target_fps;
// settings.show_fps = game.show_fps;
// settings.always_backlight = game.always_backlight;
// settings.frame_callback = frame_cb;
// settings.context = game_manager;

// GameEngine *engine = game_engine_alloc(settings);
// game_manager_engine_set(game_manager, engine);

// void *game_context = NULL;
// if (game.context_size > 0)
// {
// game_context = malloc(game.context_size);
// game_manager_game_context_set(game_manager, game_context);
// }
// game.start(game_manager, game_context);

// game_engine_run(engine);
// game_engine_free(engine);

// game_manager_free(game_manager);

// game.stop(game_context);
// if (game_context)
// {
// free(game_context);
// }

// int32_t entities = entities_get_count();
// if (entities != 0)
// {
// FURI_LOG_E("Game", "Memory leak detected: %ld entities still allocated", entities);
// return -1;
// }

// return 0;
// }
7 changes: 6 additions & 1 deletion flip_world.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,14 @@ typedef enum
FlipWorldViewAbout, // The about screen
FlipWorldViewSettings, // The settings screen
FlipWorldViewTextInput, // The text input screen
FlipWorldlViewDialog, // The dialog screen
} FlipWorldView;

// Define a custom event for our FlipWorld application
typedef enum
{
FlipWorldCustomEventPlay, // Play the game
} FlipWorldCustomEvent;

// Each screen will have its own view
typedef struct
{
Expand Down

0 comments on commit b240f0a

Please sign in to comment.