From d009e899c893014d602b425e115b206f25e74bac Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Hamil?= Date: Wed, 11 Feb 2026 15:23:51 +0300 Subject: [PATCH] Address review comments --- rpcs3/Emu/CMakeLists.txt | 1 + rpcs3/Emu/Io/wiimote_config.cpp | 34 +++++++++ rpcs3/Emu/Io/wiimote_config.h | 32 ++++++++ rpcs3/Input/hid_instance.cpp | 42 ++++------- rpcs3/Input/wiimote_handler.cpp | 89 ++++++++--------------- rpcs3/Input/wiimote_handler.h | 2 +- rpcs3/emucore.vcxproj | 2 + rpcs3/emucore.vcxproj.filters | 6 ++ rpcs3/rpcs3qt/wiimote_settings_dialog.cpp | 21 +++--- 9 files changed, 131 insertions(+), 98 deletions(-) create mode 100644 rpcs3/Emu/Io/wiimote_config.cpp create mode 100644 rpcs3/Emu/Io/wiimote_config.h diff --git a/rpcs3/Emu/CMakeLists.txt b/rpcs3/Emu/CMakeLists.txt index 59434a8452..e42fe70cf6 100644 --- a/rpcs3/Emu/CMakeLists.txt +++ b/rpcs3/Emu/CMakeLists.txt @@ -402,6 +402,7 @@ target_sources(rpcs3_emu PRIVATE Io/GHLtar.cpp Io/GunCon3.cpp Io/Infinity.cpp + Io/wiimote_config.cpp Io/interception.cpp Io/KamenRider.cpp Io/KeyboardHandler.cpp diff --git a/rpcs3/Emu/Io/wiimote_config.cpp b/rpcs3/Emu/Io/wiimote_config.cpp new file mode 100644 index 0000000000..9825fa6741 --- /dev/null +++ b/rpcs3/Emu/Io/wiimote_config.cpp @@ -0,0 +1,34 @@ +#include "stdafx.h" +#include "wiimote_config.h" +#include "Utilities/File.h" + +LOG_CHANNEL(wiimote_log, "Wiimote"); + +cfg_wiimote& get_wiimote_config() +{ + static cfg_wiimote instance; + return instance; +} + +cfg_wiimote::cfg_wiimote() + : cfg::node() + , path(fs::get_config_dir(true) + "wiimote.yml") +{ +} + +bool cfg_wiimote::load() +{ + if (fs::file f{path, fs::read}) + { + return from_string(f.to_string()); + } + return false; +} + +void cfg_wiimote::save() const +{ + if (!cfg::node::save(path)) + { + wiimote_log.error("Failed to save wiimote config to '%s'", path); + } +} diff --git a/rpcs3/Emu/Io/wiimote_config.h b/rpcs3/Emu/Io/wiimote_config.h new file mode 100644 index 0000000000..2d3334cdbb --- /dev/null +++ b/rpcs3/Emu/Io/wiimote_config.h @@ -0,0 +1,32 @@ +#pragma once + +#include "Utilities/Config.h" + +struct cfg_wiimote final : cfg::node +{ + cfg_wiimote(); + bool load(); + void save() const; + + struct node_mapping : cfg::node + { + node_mapping(cfg::node* _parent) : cfg::node(_parent, "Mapping") {} + + cfg::uint<0, 0xFFFF> trigger{ this, "Trigger", 0x0400 }; + cfg::uint<0, 0xFFFF> a1{ this, "A1", 0x0800 }; + cfg::uint<0, 0xFFFF> a2{ this, "A2", 0x1000 }; + cfg::uint<0, 0xFFFF> a3{ this, "A3", 0x0001 }; + cfg::uint<0, 0xFFFF> b1{ this, "B1", 0x0200 }; + cfg::uint<0, 0xFFFF> b2{ this, "B2", 0x0100 }; + cfg::uint<0, 0xFFFF> b3{ this, "B3", 0x8000 }; + cfg::uint<0, 0xFFFF> c1{ this, "C1", 0x0010 }; + cfg::uint<0, 0xFFFF> c2{ this, "C2", 0x0002 }; + + cfg::uint<0, 0xFFFF> b1_alt{ this, "B1_Alt", 0x0008 }; + cfg::uint<0, 0xFFFF> b2_alt{ this, "B2_Alt", 0x0004 }; + } mapping{ this }; + + const std::string path; +}; + +cfg_wiimote& get_wiimote_config(); diff --git a/rpcs3/Input/hid_instance.cpp b/rpcs3/Input/hid_instance.cpp index f462db5515..0daa9bcdda 100644 --- a/rpcs3/Input/hid_instance.cpp +++ b/rpcs3/Input/hid_instance.cpp @@ -42,19 +42,11 @@ bool hid_instance::initialize() #if defined(__APPLE__) int error_code = 0; - if (thread_ctrl::is_main()) + Emu.BlockingCallFromMainThread([&error_code]() { error_code = hid_init(); hid_darwin_set_open_exclusive(0); - } - else - { - Emu.BlockingCallFromMainThread([&error_code]() - { - error_code = hid_init(); - hid_darwin_set_open_exclusive(0); - }, false); - } + }, false); #else const int error_code = hid_init(); #endif @@ -72,14 +64,12 @@ hid_device_info* hid_instance::enumerate(u16 vid, u16 pid) { std::lock_guard lock(g_hid_mutex); #if defined(__APPLE__) - if (!thread_ctrl::is_main()) - { - hid_device_info* devs = nullptr; - Emu.BlockingCallFromMainThread([&]() { devs = hid_enumerate(vid, pid); }, false); - return devs; - } -#endif + hid_device_info* devs = nullptr; + Emu.BlockingCallFromMainThread([&]() { devs = hid_enumerate(vid, pid); }, false); + return devs; +#else return hid_enumerate(vid, pid); +#endif } void hid_instance::free_enumeration(hid_device_info* devs) @@ -88,13 +78,10 @@ void hid_instance::free_enumeration(hid_device_info* devs) std::lock_guard lock(g_hid_mutex); #if defined(__APPLE__) - if (!thread_ctrl::is_main()) - { - Emu.BlockingCallFromMainThread([&]() { hid_free_enumeration(devs); }, false); - return; - } -#endif + Emu.BlockingCallFromMainThread([&]() { hid_free_enumeration(devs); }, false); +#else hid_free_enumeration(devs); +#endif } hid_device* hid_instance::open_path(const char* path) @@ -117,11 +104,8 @@ void hid_instance::close(hid_device* dev) std::lock_guard lock(g_hid_mutex); #if defined(__APPLE__) - if (!thread_ctrl::is_main()) - { - Emu.BlockingCallFromMainThread([&]() { hid_close(dev); }, false); - return; - } -#endif + Emu.BlockingCallFromMainThread([&]() { hid_close(dev); }, false); +#else hid_close(dev); +#endif } diff --git a/rpcs3/Input/wiimote_handler.cpp b/rpcs3/Input/wiimote_handler.cpp index 8a6afeaf26..02db99c729 100644 --- a/rpcs3/Input/wiimote_handler.cpp +++ b/rpcs3/Input/wiimote_handler.cpp @@ -2,8 +2,7 @@ #include "wiimote_handler.h" #include "Input/hid_instance.h" #include "Emu/System.h" -#include "Utilities/File.h" -#include "util/yaml.hpp" +#include "Emu/Io/wiimote_config.h" #include "util/logs.hpp" #include #include @@ -208,66 +207,44 @@ bool wiimote_device::update() static wiimote_handler* s_instance = nullptr; -static std::string get_config_path() -{ - return fs::get_config_dir(true) + "wiimote.yml"; -} - void wiimote_handler::load_config() { - const std::string path = get_config_path(); - fs::file f(path, fs::read); - if (!f) return; - - auto [root, error] = yaml_load(f.to_string()); - if (!error.empty()) + auto& cfg = get_wiimote_config(); + if (cfg.load()) { - wiimote_log.error("Failed to load wiimote config: %s", error); - return; + std::unique_lock lock(m_mutex); + m_mapping.trigger = static_cast(cfg.mapping.trigger.get()); + m_mapping.a1 = static_cast(cfg.mapping.a1.get()); + m_mapping.a2 = static_cast(cfg.mapping.a2.get()); + m_mapping.a3 = static_cast(cfg.mapping.a3.get()); + m_mapping.b1 = static_cast(cfg.mapping.b1.get()); + m_mapping.b2 = static_cast(cfg.mapping.b2.get()); + m_mapping.b3 = static_cast(cfg.mapping.b3.get()); + m_mapping.c1 = static_cast(cfg.mapping.c1.get()); + m_mapping.c2 = static_cast(cfg.mapping.c2.get()); + m_mapping.b1_alt = static_cast(cfg.mapping.b1_alt.get()); + m_mapping.b2_alt = static_cast(cfg.mapping.b2_alt.get()); } - - wiimote_guncon_mapping map; - auto parse_btn = [&](const char* key, wiimote_button& btn) - { - if (root[key]) - { - btn = static_cast(root[key].as(static_cast(btn))); - } - }; - - parse_btn("trigger", map.trigger); - parse_btn("a1", map.a1); - parse_btn("a2", map.a2); - parse_btn("a3", map.a3); - parse_btn("b1", map.b1); - parse_btn("b2", map.b2); - parse_btn("b3", map.b3); - parse_btn("c1", map.c1); - parse_btn("c2", map.c2); - - std::unique_lock lock(m_mutex); - m_mapping = map; } void wiimote_handler::save_config() { - YAML::Node root; { std::shared_lock lock(m_mutex); - root["trigger"] = static_cast(m_mapping.trigger); - root["a1"] = static_cast(m_mapping.a1); - root["a2"] = static_cast(m_mapping.a2); - root["a3"] = static_cast(m_mapping.a3); - root["b1"] = static_cast(m_mapping.b1); - root["b2"] = static_cast(m_mapping.b2); - root["b3"] = static_cast(m_mapping.b3); - root["c1"] = static_cast(m_mapping.c1); - root["c2"] = static_cast(m_mapping.c2); + auto& cfg = get_wiimote_config(); + cfg.mapping.trigger.set(static_cast(m_mapping.trigger)); + cfg.mapping.a1.set(static_cast(m_mapping.a1)); + cfg.mapping.a2.set(static_cast(m_mapping.a2)); + cfg.mapping.a3.set(static_cast(m_mapping.a3)); + cfg.mapping.b1.set(static_cast(m_mapping.b1)); + cfg.mapping.b2.set(static_cast(m_mapping.b2)); + cfg.mapping.b3.set(static_cast(m_mapping.b3)); + cfg.mapping.c1.set(static_cast(m_mapping.c1)); + cfg.mapping.c2.set(static_cast(m_mapping.c2)); + cfg.mapping.b1_alt.set(static_cast(m_mapping.b1_alt)); + cfg.mapping.b2_alt.set(static_cast(m_mapping.b2_alt)); } - - YAML::Emitter emitter; - emitter << root; - fs::write_file(get_config_path(), fs::rewrite, emitter.c_str(), emitter.size()); + get_wiimote_config().save(); } wiimote_handler::wiimote_handler() @@ -321,7 +298,7 @@ void wiimote_handler::stop() m_thread.reset(); } -size_t wiimote_handler::get_device_count() +usz wiimote_handler::get_device_count() { std::shared_lock lock(m_mutex); return m_devices.size(); @@ -358,10 +335,8 @@ std::vector wiimote_handler::get_states() void wiimote_handler::thread_proc() { - thread_ctrl::set_name("WiiMoteManager"); - u32 counter = 0; - while (m_running) + while (m_running && thread_ctrl::state() != thread_state::aborting) { // Scan every 2 seconds if (counter++ % 200 == 0) @@ -418,7 +393,7 @@ void wiimote_handler::thread_proc() { // Generic Wiimote: Find first available slot std::shared_lock lock(m_mutex); - for (size_t i = 0; i < m_devices.size(); i++) + for (usz i = 0; i < m_devices.size(); i++) { if (!m_devices[i]->get_state().connected) { @@ -471,6 +446,6 @@ void wiimote_handler::thread_proc() } } - std::this_thread::sleep_for(std::chrono::milliseconds(10)); + thread_ctrl::wait_for(10'000); } } diff --git a/rpcs3/Input/wiimote_handler.h b/rpcs3/Input/wiimote_handler.h index 097450e156..d7dc5d56dd 100644 --- a/rpcs3/Input/wiimote_handler.h +++ b/rpcs3/Input/wiimote_handler.h @@ -100,7 +100,7 @@ public: void stop(); std::vector get_states(); - size_t get_device_count(); + usz get_device_count(); void set_mapping(const wiimote_guncon_mapping& mapping); wiimote_guncon_mapping get_mapping() const; diff --git a/rpcs3/emucore.vcxproj b/rpcs3/emucore.vcxproj index 180af236b2..22f547cc11 100644 --- a/rpcs3/emucore.vcxproj +++ b/rpcs3/emucore.vcxproj @@ -88,6 +88,7 @@ + @@ -602,6 +603,7 @@ + diff --git a/rpcs3/emucore.vcxproj.filters b/rpcs3/emucore.vcxproj.filters index 5ca602fbec..78fbbb5d9b 100644 --- a/rpcs3/emucore.vcxproj.filters +++ b/rpcs3/emucore.vcxproj.filters @@ -957,6 +957,9 @@ Emu\Io + + Emu\Io + Emu\Io @@ -2590,6 +2593,9 @@ Emu\Io + + Emu\Io + Emu\Io diff --git a/rpcs3/rpcs3qt/wiimote_settings_dialog.cpp b/rpcs3/rpcs3qt/wiimote_settings_dialog.cpp index edf82492ef..c2860eb022 100644 --- a/rpcs3/rpcs3qt/wiimote_settings_dialog.cpp +++ b/rpcs3/rpcs3qt/wiimote_settings_dialog.cpp @@ -1,6 +1,5 @@ #include "stdafx.h" #include "wiimote_settings_dialog.h" -#include "Emu/System.h" #include "Input/wiimote_handler.h" #include #include @@ -66,7 +65,7 @@ void wiimote_settings_dialog::populate_mappings() } // Set current selection - int index = boxes[i]->findData(QVariant::fromValue(static_cast(*targets[i]))); + const int index = boxes[i]->findData(QVariant::fromValue(static_cast(*targets[i]))); if (index >= 0) boxes[i]->setCurrentIndex(index); // Connect change signal @@ -162,8 +161,8 @@ void wiimote_settings_dialog::update_state() return; } - auto states = wm->get_states(); - if (static_cast(index) >= states.size()) + const auto states = wm->get_states(); + if (static_cast(index) >= states.size()) { ui->connectionStatus->setText(tr("N/A")); ui->buttonState->setText(tr("N/A")); @@ -215,8 +214,8 @@ void wiimote_settings_dialog::update_state() // Map 0..1023 X and 0..767 Y to pixmap coordinates // Wiimote X/Y are inverted relative to pointing direction - float x = ((1023 - state.ir[i].x) / 1023.0f) * pixmap.width(); - float y = (state.ir[i].y / 767.0f) * pixmap.height(); + const float x = ((1023 - state.ir[i].x) / 1023.0f) * pixmap.width(); + const float y = (state.ir[i].y / 767.0f) * pixmap.height(); painter.setPen(colors[i]); painter.setBrush(colors[i]); @@ -241,15 +240,15 @@ void wiimote_settings_dialog::update_list() return; } - auto states = wm->get_states(); + const auto states = wm->get_states(); // Only update if the list content actually changed (avoid flicker) - if (static_cast(ui->wiimoteList->count()) != states.size()) + if (static_cast(ui->wiimoteList->count()) != states.size()) { - int current_row = ui->wiimoteList->currentRow(); + const int current_row = ui->wiimoteList->currentRow(); ui->wiimoteList->clear(); - for (size_t i = 0; i < states.size(); i++) + for (usz i = 0; i < states.size(); i++) { QString label = tr("Wiimote #%1").arg(i + 1); if (!states[i].connected) label += " (" + tr("Disconnected") + ")"; @@ -268,7 +267,7 @@ void wiimote_settings_dialog::update_list() else { // Just update connection status labels without clearing - for (size_t i = 0; i < states.size(); i++) + for (usz i = 0; i < states.size(); i++) { QString label = tr("Wiimote #%1").arg(i + 1); if (!states[i].connected) label += " (" + tr("Disconnected") + ")";