Skip to content

Commit

Permalink
Remove slimsig lig, replace SDL event handling with a simple loop, fi…
Browse files Browse the repository at this point in the history
…x RML input handlers piling up on game reloads (#1719)

* Remove slimsig lig, replace SDL event handling with a simple loop, fix RML input handlers piling up on game reloads
* Update aGui to not use slimsig
  • Loading branch information
lhog authored Oct 12, 2024
1 parent f6ac43d commit 8c72f5d
Show file tree
Hide file tree
Showing 31 changed files with 122 additions and 1,519 deletions.
48 changes: 24 additions & 24 deletions rts/Menu/SelectMenu.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,26 +57,26 @@ class ConnectWindow : public agui::Window {
HorizontalLayout* input = new HorizontalLayout(wndLayout);
/*agui::TextElement* label = */new agui::TextElement("Address:", input); // will be deleted in input
address = new agui::LineEdit(input);
address->DefaultAction.connect(std::bind(&ConnectWindow::Finish, this, true));
address->DefaultAction = std::bind(&ConnectWindow::Finish, this, true);
address->SetFocus(true);
address->SetContent(configHandler->GetString("address"));
HorizontalLayout* buttons = new HorizontalLayout(wndLayout);
Button* connect = new Button("Connect", buttons);
connect->Clicked.connect(std::bind(&ConnectWindow::Finish, this, true));
connect->Clicked = std::bind(&ConnectWindow::Finish, this, true);
Button* close = new Button("Close", buttons);
close->Clicked.connect(std::bind(&ConnectWindow::Finish, this, false));
close->Clicked = std::bind(&ConnectWindow::Finish, this, false);
GeometryChange();
}

slimsig::signal<void (std::string)> Connect;
OnClickStringType Connect;
agui::LineEdit* address;

private:
void Finish(bool connect) {
if (connect)
Connect.emit(address->GetContent());
Connect(address->GetContent());
else
WantClose.emit();
WantClose();
};
};

Expand All @@ -91,27 +91,27 @@ class SettingsWindow : public agui::Window {
HorizontalLayout* input = new HorizontalLayout(wndLayout);
/*agui::TextElement* value_label = */new agui::TextElement("Value:", input); // will be deleted in input
value = new agui::LineEdit(input);
value->DefaultAction.connect(std::bind(&SettingsWindow::Finish, this, true));
value->DefaultAction = std::bind(&SettingsWindow::Finish, this, true);
value->SetFocus(true);
if (configHandler->IsSet(name))
value->SetContent(configHandler->GetString(name));
HorizontalLayout* buttons = new HorizontalLayout(wndLayout);
Button* ok = new Button("OK", buttons);
ok->Clicked.connect(std::bind(&SettingsWindow::Finish, this, true));
ok->Clicked = std::bind(&SettingsWindow::Finish, this, true);
Button* close = new Button("Cancel", buttons);
close->Clicked.connect(std::bind(&SettingsWindow::Finish, this, false));
close->Clicked = std::bind(&SettingsWindow::Finish, this, false);
GeometryChange();
}

slimsig::signal<void (std::string)> OK;
OnClickStringType OK;
agui::LineEdit* value;

private:
void Finish(bool set) {
if (set)
OK.emit(title + " = " + value->GetContent());
OK(title + " = " + value->GetContent());
else
WantClose.emit();
WantClose();
};
};

Expand Down Expand Up @@ -152,23 +152,23 @@ SelectMenu::SelectMenu(std::shared_ptr<ClientSetup> setup)
menu->SetBorder(1.2f);
/*agui::TextElement* title = */new agui::TextElement("Spring " + SpringVersion::GetFull(), menu); // will be deleted in menu
Button* testGame = new Button("Test Game", menu);
testGame->Clicked.connect(std::bind(&SelectMenu::Single, this));
testGame->Clicked = std::bind(&SelectMenu::Single, this);

Button* playDemo = new Button("Play Demo", menu);
playDemo->Clicked.connect(std::bind(&SelectMenu::Demo, this));
playDemo->Clicked = std::bind(&SelectMenu::Demo, this);

Button* loadGame = new Button("Load Game", menu);
loadGame->Clicked.connect(std::bind(&SelectMenu::Load, this));
loadGame->Clicked = std::bind(&SelectMenu::Load, this);

userSetting = configHandler->GetString("LastSelectedSetting");
Button* editsettings = new Button("Edit Settings", menu);
editsettings->Clicked.connect(std::bind(&SelectMenu::ShowSettingsList, this));
editsettings->Clicked = std::bind(&SelectMenu::ShowSettingsList, this);

