Tweaks to ENABLE_REMOTE_CONTROL usage & sail hooks (#5928)

This commit is contained in:
Garrett Cox
2025-11-10 11:33:28 -06:00
committed by GitHub
parent 33929534f5
commit 754d79a86e
10 changed files with 100 additions and 166 deletions

View File

@@ -1,5 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#include "CrowdControl.h"
#include "CrowdControlTypes.h"
#include <libultraship/bridge.h>
@@ -629,4 +627,3 @@ CrowdControl::Effect* CrowdControl::ParseMessage(nlohmann::json dataReceived) {
return effect;
}
#endif

View File

@@ -1,4 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#ifndef NETWORK_CROWD_CONTROL_H
#define NETWORK_CROWD_CONTROL_H
#ifdef __cplusplus
@@ -87,4 +86,3 @@ class CrowdControl : public Network {
#endif // __cplusplus
#endif // NETWORK_CROWD_CONTROL_H
#endif // ENABLE_REMOTE_CONTROL

View File

@@ -1,5 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#include "Network.h"
#include <spdlog/spdlog.h>
#include <libultraship/libultraship.h>
@@ -7,6 +5,7 @@
// MARK: - Public
void Network::Enable(const char* host, uint16_t port) {
#ifdef ENABLE_REMOTE_CONTROL
if (isEnabled) {
return;
}
@@ -23,6 +22,7 @@ void Network::Enable(const char* host, uint16_t port) {
}
receiveThread = std::thread(&Network::ReceiveFromServer, this);
#endif
}
void Network::Disable() {
@@ -47,8 +47,10 @@ void Network::OnDisconnected() {
}
void Network::SendDataToRemote(const char* payload) {
#ifdef ENABLE_REMOTE_CONTROL
SPDLOG_DEBUG("[Network] Sending data: {}", payload);
SDLNet_TCP_Send(networkSocket, payload, strlen(payload) + 1);
#endif
}
void Network::SendJsonToRemote(nlohmann::json payload) {
@@ -58,6 +60,7 @@ void Network::SendJsonToRemote(nlohmann::json payload) {
// MARK: - Private
void Network::ReceiveFromServer() {
#ifdef ENABLE_REMOTE_CONTROL
while (isEnabled) {
while (!isConnected && isEnabled) {
SPDLOG_TRACE("[Network] Attempting to make connection to server...");
@@ -123,6 +126,7 @@ void Network::ReceiveFromServer() {
SPDLOG_INFO("[Network] Ending receiving thread...");
}
}
#endif
}
void Network::HandleRemoteData(char payload[512]) {
@@ -141,5 +145,3 @@ void Network::HandleRemoteJson(std::string payload) {
OnIncomingJson(jsonPayload);
}
#endif // ENABLE_REMOTE_CONTROL

View File

@@ -1,16 +1,19 @@
#ifdef ENABLE_REMOTE_CONTROL
#ifndef NETWORK_H
#define NETWORK_H
#ifdef __cplusplus
#include <thread>
#ifdef ENABLE_REMOTE_CONTROL
#include <SDL2/SDL_net.h>
#endif
#include <nlohmann/json.hpp>
class Network {
private:
#ifdef ENABLE_REMOTE_CONTROL
IPaddress networkAddress;
TCPsocket networkSocket;
#endif
std::thread receiveThread;
std::string receivedData;
@@ -47,4 +50,3 @@ class Network {
#endif // __cplusplus
#endif // NETWORK_H
#endif // ENABLE_REMOTE_CONTROL

View File

@@ -1,5 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#include "Sail.h"
#include <libultraship/bridge.h>
#include <libultraship/libultraship.h>
@@ -336,57 +334,20 @@ GameInteractionEffectBase* Sail::EffectFromJson(nlohmann::json payload) {
}
void Sail::RegisterHooks() {
static HOOK_ID onTransitionEndHook = 0;
static HOOK_ID onLoadGameHook = 0;
static HOOK_ID onExitGameHook = 0;
static HOOK_ID onItemReceiveHook = 0;
static HOOK_ID onEnemyDefeatHook = 0;
static HOOK_ID onActorInitHook = 0;
static HOOK_ID onFlagSetHook = 0;
static HOOK_ID onFlagUnsetHook = 0;
static HOOK_ID onSceneFlagSetHook = 0;
static HOOK_ID onSceneFlagUnsetHook = 0;
COND_HOOK(OnTransitionEnd, isConnected, [&](int32_t sceneNum) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnTransitionEnd>(onTransitionEndHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnLoadGame>(onLoadGameHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnExitGame>(onExitGameHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnItemReceive>(onItemReceiveHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnEnemyDefeat>(onEnemyDefeatHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnActorInit>(onActorInitHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnFlagSet>(onFlagSetHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnFlagUnset>(onFlagUnsetHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnSceneFlagSet>(onSceneFlagSetHook);
GameInteractor::Instance->UnregisterGameHook<GameInteractor::OnSceneFlagUnset>(onSceneFlagUnsetHook);
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnTransitionEnd";
payload["hook"]["sceneNum"] = sceneNum;
onTransitionEndHook = 0;
onLoadGameHook = 0;
onExitGameHook = 0;
onItemReceiveHook = 0;
onEnemyDefeatHook = 0;
onActorInitHook = 0;
onFlagSetHook = 0;
onFlagUnsetHook = 0;
onSceneFlagSetHook = 0;
onSceneFlagUnsetHook = 0;
SendJsonToRemote(payload);
});
if (!isConnected) {
return;
}
onTransitionEndHook =
GameInteractor::Instance->RegisterGameHook<GameInteractor::OnTransitionEnd>([&](int32_t sceneNum) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnTransitionEnd";
payload["hook"]["sceneNum"] = sceneNum;
SendJsonToRemote(payload);
});
onLoadGameHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnLoadGame>([&](int32_t fileNum) {
COND_HOOK(OnLoadGame, isConnected, [&](int32_t fileNum) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
@@ -398,7 +359,8 @@ void Sail::RegisterHooks() {
SendJsonToRemote(payload);
});
onExitGameHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnExitGame>([&](int32_t fileNum) {
COND_HOOK(OnExitGame, isConnected, [&](int32_t fileNum) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
@@ -410,21 +372,21 @@ void Sail::RegisterHooks() {
SendJsonToRemote(payload);
});
onItemReceiveHook =
GameInteractor::Instance->RegisterGameHook<GameInteractor::OnItemReceive>([&](GetItemEntry itemEntry) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnItemReceive";
payload["hook"]["tableId"] = itemEntry.tableId;
payload["hook"]["getItemId"] = itemEntry.getItemId;
COND_HOOK(OnItemReceive, isConnected, [&](GetItemEntry itemEntry) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnItemReceive";
payload["hook"]["tableId"] = itemEntry.tableId;
payload["hook"]["getItemId"] = itemEntry.getItemId;
SendJsonToRemote(payload);
});
onEnemyDefeatHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnEnemyDefeat>([&](void* refActor) {
SendJsonToRemote(payload);
});
COND_HOOK(OnEnemyDefeat, isConnected, [&](void* refActor) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
@@ -438,7 +400,8 @@ void Sail::RegisterHooks() {
SendJsonToRemote(payload);
});
onActorInitHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnActorInit>([&](void* refActor) {
COND_HOOK(OnActorInit, isConnected, [&](void* refActor) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
@@ -452,64 +415,58 @@ void Sail::RegisterHooks() {
SendJsonToRemote(payload);
});
onFlagSetHook =
GameInteractor::Instance->RegisterGameHook<GameInteractor::OnFlagSet>([&](int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnFlagSet";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
COND_HOOK(OnFlagSet, isConnected, [&](int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnFlagSet";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
SendJsonToRemote(payload);
});
onFlagUnsetHook =
GameInteractor::Instance->RegisterGameHook<GameInteractor::OnFlagUnset>([&](int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
SendJsonToRemote(payload);
});
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnFlagUnset";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
COND_HOOK(OnFlagUnset, isConnected, [&](int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnFlagUnset";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
SendJsonToRemote(payload);
});
onSceneFlagSetHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnSceneFlagSet>(
[&](int16_t sceneNum, int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
SendJsonToRemote(payload);
});
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnSceneFlagSet";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
payload["hook"]["sceneNum"] = sceneNum;
COND_HOOK(OnSceneFlagSet, isConnected, [&](int16_t sceneNum, int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnSceneFlagSet";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
payload["hook"]["sceneNum"] = sceneNum;
SendJsonToRemote(payload);
});
onSceneFlagUnsetHook = GameInteractor::Instance->RegisterGameHook<GameInteractor::OnSceneFlagUnset>(
[&](int16_t sceneNum, int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
SendJsonToRemote(payload);
});
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnSceneFlagUnset";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
payload["hook"]["sceneNum"] = sceneNum;
COND_HOOK(OnSceneFlagUnset, isConnected, [&](int16_t sceneNum, int16_t flagType, int16_t flag) {
if (!isConnected || !GameInteractor::IsSaveLoaded())
return;
nlohmann::json payload;
payload["id"] = std::rand();
payload["type"] = "hook";
payload["hook"]["type"] = "OnSceneFlagUnset";
payload["hook"]["flagType"] = flagType;
payload["hook"]["flag"] = flag;
payload["hook"]["sceneNum"] = sceneNum;
SendJsonToRemote(payload);
});
SendJsonToRemote(payload);
});
}
#endif // ENABLE_REMOTE_CONTROL

View File

@@ -1,4 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#ifndef NETWORK_SAIL_H
#define NETWORK_SAIL_H
#ifdef __cplusplus
@@ -22,4 +21,3 @@ class Sail : public Network {
#endif // __cplusplus
#endif // NETWORK_SAIL_H
#endif // ENABLE_REMOTE_CONTROL

View File

@@ -75,14 +75,8 @@
#include "soh/SohGui/ImGuiUtils.h"
#include "ActorDB.h"
#include "SaveManager.h"
#ifdef ENABLE_REMOTE_CONTROL
#include "soh/Network/CrowdControl/CrowdControl.h"
#include "soh/Network/Sail/Sail.h"
CrowdControl* CrowdControl::Instance;
Sail* Sail::Instance;
#endif
#include "Enhancements/mods.h"
#include "Enhancements/game-interactor/GameInteractor.h"
#include "Enhancements/randomizer/draw.h"
@@ -146,6 +140,8 @@ ItemTableManager* ItemTableManager::Instance;
GameInteractor* GameInteractor::Instance;
AudioCollection* AudioCollection::Instance;
SpeechSynthesizer* SpeechSynthesizer::Instance;
CrowdControl* CrowdControl::Instance;
Sail* Sail::Instance;
extern "C" char** cameraStrings;
std::vector<std::shared_ptr<std::string>> cameraStdStrings;
@@ -1291,10 +1287,8 @@ extern "C" void InitOTR(int argc, char* argv[]) {
#endif
SpeechSynthesizer::Instance->Init();
#ifdef ENABLE_REMOTE_CONTROL
CrowdControl::Instance = new CrowdControl();
Sail::Instance = new Sail();
#endif
OTRMessage_Init();
OTRAudio_Init();
@@ -1324,13 +1318,13 @@ extern "C" void InitOTR(int argc, char* argv[]) {
srand(now);
#ifdef ENABLE_REMOTE_CONTROL
SDLNet_Init();
#endif
if (CVarGetInteger(CVAR_REMOTE_CROWD_CONTROL("Enabled"), 0)) {
CrowdControl::Instance->Enable();
}
if (CVarGetInteger(CVAR_REMOTE_SAIL("Enabled"), 0)) {
Sail::Instance->Enable();
}
#endif
}
extern "C" void SaveManager_ThreadPoolWait() {
@@ -1340,13 +1334,13 @@ extern "C" void SaveManager_ThreadPoolWait() {
extern "C" void DeinitOTR() {
SaveManager_ThreadPoolWait();
OTRAudio_Exit();
#ifdef ENABLE_REMOTE_CONTROL
if (CVarGetInteger(CVAR_REMOTE_CROWD_CONTROL("Enabled"), 0)) {
CrowdControl::Instance->Disable();
}
if (CVarGetInteger(CVAR_REMOTE_SAIL("Enabled"), 0)) {
Sail::Instance->Disable();
}
#ifdef ENABLE_REMOTE_CONTROL
SDLNet_Quit();
#endif

View File

@@ -81,27 +81,6 @@ SohMenu::SohMenu(const std::string& consoleVariable, const std::string& name)
: Menu(consoleVariable, name, 0, UIWidgets::Colors::LightBlue) {
}
#ifndef ENABLE_REMOTE_CONTROL
void SohMenu::AddMenuNetwork() {
#ifndef _DEBUG
// in release builds, the tab doesn't even show
return;
#endif
// Add Network Menu
AddMenuEntry("Network", CVAR_SETTING("Menu.NetworkSidebarSection"));
WidgetPath path = { "Network", "Info", SECTION_COLUMN_1 };
AddSidebarEntry("Network", path.sidebarName, 2);
AddWidget(path,
ICON_FA_EXCLAMATION_TRIANGLE " The Network features are unavailable because SoH was compiled without "
"network support (\"ENABLE_REMOTE_CONTROL\" build flag).",
WIDGET_TEXT)
.Options(TextOptions().Color(Colors::Orange));
}
#endif
void SohMenu::InitElement() {
Ship::Menu::InitElement();
AddMenuSettings();

View File

@@ -18,11 +18,8 @@
#include "soh/Enhancements/mods.h"
#include "soh/Notification/Notification.h"
#include "soh/Enhancements/cosmetics/authenticGfxPatches.h"
#ifdef ENABLE_REMOTE_CONTROL
#include "soh/Network/CrowdControl/CrowdControl.h"
#include "soh/Network/Sail/Sail.h"
#endif
#include "soh/Enhancements/audio/AudioEditor.h"
#include "soh/Enhancements/controls/InputViewer.h"
#include "soh/Enhancements/cosmetics/CosmeticsEditor.h"

View File

@@ -1,4 +1,3 @@
#ifdef ENABLE_REMOTE_CONTROL
#include "SohMenu.h"
#include <soh/Notification/Notification.h>
#include <soh/Network/Network.h>
@@ -16,6 +15,18 @@ void SohMenu::AddMenuNetwork() {
// Add Network Menu
AddMenuEntry("Network", CVAR_SETTING("Menu.NetworkSidebarSection"));
#ifndef ENABLE_REMOTE_CONTROL
WidgetPath path = { "Network", "Info", SECTION_COLUMN_1 };
AddSidebarEntry("Network", path.sidebarName, 2);
AddWidget(path,
ICON_FA_EXCLAMATION_TRIANGLE " The Network features are unavailable because SoH was compiled without "
"network support (\"ENABLE_REMOTE_CONTROL\" build flag).",
WIDGET_TEXT)
.Options(TextOptions().Color(Colors::Orange));
return;
#endif
// Sail
WidgetPath path = { "Network", "Sail", SECTION_COLUMN_1 };
AddSidebarEntry("Network", path.sidebarName, 3);
@@ -171,4 +182,3 @@ void SohMenu::AddMenuNetwork() {
}
} // namespace SohGui
#endif