From 0748b75d6688d3e0e2feef0c95de656af8b4f655 Mon Sep 17 00:00:00 2001 From: samstalhandske Date: Tue, 23 Dec 2025 15:10:14 +0100 Subject: [PATCH] Not finished. Need to commit. --- Makefile | 4 +- .../presentation/states/state_main_menu.c | 57 ++++++----- src/game/session/multiplayer_api.c | 8 +- src/game/session/multiplayer_api.h | 2 +- src/game/session/networking.c | 94 ++++++++++++++++--- src/todo.md | 5 +- 6 files changed, 122 insertions(+), 48 deletions(-) diff --git a/Makefile b/Makefile index e1f4f6f..bb51f3a 100644 --- a/Makefile +++ b/Makefile @@ -19,9 +19,7 @@ LIB_DIR := $(abspath libs/$(PLATFORM)) CFLAGS += -I$(LIB_DIR) LDFLAGS += -L$(LIB_DIR) -ifeq ($(PLATFORM), linux) - LIBS += -lraylib -lm -lraygui -endif +LIBS += -lraylib -lm -lraygui SRC := $(shell find -L $(SRC_DIR) -type f -name '*.c') diff --git a/src/game/presentation/states/state_main_menu.c b/src/game/presentation/states/state_main_menu.c index fb594df..28cabff 100644 --- a/src/game/presentation/states/state_main_menu.c +++ b/src/game/presentation/states/state_main_menu.c @@ -21,32 +21,41 @@ static void state_enter(Presentation_State *state) { static void state_tick(Presentation_State *state) { Presentation_State_Main_Menu_Context *ctx = (Presentation_State_Main_Menu_Context *)state->context; - { // DEBUG - if(IsKeyPressed(KEY_P)) { - printf("Shortcut to singleplayer.\n"); - game_session_init_default_settings(false, &ctx->session_settings); - ctx->session_settings.max_players = 1; + switch(ctx->mode) { + case Main_Menu_Mode_Home: { + { // DEBUG + if(IsKeyPressed(KEY_P)) { + printf("Shortcut to singleplayer.\n"); + game_session_init_default_settings(false, &ctx->session_settings); + ctx->session_settings.max_players = 1; + + if(game_instance_host_session(ctx->game_instance, ctx->session_settings)) { + ctx->ingame_ctx->game_instance = ctx->game_instance; + presentation_state_machine_go_to(&presentation_state_ingame); + } + else { + printf("Failed to play.\n"); + } + } + else if(IsKeyPressed(KEY_L)) { + printf("Shortcut to local multiplayer (2 players).\n"); + game_session_init_default_settings(false, &ctx->session_settings); + ctx->session_settings.max_players = 2; + + if(game_instance_host_session(ctx->game_instance, ctx->session_settings)) { + ctx->ingame_ctx->game_instance = ctx->game_instance; + presentation_state_machine_go_to(&presentation_state_ingame); + } + else { + printf("Failed to play.\n"); + } + } + } - if(game_instance_host_session(ctx->game_instance, ctx->session_settings)) { - ctx->ingame_ctx->game_instance = ctx->game_instance; - presentation_state_machine_go_to(&presentation_state_ingame); - } - else { - printf("Failed to play.\n"); - } + break; } - else if(IsKeyPressed(KEY_L)) { - printf("Shortcut to local multiplayer (2 players).\n"); - game_session_init_default_settings(false, &ctx->session_settings); - ctx->session_settings.max_players = 2; - - if(game_instance_host_session(ctx->game_instance, ctx->session_settings)) { - ctx->ingame_ctx->game_instance = ctx->game_instance; - presentation_state_machine_go_to(&presentation_state_ingame); - } - else { - printf("Failed to play.\n"); - } + default: { + break; } } } diff --git a/src/game/session/multiplayer_api.c b/src/game/session/multiplayer_api.c index 82c14da..8a2df1b 100644 --- a/src/game/session/multiplayer_api.c +++ b/src/game/session/multiplayer_api.c @@ -392,7 +392,7 @@ int mp_api_join(MultiplayerApi *api, return joinAccepted ? MP_API_OK : MP_API_ERR_REJECTED; } -int mp_api_game(MultiplayerApi *api, json_t *data, const char* destination) { +int mp_api_game(MultiplayerApi *api, json_t *data, const char* target_client_id) { if (!api || !data) return MP_API_ERR_ARGUMENT; if (api->sockfd < 0 || !api->session_id) return MP_API_ERR_STATE; @@ -403,8 +403,8 @@ int mp_api_game(MultiplayerApi *api, json_t *data, const char* destination) { json_object_set_new(root, "session", json_string(api->session_id)); json_object_set_new(root, "cmd", json_string("game")); - if(destination) - json_object_set_new(root, "destination", json_string(destination)); + if(target_client_id) + json_object_set_new(root, "target_client_id", json_string(target_client_id)); json_t *data_copy; if (json_is_object(data)) { @@ -612,7 +612,7 @@ static void process_line(MultiplayerApi *api, const char *line) { } if (strcmp(cmd, "joined") != 0 && - strcmp(cmd, "leaved") != 0 && + strcmp(cmd, "left") != 0 && strcmp(cmd, "game") != 0) { json_decref(root); return; diff --git a/src/game/session/multiplayer_api.h b/src/game/session/multiplayer_api.h index 507f233..2e90bd4 100644 --- a/src/game/session/multiplayer_api.h +++ b/src/game/session/multiplayer_api.h @@ -67,7 +67,7 @@ int mp_api_join(MultiplayerApi *api, json_t **out_data); /* Skickar ett "game"‑meddelande med godtycklig JSON‑data till sessionen. */ -int mp_api_game(MultiplayerApi *api, json_t *data, const char* destination); +int mp_api_game(MultiplayerApi *api, json_t *data, const char* target_client_id); /* Registrerar en lyssnare för inkommande events. Returnerar ett positivt listener‑ID, eller −1 vid fel. */ diff --git a/src/game/session/networking.c b/src/game/session/networking.c index 2bc79d2..dd58877 100644 --- a/src/game/session/networking.c +++ b/src/game/session/networking.c @@ -17,7 +17,12 @@ static void listen_callback( (void)data; - printf("#%li :: Event: '%s' from '%s'.\n", messsage_id, event, client_id); + printf("%s * #%li :: Event: '%s' from '%s'.\n", + networking->is_host ? "Host" : "Client", + messsage_id, + event, + client_id + ); assert(networking != NULL); @@ -35,8 +40,17 @@ static void listen_callback( // TODO: SS - Send a 'game' message to the joinee with information about the session? printf("Added client-id '%s' (player-index: %u) to the map.\n", client_id, player_index); + + { // TEMP: SS - Testing to see if the joinee gets a message. + json_t *gameData = json_object(); + json_object_set_new(gameData, "temp", json_integer(4)); + + mp_api_game(networking->api, gameData, NULL); + + json_decref(gameData); + } } - else if(strcmp(event, "leaved") == 0) { + else if(strcmp(event, "left") == 0) { // TODO: SS - Index the hashmap using 'client_id' as the key and attempt to get the // player-index for that client. Run 'game_session_destroy_player()'. @@ -129,12 +143,21 @@ bool networking_try_host(Game_Networking *networking, Game_Session *session, Gam return false; } + json_t *payload = json_object(); + json_object_set_new(payload, "test", json_integer(settings.max_players)); + + json_t *data = json_object(); + json_object_set_new(data, "name", json_string("My session")); // TODO: SS - Use 'settings.name'. + json_object_set_new(data, "private", json_boolean(false)); // TODO: SS - Use 'settings.private' or '!settings.public'. + json_object_set_new(data, "maxClients", json_integer(settings.max_players)); + json_object_set_new(data, "payload", payload); + char *session_id = NULL; char *local_client_id = NULL; json_t *response_data = NULL; int host_result = mp_api_host( networking->api, - NULL, // TODO: SS - Send data to server that contains the game-session's settings. + data, &session_id, &local_client_id, &response_data @@ -142,6 +165,13 @@ bool networking_try_host(Game_Networking *networking, Game_Session *session, Gam if(host_result != MP_API_OK) { printf("Failed to host; Got result: %i.\n", host_result); shutdown_api(networking); + + if(response_data != NULL) { + char *response = json_dumps(response_data, 0); + printf("Response: '%s'.\n", response); + free(response); + } + return false; } @@ -191,9 +221,10 @@ bool networking_try_join(Game_Networking *networking, Game_Session *session, con printf("Trying to join session using code: '%s' ...\n", session_id); - char *result_session_id; - char *local_client_id; - json_t *received_json; + char *result_session_id = NULL; + char *local_client_id = NULL; + json_t *received_json = NULL; + int join_result = mp_api_join( networking->api, // API. session_id, // Session-code. @@ -210,30 +241,63 @@ bool networking_try_join(Game_Networking *networking, Game_Session *session, con assert(strcmp(result_session_id, session_id) == 0); printf("Joined session '%s', local_client_id is '%s'.\n", result_session_id, local_client_id); - networking->is_host = true; + networking->is_host = false; networking->game_session = session; networking->session_id = result_session_id; networking->local_client_id = local_client_id; - + + assert(start_listening(networking)); + map_init(&networking->client_id_to_player_index); // TODO: SS - Decide how to network this.. // Should we just receive the session's settings as well as a long list of commands of what has happened throughout the match (so far) - at least one per tick? // Or, should this client receive the current state of the session? + + // TODO: SS - Set up session based on what we got in the json. + Game_Session_Settings settings; + memset(&settings, 0, sizeof(Game_Session_Settings)); + settings.online = true; + { // TEMP: SS - Get values from json. + settings.seed = 1337; // TODO: SS - Get from json. + settings.level_width = 64; // TODO: SS - Get from json. + settings.level_height = 48; // TODO: SS - Get from json. + settings.tickrate = 10.0f; // TODO: SS - Get from json. + settings.max_players = 8; // TODO: SS - Get from json. + } + if(received_json != NULL) { // TODO: SS - Read this json. It should contain valuable information about the session. + printf("received_json is NOT NULL.\n"); + + char *recv_str = json_dumps(received_json, 0); + printf("Received JSON: '%s'.\n", recv_str); + + printf("trying to get maxClients.\n"); + json_t* max_clients_json = json_object_get(received_json, "maxClients"); + if(max_clients_json != NULL) { + printf("found maxClients.\n"); + if(json_is_integer(max_clients_json)) { + printf("maxClients is integer.\n"); + long max_clients = json_integer_value(max_clients_json); + printf("Max clients is: '%lu'.\n", max_clients); + } + else { + printf("maxClients is NOT an integer.\n"); + } + } json_decref(received_json); } + else { + printf("received_json is NULL.\n"); + } - assert(start_listening(networking)); - - // TODO: SS - Set up session based on what we got in the json. - // game_session_init( - // session, - // settings - // ); + game_session_init( + session, + settings + ); return true; } diff --git a/src/todo.md b/src/todo.md index f57f6da..ee3a59c 100644 --- a/src/todo.md +++ b/src/todo.md @@ -21,5 +21,8 @@ - Right now we're moving relative to world-up. - This would fix issues with invalid inputs, for example when the player inputs RIGHT when going LEFT. - Make this an option later? +- [ ] Customize the session. +- [ ] Replays. - [ ] Sound effects + music. -- [ ] Customize the session. \ No newline at end of file +- [ ] Options menu. +- [ ] Scoreboard. \ No newline at end of file