Button* directConnect = new Button("Direct Connect", menu);
directConnect->Clicked.connect(std::bind(&SelectMenu::ShowConnectWindow, this, true));
directConnect->Clicked = std::bind(&SelectMenu::ShowConnectWindow, this, true);

Button* quit = new Button("Quit", menu);
quit->Clicked.connect(std::bind(&SelectMenu::Quit, this));
quit->Clicked = std::bind(&SelectMenu::Quit, this);
background->GeometryChange();
}

Expand Down Expand Up @@ -273,8 +273,8 @@ void SelectMenu::ShowConnectWindow(bool show)
if (show && !conWindow)
{
conWindow = new ConnectWindow();
conWindow->Connect.connect(std::bind(&SelectMenu::DirectConnect, this, std::placeholders::_1));
conWindow->WantClose.connect(std::bind(&SelectMenu::ShowConnectWindow, this, false));
conWindow->Connect = (std::bind(&SelectMenu::DirectConnect, this, std::placeholders::_1));
conWindow->WantClose = std::bind(&SelectMenu::ShowConnectWindow, this, false);
}
else if (!show && conWindow)
{
Expand All @@ -291,8 +291,8 @@ void SelectMenu::ShowSettingsWindow(bool show, std::string name)
settingsWindow = nullptr;
}
settingsWindow = new SettingsWindow(name);
settingsWindow->OK.connect(std::bind(&SelectMenu::ShowSettingsWindow, this, false, std::placeholders::_1));
settingsWindow->WantClose.connect(std::bind(&SelectMenu::ShowSettingsWindow, this, false, ""));
settingsWindow->OK = std::bind(&SelectMenu::ShowSettingsWindow, this, false, std::placeholders::_1);
settingsWindow->WantClose = std::bind(&SelectMenu::ShowSettingsWindow, this, false, "");
}
else if (!show && settingsWindow) {
agui::gui->RmElement(settingsWindow);
Expand All @@ -311,8 +311,8 @@ void SelectMenu::ShowSettingsList()
{
if (curSelect == nullptr) {
curSelect = new ListSelectWnd("Select setting");
curSelect->Selected.connect(std::bind(&SelectMenu::SelectSetting, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectMenu::CleanWindow, this));
curSelect->Selected = std::bind(&SelectMenu::SelectSetting, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectMenu::CleanWindow, this);
}
curSelect->list->RemoveAllItems();

Expand Down
26 changes: 13 additions & 13 deletions rts/Menu/SelectionWidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ SelectionWidget::SelectionWidget(agui::GuiElement* parent) : agui::GuiElement(pa

agui::HorizontalLayout* modL = new agui::HorizontalLayout(vl);
mod = new agui::Button("Select", modL);
mod->Clicked.connect(std::bind(&SelectionWidget::ShowModList, this));
mod->Clicked = std::bind(&SelectionWidget::ShowModList, this);
mod->SetSize(0.1f, 0.00f, true);

userDemo = NoDemoSelect;
Expand All @@ -70,12 +70,12 @@ SelectionWidget::SelectionWidget(agui::GuiElement* parent) : agui::GuiElement(pa

agui::HorizontalLayout* mapL = new agui::HorizontalLayout(vl);
map = new agui::Button("Select", mapL);
map->Clicked.connect(std::bind(&SelectionWidget::ShowMapList, this));
map->Clicked = std::bind(&SelectionWidget::ShowMapList, this);
map->SetSize(0.1f, 0.00f, true);

agui::HorizontalLayout* scriptL = new agui::HorizontalLayout(vl);
script = new agui::Button("Select", scriptL);
script->Clicked.connect(std::bind(&SelectionWidget::ShowScriptList, this));
script->Clicked = std::bind(&SelectionWidget::ShowScriptList, this);
script->SetSize(0.1f, 0.00f, true);

modT = new agui::TextElement(userMod, modL);
Expand All @@ -97,8 +97,8 @@ void SelectionWidget::ShowDemoList(const std::function<void(const std::string&)>
return;

curSelect = new ListSelectWnd("Select demo");
curSelect->Selected.connect(std::bind(&SelectionWidget::SelectDemo, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectionWidget::CleanWindow, this));
curSelect->Selected = std::bind(&SelectionWidget::SelectDemo, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectionWidget::CleanWindow, this);

const std::string cwd = FileSystem::EnsurePathSepAtEnd(FileSystemAbstraction::GetCwd());
const std::string dir = FileSystem::EnsurePathSepAtEnd("demos");
Expand All @@ -117,8 +117,8 @@ void SelectionWidget::ShowSavegameList(const std::function<void(const std::strin
return;

curSelect = new ListSelectWnd("Select savegame");
curSelect->Selected.connect(std::bind(&SelectionWidget::SelectSavegame, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectionWidget::CleanWindow, this));
curSelect->Selected = std::bind(&SelectionWidget::SelectSavegame, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectionWidget::CleanWindow, this);

const std::string cwd = FileSystem::EnsurePathSepAtEnd(FileSystemAbstraction::GetCwd());
const std::string dir = FileSystem::EnsurePathSepAtEnd("Saves");
Expand Down Expand Up @@ -151,8 +151,8 @@ void SelectionWidget::ShowModList()
return;

curSelect = new ListSelectWnd("Select game");
curSelect->Selected.connect(std::bind(&SelectionWidget::SelectMod, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectionWidget::CleanWindow, this));
curSelect->Selected = std::bind(&SelectionWidget::SelectMod, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectionWidget::CleanWindow, this);

std::vector<CArchiveScanner::ArchiveData> found = archiveScanner->GetPrimaryMods();
std::sort(found.begin(), found.end(), [](const CArchiveScanner::ArchiveData& a, const CArchiveScanner::ArchiveData& b) {
Expand All @@ -172,8 +172,8 @@ void SelectionWidget::ShowMapList()
return;

curSelect = new ListSelectWnd("Select map");
curSelect->Selected.connect(std::bind(&SelectionWidget::SelectMap, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectionWidget::CleanWindow, this));
curSelect->Selected = std::bind(&SelectionWidget::SelectMap, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectionWidget::CleanWindow, this);

std::vector<std::string> arFound = archiveScanner->GetMaps();
std::sort(arFound.begin(), arFound.end(), doj::alphanum_less<std::string>());
Expand Down Expand Up @@ -243,8 +243,8 @@ void SelectionWidget::ShowScriptList()
return;

curSelect = new ListSelectWnd("Select script");
curSelect->Selected.connect(std::bind(&SelectionWidget::SelectScript, this, std::placeholders::_1));
curSelect->WantClose.connect(std::bind(&SelectionWidget::CleanWindow, this));
curSelect->Selected = std::bind(&SelectionWidget::SelectScript, this, std::placeholders::_1);
curSelect->WantClose = std::bind(&SelectionWidget::CleanWindow, this);

for (const std::string& scriptName: availableScripts) {
curSelect->list->AddItem(scriptName, "");
Expand Down
12 changes: 6 additions & 6 deletions rts/Menu/SelectionWidget.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,28 +34,28 @@ class ListSelectWnd : public agui::Window

agui::VerticalLayout* modWindowLayout = new agui::VerticalLayout(this);
list = new agui::List(modWindowLayout);
list->FinishSelection.connect(std::bind(&ListSelectWnd::SelectButton, this));
list->FinishSelection = std::bind(&ListSelectWnd::SelectButton, this);
agui::HorizontalLayout* buttons = new agui::HorizontalLayout(modWindowLayout);
buttons->SetSize(0.0f, 0.04f, true);
agui::Button* select = new agui::Button("Select", buttons);
select->Clicked.connect(std::bind(&ListSelectWnd::SelectButton, this));
select->Clicked = std::bind(&ListSelectWnd::SelectButton, this);
agui::Button* cancel = new agui::Button("Close", buttons);
cancel->Clicked.connect(std::bind(&ListSelectWnd::CancelButton, this));
cancel->Clicked = std::bind(&ListSelectWnd::CancelButton, this);
GeometryChange();
}

slimsig::signal<void (std::string)> Selected;
OnClickStringType Selected;
agui::List* list;

private:
void SelectButton()
{
list->SetFocus(false);
Selected.emit(list->GetCurrentItem());
Selected(list->GetCurrentItem());
}
void CancelButton()
{
WantClose.emit();
WantClose();
}
};

Expand Down
2 changes: 1 addition & 1 deletion rts/Rml/Backends/RmlUi_Backend.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ class BackendState : public Rml::Plugin {
Rml::Context* debug_host_context = nullptr;
Rml::Context* clicked_context = nullptr;

InputHandler::SignalType::connection_type inputCon;
InputHandler::HandlerTokenT inputCon;
CRmlInputReceiver inputReceiver;

bool initialized = false;
Expand Down
21 changes: 17 additions & 4 deletions rts/System/Input/InputHandler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,12 @@ InputHandler::InputHandler() = default;

void InputHandler::PushEvent(const SDL_Event& ev)
{
sig.emit(ev);
for (const auto& eventHandler : eventHandlers) {
if (eventHandler) {
if (eventHandler(ev))
break;
}
}
}

void InputHandler::PushEvents()
Expand All @@ -25,8 +30,16 @@ void InputHandler::PushEvents()
}
}


InputHandler::SignalType::connection_type InputHandler::AddHandler(SignalType::callback handler)
InputHandler::HandlerTokenT InputHandler::AddHandler(InputHandler::HandlerFuncT func)
{
return sig.connect(handler);
for (size_t i = 0; i < eventHandlers.size(); ++i) {
if (eventHandlers[i] == nullptr) {
eventHandlers[i] = func;
return InputHandler::HandlerTokenT{ *this, i};
}
}
eventHandlers.emplace_back(func);
return InputHandler::HandlerTokenT{ *this, eventHandlers.size() - 1 };
}


42 changes: 37 additions & 5 deletions rts/System/Input/InputHandler.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@
#ifndef INPUT_HANDLER_H
#define INPUT_HANDLER_H

#include <slimsig/slimsig.h>
#include <vector>
#include <functional>
#include <SDL_events.h>

/**
Expand All @@ -13,17 +14,48 @@
class InputHandler
{
public:
typedef slimsig::signal<void (const SDL_Event&)> SignalType;
class HandlerTokenT {
public:
friend class InputHandler;
constexpr HandlerTokenT()
: ih(nullptr)
, pos(0)
{}
HandlerTokenT(InputHandler& ih_, size_t pos_)
: ih(&ih_)
, pos(pos_)
{}
HandlerTokenT(const HandlerTokenT&) = delete;
HandlerTokenT(HandlerTokenT&& other) noexcept { *this = std::move(other); }
~HandlerTokenT()
{
if (ih) {
ih->eventHandlers[pos] = nullptr;
}
}

HandlerTokenT& operator=(const HandlerTokenT&) = delete;
HandlerTokenT& operator=(HandlerTokenT&& other) noexcept {
std::swap(ih, other.ih);
std::swap(pos, other.pos);

return *this;
}
private:
InputHandler* ih;
size_t pos;
};
public:
using HandlerFuncT = std::function<bool(const SDL_Event&)>;

InputHandler();

void PushEvent(const SDL_Event& ev);
void PushEvents();

SignalType::connection_type AddHandler(SignalType::callback);

HandlerTokenT AddHandler(HandlerFuncT func);
private:
SignalType sig;
std::vector<HandlerFuncT> eventHandlers;
};

extern InputHandler input;
Expand Down
6 changes: 1 addition & 5 deletions rts/System/Input/MouseInput.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -27,19 +27,16 @@
#include "System/MainDefines.h"
#include "System/SafeUtil.h"

#include <functional>

#include <SDL_events.h>
#include <SDL_hints.h>
#include <SDL_syswm.h>


IMouseInput* mouseInput = nullptr;


IMouseInput::IMouseInput(bool relModeWarp)
{
inputCon = input.AddHandler(std::bind(&IMouseInput::HandleSDLMouseEvent, this, std::placeholders::_1));
inputCon = input.AddHandler([this](const SDL_Event& event) { return this->HandleSDLMouseEvent(event); });
#ifndef HEADLESS
// Windows 10 FCU (Fall Creators Update) causes spurious SDL_MOUSEMOTION
// events to be generated with SDL_HINT_MOUSE_RELATIVE_MODE_WARP enabled
Expand All @@ -62,7 +59,6 @@ IMouseInput::~IMouseInput()
#ifndef HEADLESS
SDL_SetHint(SDL_HINT_MOUSE_RELATIVE_MODE_WARP, "0");
#endif
inputCon.disconnect();
}


Expand Down
3 changes: 1 addition & 2 deletions rts/System/Input/MouseInput.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
#define MOUSE_INPUT_H

#include <SDL_events.h>
#include <slimsig/connection.h>
#include "System/Input/InputHandler.h"

#include "System/type2.h"
Expand Down Expand Up @@ -33,7 +32,7 @@ class IMouseInput

protected:
int2 mousepos;
InputHandler::SignalType::connection_type inputCon;
InputHandler::HandlerTokenT inputCon;
};

extern IMouseInput* mouseInput;
Expand Down
Loading

0 comments on commit 8c72f5d

Please sign in to comment.