From dbe1ad4fe47e9adc96a73d7c676b37cb17c97dcf Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 12:36:28 -0400 Subject: GC Adapter Implementation --- src/input_common/main.cpp | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index 95e351e241..be13129afb 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -4,8 +4,11 @@ #include #include +#include +#include #include "common/param_package.h" #include "input_common/analog_from_button.h" +#include "input_common/gcadapter/gc_poller.h" #include "input_common/keyboard.h" #include "input_common/main.h" #include "input_common/motion_emu.h" @@ -22,8 +25,15 @@ static std::shared_ptr motion_emu; static std::unique_ptr sdl; #endif static std::unique_ptr udp; +static std::shared_ptr gcbuttons; +static std::shared_ptr gcanalog; void Init() { + gcbuttons = std::make_shared(); + Input::RegisterFactory("gcpad", gcbuttons); + gcanalog = std::make_shared(); + Input::RegisterFactory("gcpad", gcanalog); + keyboard = std::make_shared(); Input::RegisterFactory("keyboard", keyboard); Input::RegisterFactory("analog_from_button", @@ -34,8 +44,10 @@ void Init() { #ifdef HAVE_SDL2 sdl = SDL::Init(); #endif + /* udp = CemuhookUDP::Init(); + */ } void Shutdown() { @@ -48,6 +60,8 @@ void Shutdown() { sdl.reset(); #endif udp.reset(); + Input::UnregisterFactory("gcpad"); + gcbuttons.reset(); } Keyboard* GetKeyboard() { @@ -58,6 +72,14 @@ MotionEmu* GetMotionEmu() { return motion_emu.get(); } +GCButtonFactory* GetGCButtons() { + return gcbuttons.get(); +} + +GCAnalogFactory* GetGCAnalogs() { + return gcanalog.get(); +} + std::string GenerateKeyboardParam(int key_code) { Common::ParamPackage param{ {"engine", "keyboard"}, @@ -88,7 +110,6 @@ std::vector> GetPollers(DeviceType type) { #ifdef HAVE_SDL2 pollers = sdl->GetPollers(type); #endif - return pollers; } -- cgit v1.2.3 From 243dbee81e2776f6f211f673917ec1dc6879fe00 Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 13:02:43 -0400 Subject: Cleanup after linter --- src/input_common/analog_from_button.cpp | 3 +- src/input_common/keyboard.cpp | 9 +- src/input_common/main.cpp | 4 - src/input_common/motion_emu.cpp | 5 +- src/input_common/sdl/sdl_impl.cpp | 52 ++++-------- src/input_common/udp/client.cpp | 140 ++++++++++++++------------------ src/input_common/udp/client.h | 2 - src/input_common/udp/protocol.h | 32 ++------ src/input_common/udp/udp.cpp | 18 +--- 9 files changed, 98 insertions(+), 167 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/analog_from_button.cpp b/src/input_common/analog_from_button.cpp index 8116fcf9fc..6cabdaa3ce 100755 --- a/src/input_common/analog_from_button.cpp +++ b/src/input_common/analog_from_button.cpp @@ -14,8 +14,7 @@ public: float modifier_scale_) : up(std::move(up_)), down(std::move(down_)), left(std::move(left_)), right(std::move(right_)), modifier(std::move(modifier_)), - modifier_scale(modifier_scale_) { - } + modifier_scale(modifier_scale_) {} std::tuple GetStatus() const override { constexpr float SQRT_HALF = 0.707106781f; diff --git a/src/input_common/keyboard.cpp b/src/input_common/keyboard.cpp index d76791860c..9138a75630 100644 --- a/src/input_common/keyboard.cpp +++ b/src/input_common/keyboard.cpp @@ -13,8 +13,7 @@ namespace InputCommon { class KeyButton final : public Input::ButtonDevice { public: explicit KeyButton(std::shared_ptr key_button_list_) - : key_button_list(std::move(key_button_list_)) { - } + : key_button_list(std::move(key_button_list_)) {} ~KeyButton() override; @@ -69,9 +68,7 @@ private: std::list list; }; -Keyboard::Keyboard() - : key_button_list{std::make_shared()} { -} +Keyboard::Keyboard() : key_button_list{std::make_shared()} {} KeyButton::~KeyButton() { key_button_list->RemoveKeyButton(this); @@ -81,7 +78,7 @@ std::unique_ptr Keyboard::Create(const Common::ParamPackage int key_code = params.Get("code", 0); std::unique_ptr button = std::make_unique(key_button_list); key_button_list->AddKeyButton(key_code, button.get()); - return std::move(button); + return button; } void Keyboard::PressKey(int key_code) { diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index be13129afb..7fc0e2db4c 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -5,7 +5,6 @@ #include #include #include -#include #include "common/param_package.h" #include "input_common/analog_from_button.h" #include "input_common/gcadapter/gc_poller.h" @@ -44,10 +43,7 @@ void Init() { #ifdef HAVE_SDL2 sdl = SDL::Init(); #endif - /* - udp = CemuhookUDP::Init(); - */ } void Shutdown() { diff --git a/src/input_common/motion_emu.cpp b/src/input_common/motion_emu.cpp index b7120311aa..d4cdf76a3f 100644 --- a/src/input_common/motion_emu.cpp +++ b/src/input_common/motion_emu.cpp @@ -22,8 +22,7 @@ public: : update_millisecond(update_millisecond), update_duration(std::chrono::duration_cast( std::chrono::milliseconds(update_millisecond))), - sensitivity(sensitivity), motion_emu_thread(&MotionEmuDevice::MotionEmuThread, this) { - } + sensitivity(sensitivity), motion_emu_thread(&MotionEmuDevice::MotionEmuThread, this) {} ~MotionEmuDevice() { if (motion_emu_thread.joinable()) { @@ -146,7 +145,7 @@ std::unique_ptr MotionEmu::Create(const Common::ParamPackag // Previously created device is disconnected here. Having two motion devices for 3DS is not // expected. current_device = device_wrapper->device; - return std::move(device_wrapper); + return device_wrapper; } void MotionEmu::BeginTilt(int x, int y) { diff --git a/src/input_common/sdl/sdl_impl.cpp b/src/input_common/sdl/sdl_impl.cpp index 3c1820c4ae..6b264f2a6f 100644 --- a/src/input_common/sdl/sdl_impl.cpp +++ b/src/input_common/sdl/sdl_impl.cpp @@ -49,8 +49,7 @@ static int SDLEventWatcher(void* user_data, SDL_Event* event) { class SDLJoystick { public: SDLJoystick(std::string guid_, int port_, SDL_Joystick* joystick) - : guid{std::move(guid_)}, port{port_}, sdl_joystick{joystick, &SDL_JoystickClose} { - } + : guid{std::move(guid_)}, port{port_}, sdl_joystick{joystick, &SDL_JoystickClose} {} void SetButton(int button, bool value) { std::lock_guard lock{mutex}; @@ -98,7 +97,6 @@ public: std::lock_guard lock{mutex}; return (state.hats.at(hat) & direction) != 0; } - /** * The guid of the joystick */ @@ -127,7 +125,6 @@ private: std::unordered_map axes; std::unordered_map hats; } state; - std::string guid; int port; std::unique_ptr sdl_joystick; @@ -158,8 +155,7 @@ std::shared_ptr SDLState::GetSDLJoystickBySDLID(SDL_JoystickID sdl_ if (map_it != joystick_map.end()) { const auto vec_it = std::find_if(map_it->second.begin(), map_it->second.end(), - [&sdl_joystick](const std::shared_ptr& joystick) - { + [&sdl_joystick](const std::shared_ptr& joystick) { return sdl_joystick == joystick->GetSDLJoystick(); }); if (vec_it != map_it->second.end()) { @@ -170,8 +166,7 @@ std::shared_ptr SDLState::GetSDLJoystickBySDLID(SDL_JoystickID sdl_ // Search for a SDLJoystick without a mapped SDL_Joystick... const auto nullptr_it = std::find_if(map_it->second.begin(), map_it->second.end(), - [](const std::shared_ptr& joystick) - { + [](const std::shared_ptr& joystick) { return !joystick->GetSDLJoystick(); }); if (nullptr_it != map_it->second.end()) { @@ -228,8 +223,7 @@ void SDLState::CloseJoystick(SDL_Joystick* sdl_joystick) { const auto& joystick_guid_list = joystick_map[guid]; const auto joystick_it = std::find_if(joystick_guid_list.begin(), joystick_guid_list.end(), - [&sdl_joystick](const std::shared_ptr& joystick) - { + [&sdl_joystick](const std::shared_ptr& joystick) { return joystick->GetSDLJoystick() == sdl_joystick; }); joystick = *joystick_it; @@ -285,8 +279,7 @@ void SDLState::CloseJoysticks() { class SDLButton final : public Input::ButtonDevice { public: explicit SDLButton(std::shared_ptr joystick_, int button_) - : joystick(std::move(joystick_)), button(button_) { - } + : joystick(std::move(joystick_)), button(button_) {} bool GetStatus() const override { return joystick->GetButton(button); @@ -300,8 +293,7 @@ private: class SDLDirectionButton final : public Input::ButtonDevice { public: explicit SDLDirectionButton(std::shared_ptr joystick_, int hat_, Uint8 direction_) - : joystick(std::move(joystick_)), hat(hat_), direction(direction_) { - } + : joystick(std::move(joystick_)), hat(hat_), direction(direction_) {} bool GetStatus() const override { return joystick->GetHatDirection(hat, direction); @@ -318,8 +310,7 @@ public: explicit SDLAxisButton(std::shared_ptr joystick_, int axis_, float threshold_, bool trigger_if_greater_) : joystick(std::move(joystick_)), axis(axis_), threshold(threshold_), - trigger_if_greater(trigger_if_greater_) { - } + trigger_if_greater(trigger_if_greater_) {} bool GetStatus() const override { const float axis_value = joystick->GetAxis(axis); @@ -339,8 +330,7 @@ private: class SDLAnalog final : public Input::AnalogDevice { public: SDLAnalog(std::shared_ptr joystick_, int axis_x_, int axis_y_, float deadzone_) - : joystick(std::move(joystick_)), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_) { - } + : joystick(std::move(joystick_)), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_) {} std::tuple GetStatus() const override { const auto [x, y] = joystick->GetAnalog(axis_x, axis_y); @@ -378,9 +368,7 @@ private: /// A button device factory that creates button devices from SDL joystick class SDLButtonFactory final : public Input::Factory { public: - explicit SDLButtonFactory(SDLState& state_) - : state(state_) { - } + explicit SDLButtonFactory(SDLState& state_) : state(state_) {} /** * Creates a button device from a joystick button @@ -455,9 +443,7 @@ private: /// An analog device factory that creates analog devices from SDL joystick class SDLAnalogFactory final : public Input::Factory { public: - explicit SDLAnalogFactory(SDLState& state_) - : state(state_) { - } + explicit SDLAnalogFactory(SDLState& state_) : state(state_) {} /** * Creates analog device from joystick axes @@ -505,8 +491,7 @@ SDLState::SDLState() { initialized = true; if (start_thread) { - poll_thread = std::thread([this] - { + poll_thread = std::thread([this] { using namespace std::chrono_literals; while (initialized) { SDL_PumpEvents(); @@ -592,9 +577,7 @@ namespace Polling { class SDLPoller : public InputCommon::Polling::DevicePoller { public: - explicit SDLPoller(SDLState& state_) - : state(state_) { - } + explicit SDLPoller(SDLState& state_) : state(state_) {} void Start() override { state.event_queue.Clear(); @@ -611,9 +594,7 @@ protected: class SDLButtonPoller final : public SDLPoller { public: - explicit SDLButtonPoller(SDLState& state_) - : SDLPoller(state_) { - } + explicit SDLButtonPoller(SDLState& state_) : SDLPoller(state_) {} Common::ParamPackage GetNextInput() override { SDL_Event event; @@ -622,7 +603,8 @@ public: case SDL_JOYAXISMOTION: if (std::abs(event.jaxis.value / 32767.0) < 0.5) { break; - }[[fallthrough]]; + } + [[fallthrough]]; case SDL_JOYBUTTONUP: case SDL_JOYHATMOTION: return SDLEventToButtonParamPackage(state, event); @@ -634,9 +616,7 @@ public: class SDLAnalogPoller final : public SDLPoller { public: - explicit SDLAnalogPoller(SDLState& state_) - : SDLPoller(state_) { - } + explicit SDLAnalogPoller(SDLState& state_) : SDLPoller(state_) {} void Start() override { SDLPoller::Start(); diff --git a/src/input_common/udp/client.cpp b/src/input_common/udp/client.cpp index befa4c86d7..da5227058d 100644 --- a/src/input_common/udp/client.cpp +++ b/src/input_common/udp/client.cpp @@ -59,8 +59,7 @@ public: void StartReceive() { socket.async_receive_from( boost::asio::buffer(receive_buffer), receive_endpoint, - [this](const boost::system::error_code& error, std::size_t bytes_transferred) - { + [this](const boost::system::error_code& error, std::size_t bytes_transferred) { HandleReceive(error, bytes_transferred); }); } @@ -212,27 +211,21 @@ void Client::StartCommunication(const std::string& host, u16 port, u8 pad_index, void TestCommunication(const std::string& host, u16 port, u8 pad_index, u32 client_id, std::function success_callback, std::function failure_callback) { - std::thread([=] - { - Common::Event success_event; - SocketCallback callback{[](Response::Version version) - { - }, - [](Response::PortInfo info) - { - }, - [&](Response::PadData data) { success_event.Set(); }}; - Socket socket{host, port, pad_index, client_id, std::move(callback)}; - std::thread worker_thread{SocketLoop, &socket}; - bool result = success_event.WaitFor(std::chrono::seconds(8)); - socket.Stop(); - worker_thread.join(); - if (result) { - success_callback(); - } else { - failure_callback(); - } - }) + std::thread([=] { + Common::Event success_event; + SocketCallback callback{[](Response::Version version) {}, [](Response::PortInfo info) {}, + [&](Response::PadData data) { success_event.Set(); }}; + Socket socket{host, port, pad_index, client_id, std::move(callback)}; + std::thread worker_thread{SocketLoop, &socket}; + bool result = success_event.WaitFor(std::chrono::seconds(8)); + socket.Stop(); + worker_thread.join(); + if (result) { + success_callback(); + } else { + failure_callback(); + } + }) .detach(); } @@ -241,60 +234,53 @@ CalibrationConfigurationJob::CalibrationConfigurationJob( std::function status_callback, std::function data_callback) { - std::thread([=] - { - constexpr u16 CALIBRATION_THRESHOLD = 100; - - u16 min_x{UINT16_MAX}; - u16 min_y{UINT16_MAX}; - u16 max_x{}; - u16 max_y{}; - - Status current_status{Status::Initialized}; - SocketCallback callback{[](Response::Version version) - { - }, - [](Response::PortInfo info) - { - }, - [&](Response::PadData data) - { - if (current_status == Status::Initialized) { - // Receiving data means the communication is ready now - current_status = Status::Ready; - status_callback(current_status); - } - if (!data.touch_1.is_active) { - return; - } - LOG_DEBUG(Input, "Current touch: {} {}", data.touch_1.x, - data.touch_1.y); - min_x = std::min(min_x, static_cast(data.touch_1.x)); - min_y = std::min(min_y, static_cast(data.touch_1.y)); - if (current_status == Status::Ready) { - // First touch - min data (min_x/min_y) - current_status = Status::Stage1Completed; - status_callback(current_status); - } - if (data.touch_1.x - min_x > CALIBRATION_THRESHOLD && - data.touch_1.y - min_y > CALIBRATION_THRESHOLD) { - // Set the current position as max value and finishes - // configuration - max_x = data.touch_1.x; - max_y = data.touch_1.y; - current_status = Status::Completed; - data_callback(min_x, min_y, max_x, max_y); - status_callback(current_status); - - complete_event.Set(); - } - }}; - Socket socket{host, port, pad_index, client_id, std::move(callback)}; - std::thread worker_thread{SocketLoop, &socket}; - complete_event.Wait(); - socket.Stop(); - worker_thread.join(); - }) + std::thread([=] { + constexpr u16 CALIBRATION_THRESHOLD = 100; + + u16 min_x{UINT16_MAX}; + u16 min_y{UINT16_MAX}; + u16 max_x{}; + u16 max_y{}; + + Status current_status{Status::Initialized}; + SocketCallback callback{[](Response::Version version) {}, [](Response::PortInfo info) {}, + [&](Response::PadData data) { + if (current_status == Status::Initialized) { + // Receiving data means the communication is ready now + current_status = Status::Ready; + status_callback(current_status); + } + if (!data.touch_1.is_active) { + return; + } + LOG_DEBUG(Input, "Current touch: {} {}", data.touch_1.x, + data.touch_1.y); + min_x = std::min(min_x, static_cast(data.touch_1.x)); + min_y = std::min(min_y, static_cast(data.touch_1.y)); + if (current_status == Status::Ready) { + // First touch - min data (min_x/min_y) + current_status = Status::Stage1Completed; + status_callback(current_status); + } + if (data.touch_1.x - min_x > CALIBRATION_THRESHOLD && + data.touch_1.y - min_y > CALIBRATION_THRESHOLD) { + // Set the current position as max value and finishes + // configuration + max_x = data.touch_1.x; + max_y = data.touch_1.y; + current_status = Status::Completed; + data_callback(min_x, min_y, max_x, max_y); + status_callback(current_status); + + complete_event.Set(); + } + }}; + Socket socket{host, port, pad_index, client_id, std::move(callback)}; + std::thread worker_thread{SocketLoop, &socket}; + complete_event.Wait(); + socket.Stop(); + worker_thread.join(); + }) .detach(); } diff --git a/src/input_common/udp/client.h b/src/input_common/udp/client.h index b58e319b65..b8c6547554 100644 --- a/src/input_common/udp/client.h +++ b/src/input_common/udp/client.h @@ -40,7 +40,6 @@ struct DeviceStatus { u16 max_x{}; u16 max_y{}; }; - std::optional touch_calibration; }; @@ -73,7 +72,6 @@ public: Stage1Completed, Completed, }; - /** * Constructs and starts the job with the specified parameter. * diff --git a/src/input_common/udp/protocol.h b/src/input_common/udp/protocol.h index 2b31846db4..3ba4d1fc8d 100644 --- a/src/input_common/udp/protocol.h +++ b/src/input_common/udp/protocol.h @@ -35,7 +35,6 @@ struct Header { ///> the data Type type{}; }; - static_assert(sizeof(Header) == 20, "UDP Message Header struct has wrong size"); static_assert(std::is_trivially_copyable_v
, "UDP Message Header is not trivially copyable"); @@ -55,9 +54,7 @@ constexpr Type GetMessageType(); namespace Request { -struct Version { -}; - +struct Version {}; /** * Requests the server to send information about what controllers are plugged into the ports * In citra's case, we only have one controller, so for simplicity's sake, we can just send a @@ -65,14 +62,12 @@ struct Version { * nice to make this configurable */ constexpr u32 MAX_PORTS = 4; - struct PortInfo { u32_le pad_count{}; ///> Number of ports to request data for std::array port; }; - static_assert(std::is_trivially_copyable_v, - "UDP Request PortInfo is not trivially copyable"); + "UDP Request PortInfo is not trivially copyable"); /** * Request the latest pad information from the server. If the server hasn't received this message @@ -85,7 +80,6 @@ struct PadData { Id, Mac, }; - /// Determines which method will be used as a look up for the controller Flags flags{}; /// Index of the port of the controller to retrieve data about @@ -93,10 +87,9 @@ struct PadData { /// Mac address of the controller to retrieve data about MacAddress mac; }; - static_assert(sizeof(PadData) == 8, "UDP Request PadData struct has wrong size"); static_assert(std::is_trivially_copyable_v, - "UDP Request PadData is not trivially copyable"); + "UDP Request PadData is not trivially copyable"); /** * Creates a message with the proper header data that can be sent to the server. @@ -121,10 +114,9 @@ namespace Response { struct Version { u16_le version{}; }; - static_assert(sizeof(Version) == 2, "UDP Response Version struct has wrong size"); static_assert(std::is_trivially_copyable_v, - "UDP Response Version is not trivially copyable"); + "UDP Response Version is not trivially copyable"); struct PortInfo { u8 id{}; @@ -135,10 +127,9 @@ struct PortInfo { u8 battery{}; u8 is_pad_active{}; }; - static_assert(sizeof(PortInfo) == 12, "UDP Response PortInfo struct has wrong size"); static_assert(std::is_trivially_copyable_v, - "UDP Response PortInfo is not trivially copyable"); + "UDP Response PortInfo is not trivially copyable"); #pragma pack(push, 1) struct PadData { @@ -215,16 +206,16 @@ struct PadData { static_assert(sizeof(PadData) == 80, "UDP Response PadData struct has wrong size "); static_assert(std::is_trivially_copyable_v, - "UDP Response PadData is not trivially copyable"); + "UDP Response PadData is not trivially copyable"); static_assert(sizeof(Message) == MAX_PACKET_SIZE, - "UDP MAX_PACKET_SIZE is no longer larger than Message"); + "UDP MAX_PACKET_SIZE is no longer larger than Message"); static_assert(sizeof(PadData::AnalogButton) == 12, - "UDP Response AnalogButton struct has wrong size "); + "UDP Response AnalogButton struct has wrong size "); static_assert(sizeof(PadData::TouchPad) == 6, "UDP Response TouchPad struct has wrong size "); static_assert(sizeof(PadData::Accelerometer) == 12, - "UDP Response Accelerometer struct has wrong size "); + "UDP Response Accelerometer struct has wrong size "); static_assert(sizeof(PadData::Gyroscope) == 12, "UDP Response Gyroscope struct has wrong size "); /** @@ -241,27 +232,22 @@ template <> constexpr Type GetMessageType() { return Type::Version; } - template <> constexpr Type GetMessageType() { return Type::PortInfo; } - template <> constexpr Type GetMessageType() { return Type::PadData; } - template <> constexpr Type GetMessageType() { return Type::Version; } - template <> constexpr Type GetMessageType() { return Type::PortInfo; } - template <> constexpr Type GetMessageType() { return Type::PadData; diff --git a/src/input_common/udp/udp.cpp b/src/input_common/udp/udp.cpp index 343c3985ef..8c6ef13949 100644 --- a/src/input_common/udp/udp.cpp +++ b/src/input_common/udp/udp.cpp @@ -16,10 +16,7 @@ namespace InputCommon::CemuhookUDP { class UDPTouchDevice final : public Input::TouchDevice { public: - explicit UDPTouchDevice(std::shared_ptr status_) - : status(std::move(status_)) { - } - + explicit UDPTouchDevice(std::shared_ptr status_) : status(std::move(status_)) {} std::tuple GetStatus() const override { std::lock_guard guard(status->update_mutex); return status->touch_status; @@ -31,10 +28,7 @@ private: class UDPMotionDevice final : public Input::MotionDevice { public: - explicit UDPMotionDevice(std::shared_ptr status_) - : status(std::move(status_)) { - } - + explicit UDPMotionDevice(std::shared_ptr status_) : status(std::move(status_)) {} std::tuple, Common::Vec3> GetStatus() const override { std::lock_guard guard(status->update_mutex); return status->motion_status; @@ -46,9 +40,7 @@ private: class UDPTouchFactory final : public Input::Factory { public: - explicit UDPTouchFactory(std::shared_ptr status_) - : status(std::move(status_)) { - } + explicit UDPTouchFactory(std::shared_ptr status_) : status(std::move(status_)) {} std::unique_ptr Create(const Common::ParamPackage& params) override { { @@ -69,9 +61,7 @@ private: class UDPMotionFactory final : public Input::Factory { public: - explicit UDPMotionFactory(std::shared_ptr status_) - : status(std::move(status_)) { - } + explicit UDPMotionFactory(std::shared_ptr status_) : status(std::move(status_)) {} std::unique_ptr Create(const Common::ParamPackage& params) override { return std::make_unique(status); -- cgit v1.2.3 From eddf2d0f4e346accb8a18fd4f4b3b7c6faa076d6 Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 18:43:01 -0400 Subject: Singleton GC Adapter class, remove globals, fix naming convention Fix clang formatting Manual fix for configure_input_player formatting Add missing lib usb cmake command --- CMakeLists.txt | 6 + src/input_common/gcadapter/gc_adapter.cpp | 176 +++++++++++----------- src/input_common/gcadapter/gc_adapter.h | 145 ++++++++++++------ src/input_common/gcadapter/gc_poller.cpp | 125 +++++++-------- src/input_common/gcadapter/gc_poller.h | 3 + src/input_common/main.cpp | 2 + src/input_common/main.h | 4 +- src/input_common/udp/client.cpp | 6 +- src/yuzu/configuration/configure_input_player.cpp | 50 +++--- 9 files changed, 289 insertions(+), 228 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/CMakeLists.txt b/CMakeLists.txt index b710712711..967968226b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -328,6 +328,12 @@ elseif(SDL2_FOUND) target_link_libraries(SDL2 INTERFACE "${SDL2_LIBRARIES}") endif() +# Ensure libusb is properly configured (based on dolphin libusb include) +find_package(LibUSB) +add_subdirectory(externals/libusb) +set(LIBUSB_LIBRARIES usb) + + # Prefer the -pthread flag on Linux. set(THREADS_PREFER_PTHREAD_FLAG ON) find_package(Threads REQUIRED) diff --git a/src/input_common/gcadapter/gc_adapter.cpp b/src/input_common/gcadapter/gc_adapter.cpp index dc04116ce7..0696a96c7b 100644 --- a/src/input_common/gcadapter/gc_adapter.cpp +++ b/src/input_common/gcadapter/gc_adapter.cpp @@ -3,45 +3,41 @@ // Refer to the license.txt file included. #include "common/logging/log.h" -#include "common/threadsafe_queue.h" #include "input_common/gcadapter/gc_adapter.h" -Common::SPSCQueue pad_queue[4]; -struct GCState state[4]; - namespace GCAdapter { +Adapter* Adapter::adapter_instance{nullptr}; -static libusb_device_handle* usb_adapter_handle = nullptr; -static u8 adapter_controllers_status[4] = { - ControllerTypes::CONTROLLER_NONE, ControllerTypes::CONTROLLER_NONE, - ControllerTypes::CONTROLLER_NONE, ControllerTypes::CONTROLLER_NONE}; - -static std::mutex s_mutex; - -static std::thread adapter_input_thread; -static bool adapter_thread_running; - -static std::mutex initialization_mutex; -static std::thread detect_thread; -static bool detect_thread_running = false; +Adapter::Adapter() { + if (usb_adapter_handle != nullptr) { + return; + } + LOG_INFO(Input, "GC Adapter Initialization started"); -static libusb_context* libusb_ctx; + current_status = NO_ADAPTER_DETECTED; + libusb_init(&libusb_ctx); -static u8 input_endpoint = 0; + StartScanThread(); +} -static bool configuring = false; +Adapter* Adapter::GetInstance() { + if (!adapter_instance) { + adapter_instance = new Adapter; + } + return adapter_instance; +} -GCPadStatus CheckStatus(int port, u8 adapter_payload[37]) { +GCPadStatus Adapter::CheckStatus(int port, u8 adapter_payload[37]) { GCPadStatus pad = {}; bool get_origin = false; - u8 type = adapter_payload[1 + (9 * port)] >> 4; - if (type) + ControllerTypes type = ControllerTypes(adapter_payload[1 + (9 * port)] >> 4); + if (type != ControllerTypes::None) get_origin = true; adapter_controllers_status[port] = type; - if (adapter_controllers_status[port] != ControllerTypes::CONTROLLER_NONE) { + if (adapter_controllers_status[port] != ControllerTypes::None) { u8 b1 = adapter_payload[1 + (9 * port) + 1]; u8 b2 = adapter_payload[1 + (9 * port) + 2]; @@ -88,18 +84,17 @@ GCPadStatus CheckStatus(int port, u8 adapter_payload[37]) { pad.button |= PAD_GET_ORIGIN; } - pad.stickX = adapter_payload[1 + (9 * port) + 3]; - pad.stickY = adapter_payload[1 + (9 * port) + 4]; - pad.substickX = adapter_payload[1 + (9 * port) + 5]; - pad.substickY = adapter_payload[1 + (9 * port) + 6]; - pad.triggerLeft = adapter_payload[1 + (9 * port) + 7]; - pad.triggerRight = adapter_payload[1 + (9 * port) + 8]; + pad.stick_x = adapter_payload[1 + (9 * port) + 3]; + pad.stick_y = adapter_payload[1 + (9 * port) + 4]; + pad.substick_x = adapter_payload[1 + (9 * port) + 5]; + pad.substick_y = adapter_payload[1 + (9 * port) + 6]; + pad.trigger_left = adapter_payload[1 + (9 * port) + 7]; + pad.trigger_right = adapter_payload[1 + (9 * port) + 8]; } return pad; } -void PadToState(GCPadStatus pad, GCState& state) { - // std::lock_guard lock{s_mutex}; +void Adapter::PadToState(GCPadStatus pad, GCState& state) { state.buttons.insert_or_assign(PAD_BUTTON_A, pad.button & PAD_BUTTON_A); state.buttons.insert_or_assign(PAD_BUTTON_B, pad.button & PAD_BUTTON_B); state.buttons.insert_or_assign(PAD_BUTTON_X, pad.button & PAD_BUTTON_X); @@ -112,15 +107,15 @@ void PadToState(GCPadStatus pad, GCState& state) { state.buttons.insert_or_assign(PAD_TRIGGER_Z, pad.button & PAD_TRIGGER_Z); state.buttons.insert_or_assign(PAD_TRIGGER_L, pad.button & PAD_TRIGGER_L); state.buttons.insert_or_assign(PAD_TRIGGER_R, pad.button & PAD_TRIGGER_R); - state.axes.insert_or_assign(STICK_X, pad.stickX); - state.axes.insert_or_assign(STICK_Y, pad.stickY); - state.axes.insert_or_assign(SUBSTICK_X, pad.substickX); - state.axes.insert_or_assign(SUBSTICK_Y, pad.substickY); - state.axes.insert_or_assign(TRIGGER_LEFT, pad.triggerLeft); - state.axes.insert_or_assign(TRIGGER_RIGHT, pad.triggerRight); + state.axes.insert_or_assign(static_cast(PadAxes::StickX), pad.stick_x); + state.axes.insert_or_assign(static_cast(PadAxes::StickY), pad.stick_y); + state.axes.insert_or_assign(static_cast(PadAxes::SubstickX), pad.substick_x); + state.axes.insert_or_assign(static_cast(PadAxes::SubstickY), pad.substick_y); + state.axes.insert_or_assign(static_cast(PadAxes::TriggerLeft), pad.trigger_left); + state.axes.insert_or_assign(static_cast(PadAxes::TriggerRight), pad.trigger_right); } -static void Read() { +void Adapter::Read() { LOG_INFO(Input, "GC Adapter Read() thread started"); int payload_size_in; @@ -145,8 +140,9 @@ static void Read() { LOG_ERROR(Input, "error reading payload (size: %d, type: %02x)", payload_size, controller_payload_copy[0]); } else { - for (int i = 0; i < 4; i++) - pad[i] = CheckStatus(i, controller_payload_copy); + for (int port = 0; port < 4; port++) { + pad[port] = CheckStatus(port, controller_payload_copy); + } } for (int port = 0; port < 4; port++) { if (DeviceConnected(port) && configuring) { @@ -155,28 +151,36 @@ static void Read() { } // Accounting for a threshold here because of some controller variance - if (pad[port].stickX > pad[port].MAIN_STICK_CENTER_X + pad[port].THRESHOLD || - pad[port].stickX < pad[port].MAIN_STICK_CENTER_X - pad[port].THRESHOLD) { - pad[port].axis_which = STICK_X; - pad[port].axis_value = pad[port].stickX; + if (pad[port].stick_x > + pad_constants.MAIN_STICK_CENTER_X + pad_constants.THRESHOLD || + pad[port].stick_x < + pad_constants.MAIN_STICK_CENTER_X - pad_constants.THRESHOLD) { + pad[port].axis = GCAdapter::PadAxes::StickX; + pad[port].axis_value = pad[port].stick_x; pad_queue[port].Push(pad[port]); } - if (pad[port].stickY > pad[port].MAIN_STICK_CENTER_Y + pad[port].THRESHOLD || - pad[port].stickY < pad[port].MAIN_STICK_CENTER_Y - pad[port].THRESHOLD) { - pad[port].axis_which = STICK_Y; - pad[port].axis_value = pad[port].stickY; + if (pad[port].stick_y > + pad_constants.MAIN_STICK_CENTER_Y + pad_constants.THRESHOLD || + pad[port].stick_y < + pad_constants.MAIN_STICK_CENTER_Y - pad_constants.THRESHOLD) { + pad[port].axis = GCAdapter::PadAxes::StickY; + pad[port].axis_value = pad[port].stick_y; pad_queue[port].Push(pad[port]); } - if (pad[port].substickX > pad[port].C_STICK_CENTER_X + pad[port].THRESHOLD || - pad[port].substickX < pad[port].C_STICK_CENTER_X - pad[port].THRESHOLD) { - pad[port].axis_which = SUBSTICK_X; - pad[port].axis_value = pad[port].substickX; + if (pad[port].substick_x > + pad_constants.C_STICK_CENTER_X + pad_constants.THRESHOLD || + pad[port].substick_x < + pad_constants.C_STICK_CENTER_X - pad_constants.THRESHOLD) { + pad[port].axis = GCAdapter::PadAxes::SubstickX; + pad[port].axis_value = pad[port].substick_x; pad_queue[port].Push(pad[port]); } - if (pad[port].substickY > pad[port].C_STICK_CENTER_Y + pad[port].THRESHOLD || - pad[port].substickY < pad[port].C_STICK_CENTER_Y - pad[port].THRESHOLD) { - pad[port].axis_which = SUBSTICK_Y; - pad[port].axis_value = pad[port].substickY; + if (pad[port].substick_y > + pad_constants.C_STICK_CENTER_Y + pad_constants.THRESHOLD || + pad[port].substick_y < + pad_constants.C_STICK_CENTER_Y - pad_constants.THRESHOLD) { + pad[port].axis = GCAdapter::PadAxes::SubstickY; + pad[port].axis_value = pad[port].substick_y; pad_queue[port].Push(pad[port]); } } @@ -186,7 +190,7 @@ static void Read() { } } -static void ScanThreadFunc() { +void Adapter::ScanThreadFunc() { LOG_INFO(Input, "GC Adapter scanning thread started"); while (detect_thread_running) { @@ -198,20 +202,7 @@ static void ScanThreadFunc() { } } -void Init() { - - if (usb_adapter_handle != nullptr) { - return; - } - LOG_INFO(Input, "GC Adapter Initialization started"); - - current_status = NO_ADAPTER_DETECTED; - libusb_init(&libusb_ctx); - - StartScanThread(); -} - -void StartScanThread() { +void Adapter::StartScanThread() { if (detect_thread_running) { return; } @@ -220,21 +211,21 @@ void StartScanThread() { } detect_thread_running = true; - detect_thread = std::thread(ScanThreadFunc); + detect_thread = std::thread([=] { ScanThreadFunc(); }); } -void StopScanThread() { +void Adapter::StopScanThread() { detect_thread.join(); } -static void Setup() { +void Adapter::Setup() { // Reset the error status in case the adapter gets unplugged if (current_status < 0) { current_status = NO_ADAPTER_DETECTED; } for (int i = 0; i < 4; i++) { - adapter_controllers_status[i] = ControllerTypes::CONTROLLER_NONE; + adapter_controllers_status[i] = ControllerTypes::None; } libusb_device** devs; // pointer to list of connected usb devices @@ -250,7 +241,7 @@ static void Setup() { } } -static bool CheckDeviceAccess(libusb_device* device) { +bool Adapter::CheckDeviceAccess(libusb_device* device) { libusb_device_descriptor desc; int ret = libusb_get_device_descriptor(device, &desc); if (ret) { @@ -300,7 +291,7 @@ static bool CheckDeviceAccess(libusb_device* device) { return true; } -static void GetGCEndpoint(libusb_device* device) { +void Adapter::GetGCEndpoint(libusb_device* device) { libusb_config_descriptor* config = nullptr; libusb_get_config_descriptor(device, 0, &config); for (u8 ic = 0; ic < config->bNumInterfaces; ic++) { @@ -318,18 +309,17 @@ static void GetGCEndpoint(libusb_device* device) { adapter_thread_running = true; current_status = ADAPTER_DETECTED; - - adapter_input_thread = std::thread(Read); // Read input + adapter_input_thread = std::thread([=] { Read(); }); // Read input } -void Shutdown() { +Adapter::~Adapter() { StopScanThread(); Reset(); current_status = NO_ADAPTER_DETECTED; } -static void Reset() { +void Adapter::Reset() { std::unique_lock lock(initialization_mutex, std::defer_lock); if (!lock.try_lock()) { return; @@ -343,7 +333,7 @@ static void Reset() { } for (int i = 0; i < 4; i++) { - adapter_controllers_status[i] = ControllerTypes::CONTROLLER_NONE; + adapter_controllers_status[i] = ControllerTypes::None; } current_status = NO_ADAPTER_DETECTED; @@ -355,20 +345,28 @@ static void Reset() { } } -bool DeviceConnected(int port) { - return adapter_controllers_status[port] != ControllerTypes::CONTROLLER_NONE; +bool Adapter::DeviceConnected(int port) { + return adapter_controllers_status[port] != ControllerTypes::None; } -void ResetDeviceType(int port) { - adapter_controllers_status[port] = ControllerTypes::CONTROLLER_NONE; +void Adapter::ResetDeviceType(int port) { + adapter_controllers_status[port] = ControllerTypes::None; } -void BeginConfiguration() { +void Adapter::BeginConfiguration() { configuring = true; } -void EndConfiguration() { +void Adapter::EndConfiguration() { configuring = false; } +std::array, 4>& Adapter::GetPadQueue() { + return pad_queue; +} + +std::array& Adapter::GetPadState() { + return state; +} + } // end of namespace GCAdapter diff --git a/src/input_common/gcadapter/gc_adapter.h b/src/input_common/gcadapter/gc_adapter.h index 05ee73c651..3d5c41f9ab 100644 --- a/src/input_common/gcadapter/gc_adapter.h +++ b/src/input_common/gcadapter/gc_adapter.h @@ -8,6 +8,9 @@ #include #include #include "common/common_types.h" +#include "common/threadsafe_queue.h" + +namespace GCAdapter { enum { PAD_USE_ORIGIN = 0x0080, @@ -33,29 +36,38 @@ enum PadButton { }; -enum PadAxes { STICK_X, STICK_Y, SUBSTICK_X, SUBSTICK_Y, TRIGGER_LEFT, TRIGGER_RIGHT }; +enum class PadAxes : u8 { + StickX, + StickY, + SubstickX, + SubstickY, + TriggerLeft, + TriggerRight, + Undefined, +}; +const struct GCPadConstants { + const u8 MAIN_STICK_CENTER_X = 0x80; + const u8 MAIN_STICK_CENTER_Y = 0x80; + const u8 MAIN_STICK_RADIUS = 0x7f; + const u8 C_STICK_CENTER_X = 0x80; + const u8 C_STICK_CENTER_Y = 0x80; + const u8 C_STICK_RADIUS = 0x7f; + + const u8 TRIGGER_CENTER = 20; + const u8 THRESHOLD = 10; +} pad_constants; struct GCPadStatus { - u16 button; // Or-ed PAD_BUTTON_* and PAD_TRIGGER_* bits - u8 stickX; // 0 <= stickX <= 255 - u8 stickY; // 0 <= stickY <= 255 - u8 substickX; // 0 <= substickX <= 255 - u8 substickY; // 0 <= substickY <= 255 - u8 triggerLeft; // 0 <= triggerLeft <= 255 - u8 triggerRight; // 0 <= triggerRight <= 255 - bool isConnected{true}; - - static const u8 MAIN_STICK_CENTER_X = 0x80; - static const u8 MAIN_STICK_CENTER_Y = 0x80; - static const u8 MAIN_STICK_RADIUS = 0x7f; - static const u8 C_STICK_CENTER_X = 0x80; - static const u8 C_STICK_CENTER_Y = 0x80; - static const u8 C_STICK_RADIUS = 0x7f; - - static const u8 TRIGGER_CENTER = 20; - static const u8 THRESHOLD = 10; + u16 button; // Or-ed PAD_BUTTON_* and PAD_TRIGGER_* bits + u8 stick_x; // 0 <= stick_x <= 255 + u8 stick_y; // 0 <= stick_y <= 255 + u8 substick_x; // 0 <= substick_x <= 255 + u8 substick_y; // 0 <= substick_y <= 255 + u8 trigger_left; // 0 <= trigger_left <= 255 + u8 trigger_right; // 0 <= trigger_right <= 255 + u8 port; - u8 axis_which = 255; + PadAxes axis = PadAxes::Undefined; u8 axis_value = 255; }; @@ -64,51 +76,88 @@ struct GCState { std::unordered_map axes; }; -namespace GCAdapter { -enum ControllerTypes { CONTROLLER_NONE = 0, CONTROLLER_WIRED = 1, CONTROLLER_WIRELESS = 2 }; +enum class ControllerTypes { None, Wired, Wireless }; enum { NO_ADAPTER_DETECTED = 0, ADAPTER_DETECTED = 1, }; -// Current adapter status: detected/not detected/in error (holds the error code) -static int current_status = NO_ADAPTER_DETECTED; +/// Singleton Adapter class +class Adapter { +public: + /// For retreiving the singleton instance + static Adapter* GetInstance(); + + /// Used for polling + void BeginConfiguration(); + void EndConfiguration(); + + std::array, 4>& GetPadQueue(); + std::array& GetPadState(); + +private: + /// Singleton instance. + static Adapter* adapter_instance; + + /// Initialize the GC Adapter capture and read sequence + Adapter(); -GCPadStatus CheckStatus(int port, u8 adapter_payload[37]); -/// Initialize the GC Adapter capture and read sequence -void Init(); + /// Close the adapter read thread and release the adapter + ~Adapter(); -/// Close the adapter read thread and release the adapter -void Shutdown(); + GCPadStatus CheckStatus(int port, u8 adapter_payload[37]); -/// Begin scanning for the GC Adapter. -void StartScanThread(); + void PadToState(GCPadStatus pad, GCState& state); -/// Stop scanning for the adapter -void StopScanThread(); + void Read(); + void ScanThreadFunc(); + /// Begin scanning for the GC Adapter. + void StartScanThread(); -/// Returns true if there is a device connected to port -bool DeviceConnected(int port); + /// Stop scanning for the adapter + void StopScanThread(); -/// Resets status of device connected to port -void ResetDeviceType(int port); + /// Returns true if there is a device connected to port + bool DeviceConnected(int port); -/// Returns true if we successfully gain access to GC Adapter -bool CheckDeviceAccess(libusb_device* device); + /// Resets status of device connected to port + void ResetDeviceType(int port); -/// Captures GC Adapter endpoint address, -void GetGCEndpoint(libusb_device* device); + /// Returns true if we successfully gain access to GC Adapter + bool CheckDeviceAccess(libusb_device* device); -/// For shutting down, clear all data, join all threads, release usb -void Reset(); + /// Captures GC Adapter endpoint address, + void GetGCEndpoint(libusb_device* device); -/// For use in initialization, querying devices to find the adapter -void Setup(); + /// For shutting down, clear all data, join all threads, release usb + void Reset(); -/// Used for polling -void BeginConfiguration(); + /// For use in initialization, querying devices to find the adapter + void Setup(); -void EndConfiguration(); + int current_status = NO_ADAPTER_DETECTED; + libusb_device_handle* usb_adapter_handle = nullptr; + ControllerTypes adapter_controllers_status[4] = {ControllerTypes::None, ControllerTypes::None, + ControllerTypes::None, ControllerTypes::None}; + + std::mutex s_mutex; + + std::thread adapter_input_thread; + bool adapter_thread_running; + + std::mutex initialization_mutex; + std::thread detect_thread; + bool detect_thread_running = false; + + libusb_context* libusb_ctx; + + u8 input_endpoint = 0; + + bool configuring = false; + + std::array, 4> pad_queue; + std::array state; +}; } // end of namespace GCAdapter diff --git a/src/input_common/gcadapter/gc_poller.cpp b/src/input_common/gcadapter/gc_poller.cpp index 51b3362d64..0e591baca2 100644 --- a/src/input_common/gcadapter/gc_poller.cpp +++ b/src/input_common/gcadapter/gc_poller.cpp @@ -10,35 +10,34 @@ #include "input_common/gcadapter/gc_adapter.h" #include "input_common/gcadapter/gc_poller.h" -// Using extern as to avoid multply defined symbols. -extern Common::SPSCQueue pad_queue[4]; -extern struct GCState state[4]; - namespace InputCommon { class GCButton final : public Input::ButtonDevice { public: - explicit GCButton(int port_, int button_, int axis_) : port(port_), button(button_) {} + explicit GCButton(int port_, int button_, int axis_, GCAdapter::Adapter* adapter) + : port(port_), button(button_), gcadapter(adapter) {} ~GCButton() override; bool GetStatus() const override { - return state[port].buttons.at(button); + return gcadapter->GetPadState()[port].buttons.at(button); } private: const int port; const int button; + GCAdapter::Adapter* gcadapter; }; class GCAxisButton final : public Input::ButtonDevice { public: - explicit GCAxisButton(int port_, int axis_, float threshold_, bool trigger_if_greater_) - : port(port_), axis(axis_), threshold(threshold_), trigger_if_greater(trigger_if_greater_) { - } + explicit GCAxisButton(int port_, int axis_, float threshold_, bool trigger_if_greater_, + GCAdapter::Adapter* adapter) + : port(port_), axis(axis_), threshold(threshold_), trigger_if_greater(trigger_if_greater_), + gcadapter(adapter) {} bool GetStatus() const override { - const float axis_value = (state[port].axes.at(axis) - 128.0f) / 128.0f; + const float axis_value = (gcadapter->GetPadState()[port].axes.at(axis) - 128.0f) / 128.0f; if (trigger_if_greater) { return axis_value > 0.10f; // TODO(ameerj) : Fix threshold. } @@ -50,14 +49,15 @@ private: const int axis; float threshold; bool trigger_if_greater; + GCAdapter::Adapter* gcadapter; }; GCButtonFactory::GCButtonFactory() { - GCAdapter::Init(); + adapter = GCAdapter::Adapter::GetInstance(); } GCButton::~GCButton() { - GCAdapter::Shutdown(); + // GCAdapter::Shutdown(); } std::unique_ptr GCButtonFactory::Create(const Common::ParamPackage& params) { @@ -77,76 +77,76 @@ std::unique_ptr GCButtonFactory::Create(const Common::Param trigger_if_greater = true; LOG_ERROR(Input, "Unknown direction {}", direction_name); } - return std::make_unique(port, axis, threshold, trigger_if_greater); + return std::make_unique(port, axis, threshold, trigger_if_greater, adapter); } std::unique_ptr button = - std::make_unique(port, button_id, params.Get("axis", 0)); + std::make_unique(port, button_id, params.Get("axis", 0), adapter); return std::move(button); } Common::ParamPackage GCButtonFactory::GetNextInput() { Common::ParamPackage params; - GCPadStatus pad; + GCAdapter::GCPadStatus pad; for (int i = 0; i < 4; i++) { - while (pad_queue[i].Pop(pad)) { + while (adapter->GetPadQueue()[i].Pop(pad)) { // This while loop will break on the earliest detected button params.Set("engine", "gcpad"); params.Set("port", i); // I was debating whether to keep these verbose for ease of reading // or to use a while loop shifting the bits to test and set the value. - if (pad.button & PAD_BUTTON_A) { - params.Set("button", PAD_BUTTON_A); + if (pad.button & GCAdapter::PAD_BUTTON_A) { + params.Set("button", GCAdapter::PAD_BUTTON_A); break; } - if (pad.button & PAD_BUTTON_B) { - params.Set("button", PAD_BUTTON_B); + if (pad.button & GCAdapter::PAD_BUTTON_B) { + params.Set("button", GCAdapter::PAD_BUTTON_B); break; } - if (pad.button & PAD_BUTTON_X) { - params.Set("button", PAD_BUTTON_X); + if (pad.button & GCAdapter::PAD_BUTTON_X) { + params.Set("button", GCAdapter::PAD_BUTTON_X); break; } - if (pad.button & PAD_BUTTON_Y) { - params.Set("button", PAD_BUTTON_Y); + if (pad.button & GCAdapter::PAD_BUTTON_Y) { + params.Set("button", GCAdapter::PAD_BUTTON_Y); break; } - if (pad.button & PAD_BUTTON_DOWN) { - params.Set("button", PAD_BUTTON_DOWN); + if (pad.button & GCAdapter::PAD_BUTTON_DOWN) { + params.Set("button", GCAdapter::PAD_BUTTON_DOWN); break; } - if (pad.button & PAD_BUTTON_LEFT) { - params.Set("button", PAD_BUTTON_LEFT); + if (pad.button & GCAdapter::PAD_BUTTON_LEFT) { + params.Set("button", GCAdapter::PAD_BUTTON_LEFT); break; } - if (pad.button & PAD_BUTTON_RIGHT) { - params.Set("button", PAD_BUTTON_RIGHT); + if (pad.button & GCAdapter::PAD_BUTTON_RIGHT) { + params.Set("button", GCAdapter::PAD_BUTTON_RIGHT); break; } - if (pad.button & PAD_BUTTON_UP) { - params.Set("button", PAD_BUTTON_UP); + if (pad.button & GCAdapter::PAD_BUTTON_UP) { + params.Set("button", GCAdapter::PAD_BUTTON_UP); break; } - if (pad.button & PAD_TRIGGER_L) { - params.Set("button", PAD_TRIGGER_L); + if (pad.button & GCAdapter::PAD_TRIGGER_L) { + params.Set("button", GCAdapter::PAD_TRIGGER_L); break; } - if (pad.button & PAD_TRIGGER_R) { - params.Set("button", PAD_TRIGGER_R); + if (pad.button & GCAdapter::PAD_TRIGGER_R) { + params.Set("button", GCAdapter::PAD_TRIGGER_R); break; } - if (pad.button & PAD_TRIGGER_Z) { - params.Set("button", PAD_TRIGGER_Z); + if (pad.button & GCAdapter::PAD_TRIGGER_Z) { + params.Set("button", GCAdapter::PAD_TRIGGER_Z); break; } - if (pad.button & PAD_BUTTON_START) { - params.Set("button", PAD_BUTTON_START); + if (pad.button & GCAdapter::PAD_BUTTON_START) { + params.Set("button", GCAdapter::PAD_BUTTON_START); break; } // For Axis button implementation - if (pad.axis_which != 255) { - params.Set("axis", pad.axis_which); - params.Set("button", PAD_STICK); + if (pad.axis != GCAdapter::PadAxes::Undefined) { + params.Set("axis", static_cast(pad.axis)); + params.Set("button", GCAdapter::PAD_STICK); if (pad.axis_value > 128) { params.Set("direction", "+"); params.Set("threshold", "0.5"); @@ -164,30 +164,30 @@ Common::ParamPackage GCButtonFactory::GetNextInput() { void GCButtonFactory::BeginConfiguration() { polling = true; for (int i = 0; i < 4; i++) { - pad_queue[i].Clear(); + adapter->GetPadQueue()[i].Clear(); } - GCAdapter::BeginConfiguration(); + adapter->BeginConfiguration(); } void GCButtonFactory::EndConfiguration() { polling = false; for (int i = 0; i < 4; i++) { - pad_queue[i].Clear(); + adapter->GetPadQueue()[i].Clear(); } - GCAdapter::EndConfiguration(); + adapter->EndConfiguration(); } class GCAnalog final : public Input::AnalogDevice { public: - GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_) - : port(port_), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_) {} + GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_, GCAdapter::Adapter* adapter) + : port(port_), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_), gcadapter(adapter) {} float GetAxis(int axis) const { std::lock_guard lock{mutex}; // division is not by a perfect 128 to account for some variance in center location // e.g. my device idled at 131 in X, 120 in Y, and full range of motion was in range // [20-230] - return (state[port].axes.at(axis) - 128.0f) / 95.0f; + return (gcadapter->GetPadState()[port].axes.at(axis) - 128.0f) / 95.0f; } std::tuple GetAnalog(int axis_x, int axis_y) const { @@ -238,10 +238,13 @@ private: const int axis_y; const float deadzone; mutable std::mutex mutex; + GCAdapter::Adapter* gcadapter; }; /// An analog device factory that creates analog devices from GC Adapter -GCAnalogFactory::GCAnalogFactory(){}; +GCAnalogFactory::GCAnalogFactory() { + adapter = GCAdapter::Adapter::GetInstance(); +}; /** * Creates analog device from joystick axes @@ -257,35 +260,36 @@ std::unique_ptr GCAnalogFactory::Create(const Common::Param const int axis_y = params.Get("axis_y", 1); const float deadzone = std::clamp(params.Get("deadzone", 0.0f), 0.0f, .99f); - return std::make_unique(port, axis_x, axis_y, deadzone); + return std::make_unique(port, axis_x, axis_y, deadzone, adapter); } void GCAnalogFactory::BeginConfiguration() { polling = true; for (int i = 0; i < 4; i++) { - pad_queue[i].Clear(); + adapter->GetPadQueue()[i].Clear(); } - GCAdapter::BeginConfiguration(); + adapter->BeginConfiguration(); } void GCAnalogFactory::EndConfiguration() { polling = false; for (int i = 0; i < 4; i++) { - pad_queue[i].Clear(); + adapter->GetPadQueue()[i].Clear(); } - GCAdapter::EndConfiguration(); + adapter->EndConfiguration(); } Common::ParamPackage GCAnalogFactory::GetNextInput() { - GCPadStatus pad; + GCAdapter::GCPadStatus pad; for (int i = 0; i < 4; i++) { - while (pad_queue[i].Pop(pad)) { - if (pad.axis_which == 255 || std::abs((pad.axis_value - 128.0f) / 128.0f) < 0.1) { + while (adapter->GetPadQueue()[i].Pop(pad)) { + if (pad.axis == GCAdapter::PadAxes::Undefined || + std::abs((pad.axis_value - 128.0f) / 128.0f) < 0.1) { continue; } // An analog device needs two axes, so we need to store the axis for later and wait for // a second SDL event. The axes also must be from the same joystick. - const int axis = pad.axis_which; + const u8 axis = static_cast(pad.axis); if (analog_x_axis == -1) { analog_x_axis = axis; controller_number = i; @@ -307,4 +311,5 @@ Common::ParamPackage GCAnalogFactory::GetNextInput() { } return params; } + } // namespace InputCommon diff --git a/src/input_common/gcadapter/gc_poller.h b/src/input_common/gcadapter/gc_poller.h index 43aa9e93a3..29b8c0b7c2 100644 --- a/src/input_common/gcadapter/gc_poller.h +++ b/src/input_common/gcadapter/gc_poller.h @@ -35,6 +35,7 @@ public: } private: + GCAdapter::Adapter* adapter; bool polling = false; }; @@ -54,9 +55,11 @@ public: } private: + GCAdapter::Adapter* adapter; int analog_x_axis = -1; int analog_y_axis = -1; int controller_number = -1; bool polling = false; }; + } // namespace InputCommon diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index 7fc0e2db4c..536e5c80a5 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -2,11 +2,13 @@ // Licensed under GPLv2 or any later version // Refer to the license.txt file included. +#include #include #include #include #include "common/param_package.h" #include "input_common/analog_from_button.h" +#include "input_common/gcadapter/gc_adapter.h" #include "input_common/gcadapter/gc_poller.h" #include "input_common/keyboard.h" #include "input_common/main.h" diff --git a/src/input_common/main.h b/src/input_common/main.h index 9e1528c88e..c26222f214 100644 --- a/src/input_common/main.h +++ b/src/input_common/main.h @@ -32,10 +32,8 @@ class MotionEmu; /// Gets the motion emulation factory. MotionEmu* GetMotionEmu(); -class GCButtonFactory; -class GCAnalogFactory; - GCButtonFactory* GetGCButtons(); + GCAnalogFactory* GetGCAnalogs(); /// Generates a serialized param package for creating a keyboard button device diff --git a/src/input_common/udp/client.cpp b/src/input_common/udp/client.cpp index 4c9794ce2c..da5227058d 100644 --- a/src/input_common/udp/client.cpp +++ b/src/input_common/udp/client.cpp @@ -225,7 +225,8 @@ void TestCommunication(const std::string& host, u16 port, u8 pad_index, u32 clie } else { failure_callback(); } - }).detach(); + }) + .detach(); } CalibrationConfigurationJob::CalibrationConfigurationJob( @@ -279,7 +280,8 @@ CalibrationConfigurationJob::CalibrationConfigurationJob( complete_event.Wait(); socket.Stop(); worker_thread.join(); - }).detach(); + }) + .detach(); } CalibrationConfigurationJob::~CalibrationConfigurationJob() { diff --git a/src/yuzu/configuration/configure_input_player.cpp b/src/yuzu/configuration/configure_input_player.cpp index c1a0c423bc..c7d3f45105 100644 --- a/src/yuzu/configuration/configure_input_player.cpp +++ b/src/yuzu/configuration/configure_input_player.cpp @@ -262,25 +262,24 @@ ConfigureInputPlayer::ConfigureInputPlayer(QWidget* parent, std::size_t player_i button->setContextMenuPolicy(Qt::CustomContextMenu); connect(button, &QPushButton::clicked, [=] { - HandleClick( - button_map[button_id], - [=](Common::ParamPackage params) { - // Workaround for ZL & ZR for analog triggers like on XBOX controllors. - // Analog triggers (from controllers like the XBOX controller) would not - // work due to a different range of their signals (from 0 to 255 on - // analog triggers instead of -32768 to 32768 on analog joysticks). The - // SDL driver misinterprets analog triggers as analog joysticks. - // TODO: reinterpret the signal range for analog triggers to map the - // values correctly. This is required for the correct emulation of the - // analog triggers of the GameCube controller. - if (button_id == Settings::NativeButton::ZL || - button_id == Settings::NativeButton::ZR) { - params.Set("direction", "+"); - params.Set("threshold", "0.5"); - } - buttons_param[button_id] = std::move(params); - }, - InputCommon::Polling::DeviceType::Button); + HandleClick(button_map[button_id], + [=](Common::ParamPackage params) { + // Workaround for ZL & ZR for analog triggers like on XBOX controllors. + // Analog triggers (from controllers like the XBOX controller) would not + // work due to a different range of their signals (from 0 to 255 on + // analog triggers instead of -32768 to 32768 on analog joysticks). The + // SDL driver misinterprets analog triggers as analog joysticks. + // TODO: reinterpret the signal range for analog triggers to map the + // values correctly. This is required for the correct emulation of the + // analog triggers of the GameCube controller. + if (button_id == Settings::NativeButton::ZL || + button_id == Settings::NativeButton::ZR) { + params.Set("direction", "+"); + params.Set("threshold", "0.5"); + } + buttons_param[button_id] = std::move(params); + }, + InputCommon::Polling::DeviceType::Button); }); connect(button, &QPushButton::customContextMenuRequested, [=](const QPoint& menu_location) { QMenu context_menu; @@ -306,13 +305,12 @@ ConfigureInputPlayer::ConfigureInputPlayer(QWidget* parent, std::size_t player_i analog_button->setContextMenuPolicy(Qt::CustomContextMenu); connect(analog_button, &QPushButton::clicked, [=]() { - HandleClick( - analog_map_buttons[analog_id][sub_button_id], - [=](const Common::ParamPackage& params) { - SetAnalogButton(params, analogs_param[analog_id], - analog_sub_buttons[sub_button_id]); - }, - InputCommon::Polling::DeviceType::Button); + HandleClick(analog_map_buttons[analog_id][sub_button_id], + [=](const Common::ParamPackage& params) { + SetAnalogButton(params, analogs_param[analog_id], + analog_sub_buttons[sub_button_id]); + }, + InputCommon::Polling::DeviceType::Button); }); connect(analog_button, &QPushButton::customContextMenuRequested, [=](const QPoint& menu_location) { -- cgit v1.2.3 From 4a54dc6bbf422ac3253a7384950db4c688196a7f Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 21:15:58 -0400 Subject: std::arrays where appropriate, clear q in adapter class, other touch ups --- src/input_common/gcadapter/gc_adapter.cpp | 16 +++++++++------- src/input_common/gcadapter/gc_adapter.h | 5 +++-- src/input_common/gcadapter/gc_poller.cpp | 16 +--------------- src/input_common/gcadapter/gc_poller.h | 4 ++-- src/input_common/main.cpp | 1 - 5 files changed, 15 insertions(+), 27 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/gcadapter/gc_adapter.cpp b/src/input_common/gcadapter/gc_adapter.cpp index 0696a96c7b..498bd0d6e8 100644 --- a/src/input_common/gcadapter/gc_adapter.cpp +++ b/src/input_common/gcadapter/gc_adapter.cpp @@ -134,7 +134,7 @@ void Adapter::Read() { payload_size = payload_size_in; } - GCPadStatus pad[4]; + std::array pad; if (payload_size != sizeof(controller_payload_copy) || controller_payload_copy[0] != LIBUSB_DT_HID) { LOG_ERROR(Input, "error reading payload (size: %d, type: %02x)", payload_size, @@ -224,9 +224,7 @@ void Adapter::Setup() { current_status = NO_ADAPTER_DETECTED; } - for (int i = 0; i < 4; i++) { - adapter_controllers_status[i] = ControllerTypes::None; - } + adapter_controllers_status.fill(ControllerTypes::None); libusb_device** devs; // pointer to list of connected usb devices @@ -332,9 +330,7 @@ void Adapter::Reset() { adapter_input_thread.join(); } - for (int i = 0; i < 4; i++) { - adapter_controllers_status[i] = ControllerTypes::None; - } + adapter_controllers_status.fill(ControllerTypes::None); current_status = NO_ADAPTER_DETECTED; @@ -354,10 +350,16 @@ void Adapter::ResetDeviceType(int port) { } void Adapter::BeginConfiguration() { + for (auto& pq : pad_queue) { + pq.Clear(); + } configuring = true; } void Adapter::EndConfiguration() { + for (auto& pq : pad_queue) { + pq.Clear(); + } configuring = false; } diff --git a/src/input_common/gcadapter/gc_adapter.h b/src/input_common/gcadapter/gc_adapter.h index a32ca04649..cb0dd0ab13 100644 --- a/src/input_common/gcadapter/gc_adapter.h +++ b/src/input_common/gcadapter/gc_adapter.h @@ -96,6 +96,8 @@ public: std::array, 4>& GetPadQueue(); std::array& GetPadState(); + std::array, 4>& GetPadQueue() const; + std::array& GetPadState() const; private: /// Singleton instance. @@ -139,8 +141,7 @@ private: int current_status = NO_ADAPTER_DETECTED; libusb_device_handle* usb_adapter_handle = nullptr; - ControllerTypes adapter_controllers_status[4] = {ControllerTypes::None, ControllerTypes::None, - ControllerTypes::None, ControllerTypes::None}; + std::array adapter_controllers_status{}; std::mutex s_mutex; diff --git a/src/input_common/gcadapter/gc_poller.cpp b/src/input_common/gcadapter/gc_poller.cpp index 0e591baca2..ac4126cb62 100644 --- a/src/input_common/gcadapter/gc_poller.cpp +++ b/src/input_common/gcadapter/gc_poller.cpp @@ -56,9 +56,7 @@ GCButtonFactory::GCButtonFactory() { adapter = GCAdapter::Adapter::GetInstance(); } -GCButton::~GCButton() { - // GCAdapter::Shutdown(); -} +GCButton::~GCButton() = default; std::unique_ptr GCButtonFactory::Create(const Common::ParamPackage& params) { int button_id = params.Get("button", 0); @@ -163,17 +161,11 @@ Common::ParamPackage GCButtonFactory::GetNextInput() { void GCButtonFactory::BeginConfiguration() { polling = true; - for (int i = 0; i < 4; i++) { - adapter->GetPadQueue()[i].Clear(); - } adapter->BeginConfiguration(); } void GCButtonFactory::EndConfiguration() { polling = false; - for (int i = 0; i < 4; i++) { - adapter->GetPadQueue()[i].Clear(); - } adapter->EndConfiguration(); } @@ -265,17 +257,11 @@ std::unique_ptr GCAnalogFactory::Create(const Common::Param void GCAnalogFactory::BeginConfiguration() { polling = true; - for (int i = 0; i < 4; i++) { - adapter->GetPadQueue()[i].Clear(); - } adapter->BeginConfiguration(); } void GCAnalogFactory::EndConfiguration() { polling = false; - for (int i = 0; i < 4; i++) { - adapter->GetPadQueue()[i].Clear(); - } adapter->EndConfiguration(); } diff --git a/src/input_common/gcadapter/gc_poller.h b/src/input_common/gcadapter/gc_poller.h index 29b8c0b7c2..31ff1c1237 100644 --- a/src/input_common/gcadapter/gc_poller.h +++ b/src/input_common/gcadapter/gc_poller.h @@ -30,7 +30,7 @@ public: void BeginConfiguration(); void EndConfiguration(); - bool IsPolling() { + bool IsPolling() const { return polling; } @@ -50,7 +50,7 @@ public: void BeginConfiguration(); void EndConfiguration(); - bool IsPolling() { + bool IsPolling() const { return polling; } diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index 536e5c80a5..89dddf7cf7 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -2,7 +2,6 @@ // Licensed under GPLv2 or any later version // Refer to the license.txt file included. -#include #include #include #include -- cgit v1.2.3 From 92a812d8152b3070311e11de8280d7f09acc5cf9 Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 21:50:58 -0400 Subject: shared_ptr for the GC adapter class, constexpr constants --- src/input_common/gcadapter/gc_adapter.cpp | 40 +++++++++++++------------------ src/input_common/gcadapter/gc_adapter.h | 40 +++++++++++++------------------ src/input_common/gcadapter/gc_poller.cpp | 24 +++++++++---------- src/input_common/gcadapter/gc_poller.h | 8 +++---- src/input_common/main.cpp | 6 +++-- 5 files changed, 52 insertions(+), 66 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/gcadapter/gc_adapter.cpp b/src/input_common/gcadapter/gc_adapter.cpp index 498bd0d6e8..db72d76334 100644 --- a/src/input_common/gcadapter/gc_adapter.cpp +++ b/src/input_common/gcadapter/gc_adapter.cpp @@ -6,7 +6,6 @@ #include "input_common/gcadapter/gc_adapter.h" namespace GCAdapter { -Adapter* Adapter::adapter_instance{nullptr}; Adapter::Adapter() { if (usb_adapter_handle != nullptr) { @@ -20,13 +19,6 @@ Adapter::Adapter() { StartScanThread(); } -Adapter* Adapter::GetInstance() { - if (!adapter_instance) { - adapter_instance = new Adapter; - } - return adapter_instance; -} - GCPadStatus Adapter::CheckStatus(int port, u8 adapter_payload[37]) { GCPadStatus pad = {}; bool get_origin = false; @@ -151,34 +143,26 @@ void Adapter::Read() { } // Accounting for a threshold here because of some controller variance - if (pad[port].stick_x > - pad_constants.MAIN_STICK_CENTER_X + pad_constants.THRESHOLD || - pad[port].stick_x < - pad_constants.MAIN_STICK_CENTER_X - pad_constants.THRESHOLD) { + if (pad[port].stick_x > pad[port].MAIN_STICK_CENTER_X + pad[port].THRESHOLD || + pad[port].stick_x < pad[port].MAIN_STICK_CENTER_X - pad[port].THRESHOLD) { pad[port].axis = GCAdapter::PadAxes::StickX; pad[port].axis_value = pad[port].stick_x; pad_queue[port].Push(pad[port]); } - if (pad[port].stick_y > - pad_constants.MAIN_STICK_CENTER_Y + pad_constants.THRESHOLD || - pad[port].stick_y < - pad_constants.MAIN_STICK_CENTER_Y - pad_constants.THRESHOLD) { + if (pad[port].stick_y > pad[port].MAIN_STICK_CENTER_Y + pad[port].THRESHOLD || + pad[port].stick_y < pad[port].MAIN_STICK_CENTER_Y - pad[port].THRESHOLD) { pad[port].axis = GCAdapter::PadAxes::StickY; pad[port].axis_value = pad[port].stick_y; pad_queue[port].Push(pad[port]); } - if (pad[port].substick_x > - pad_constants.C_STICK_CENTER_X + pad_constants.THRESHOLD || - pad[port].substick_x < - pad_constants.C_STICK_CENTER_X - pad_constants.THRESHOLD) { + if (pad[port].substick_x > pad[port].C_STICK_CENTER_X + pad[port].THRESHOLD || + pad[port].substick_x < pad[port].C_STICK_CENTER_X - pad[port].THRESHOLD) { pad[port].axis = GCAdapter::PadAxes::SubstickX; pad[port].axis_value = pad[port].substick_x; pad_queue[port].Push(pad[port]); } - if (pad[port].substick_y > - pad_constants.C_STICK_CENTER_Y + pad_constants.THRESHOLD || - pad[port].substick_y < - pad_constants.C_STICK_CENTER_Y - pad_constants.THRESHOLD) { + if (pad[port].substick_y > pad[port].C_STICK_CENTER_Y + pad[port].THRESHOLD || + pad[port].substick_y < pad[port].C_STICK_CENTER_Y - pad[port].THRESHOLD) { pad[port].axis = GCAdapter::PadAxes::SubstickY; pad[port].axis_value = pad[port].substick_y; pad_queue[port].Push(pad[port]); @@ -367,8 +351,16 @@ std::array, 4>& Adapter::GetPadQueue() { return pad_queue; } +const std::array, 4>& Adapter::GetPadQueue() const { + return pad_queue; +} + std::array& Adapter::GetPadState() { return state; } +const std::array& Adapter::GetPadState() const { + return state; +} + } // end of namespace GCAdapter diff --git a/src/input_common/gcadapter/gc_adapter.h b/src/input_common/gcadapter/gc_adapter.h index cb0dd0ab13..d7a57e7b71 100644 --- a/src/input_common/gcadapter/gc_adapter.h +++ b/src/input_common/gcadapter/gc_adapter.h @@ -46,17 +46,6 @@ enum class PadAxes : u8 { TriggerRight, Undefined, }; -const struct GCPadConstants { - const u8 MAIN_STICK_CENTER_X = 0x80; - const u8 MAIN_STICK_CENTER_Y = 0x80; - const u8 MAIN_STICK_RADIUS = 0x7f; - const u8 C_STICK_CENTER_X = 0x80; - const u8 C_STICK_CENTER_Y = 0x80; - const u8 C_STICK_RADIUS = 0x7f; - - const u8 TRIGGER_CENTER = 20; - const u8 THRESHOLD = 10; -} pad_constants; struct GCPadStatus { u16 button; // Or-ed PAD_BUTTON_* and PAD_TRIGGER_* bits @@ -67,6 +56,15 @@ struct GCPadStatus { u8 trigger_left; // 0 <= trigger_left <= 255 u8 trigger_right; // 0 <= trigger_right <= 255 + static constexpr u8 MAIN_STICK_CENTER_X = 0x80; + static constexpr u8 MAIN_STICK_CENTER_Y = 0x80; + static constexpr u8 MAIN_STICK_RADIUS = 0x7f; + static constexpr u8 C_STICK_CENTER_X = 0x80; + static constexpr u8 C_STICK_CENTER_Y = 0x80; + static constexpr u8 C_STICK_RADIUS = 0x7f; + static constexpr u8 TRIGGER_CENTER = 20; + static constexpr u8 THRESHOLD = 10; + u8 port; PadAxes axis = PadAxes::Undefined; u8 axis_value = 255; @@ -87,28 +85,22 @@ enum { /// Singleton Adapter class class Adapter { public: - /// For retreiving the singleton instance - static Adapter* GetInstance(); + /// Initialize the GC Adapter capture and read sequence + Adapter(); + /// Close the adapter read thread and release the adapter + ~Adapter(); /// Used for polling void BeginConfiguration(); void EndConfiguration(); std::array, 4>& GetPadQueue(); + const std::array, 4>& GetPadQueue() const; + std::array& GetPadState(); - std::array, 4>& GetPadQueue() const; - std::array& GetPadState() const; + const std::array& GetPadState() const; private: - /// Singleton instance. - static Adapter* adapter_instance; - - /// Initialize the GC Adapter capture and read sequence - Adapter(); - - /// Close the adapter read thread and release the adapter - ~Adapter(); - GCPadStatus CheckStatus(int port, u8 adapter_payload[37]); void PadToState(GCPadStatus pad, GCState& state); diff --git a/src/input_common/gcadapter/gc_poller.cpp b/src/input_common/gcadapter/gc_poller.cpp index ac4126cb62..ad8b4b431b 100644 --- a/src/input_common/gcadapter/gc_poller.cpp +++ b/src/input_common/gcadapter/gc_poller.cpp @@ -14,7 +14,8 @@ namespace InputCommon { class GCButton final : public Input::ButtonDevice { public: - explicit GCButton(int port_, int button_, int axis_, GCAdapter::Adapter* adapter) + explicit GCButton(int port_, int button_, int axis_, + std::shared_ptr adapter) : port(port_), button(button_), gcadapter(adapter) {} ~GCButton() override; @@ -26,13 +27,13 @@ public: private: const int port; const int button; - GCAdapter::Adapter* gcadapter; + std::shared_ptr gcadapter; }; class GCAxisButton final : public Input::ButtonDevice { public: explicit GCAxisButton(int port_, int axis_, float threshold_, bool trigger_if_greater_, - GCAdapter::Adapter* adapter) + std::shared_ptr adapter) : port(port_), axis(axis_), threshold(threshold_), trigger_if_greater(trigger_if_greater_), gcadapter(adapter) {} @@ -49,12 +50,11 @@ private: const int axis; float threshold; bool trigger_if_greater; - GCAdapter::Adapter* gcadapter; + std::shared_ptr gcadapter; }; -GCButtonFactory::GCButtonFactory() { - adapter = GCAdapter::Adapter::GetInstance(); -} +GCButtonFactory::GCButtonFactory(std::shared_ptr adapter_) + : adapter(adapter_) {} GCButton::~GCButton() = default; @@ -171,7 +171,8 @@ void GCButtonFactory::EndConfiguration() { class GCAnalog final : public Input::AnalogDevice { public: - GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_, GCAdapter::Adapter* adapter) + GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_, + std::shared_ptr adapter) : port(port_), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_), gcadapter(adapter) {} float GetAxis(int axis) const { @@ -230,13 +231,12 @@ private: const int axis_y; const float deadzone; mutable std::mutex mutex; - GCAdapter::Adapter* gcadapter; + std::shared_ptr gcadapter; }; /// An analog device factory that creates analog devices from GC Adapter -GCAnalogFactory::GCAnalogFactory() { - adapter = GCAdapter::Adapter::GetInstance(); -}; +GCAnalogFactory::GCAnalogFactory(std::shared_ptr adapter_) + : adapter(adapter_) {} /** * Creates analog device from joystick axes diff --git a/src/input_common/gcadapter/gc_poller.h b/src/input_common/gcadapter/gc_poller.h index 31ff1c1237..d3a56da5be 100644 --- a/src/input_common/gcadapter/gc_poller.h +++ b/src/input_common/gcadapter/gc_poller.h @@ -15,7 +15,7 @@ namespace InputCommon { */ class GCButtonFactory final : public Input::Factory { public: - GCButtonFactory(); + GCButtonFactory(std::shared_ptr adapter_); /** * Creates a button device from a button press @@ -35,14 +35,14 @@ public: } private: - GCAdapter::Adapter* adapter; + std::shared_ptr adapter; bool polling = false; }; /// An analog device factory that creates analog devices from GC Adapter class GCAnalogFactory final : public Input::Factory { public: - GCAnalogFactory(); + GCAnalogFactory(std::shared_ptr adapter_); std::unique_ptr Create(const Common::ParamPackage& params) override; Common::ParamPackage GetNextInput(); @@ -55,7 +55,7 @@ public: } private: - GCAdapter::Adapter* adapter; + std::shared_ptr adapter; int analog_x_axis = -1; int analog_y_axis = -1; int controller_number = -1; diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index 89dddf7cf7..fc399db7e9 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -25,13 +25,15 @@ static std::shared_ptr motion_emu; static std::unique_ptr sdl; #endif static std::unique_ptr udp; +static std::shared_ptr gcadapter; static std::shared_ptr gcbuttons; static std::shared_ptr gcanalog; void Init() { - gcbuttons = std::make_shared(); + gcadapter = std::make_shared(); + gcbuttons = std::make_shared(gcadapter); Input::RegisterFactory("gcpad", gcbuttons); - gcanalog = std::make_shared(); + gcanalog = std::make_shared(gcadapter); Input::RegisterFactory("gcpad", gcanalog); keyboard = std::make_shared(); -- cgit v1.2.3 From 54794273352e92cada75fea687fc26dbba440556 Mon Sep 17 00:00:00 2001 From: Ameer Date: Sun, 21 Jun 2020 23:56:56 -0400 Subject: Tidy up the pointers, use pair over tuple where appropriate --- src/input_common/gcadapter/gc_poller.cpp | 36 +++++++++++++++----------------- src/input_common/gcadapter/gc_poller.h | 6 ++++-- src/input_common/main.cpp | 3 +-- src/input_common/main.h | 1 - 4 files changed, 22 insertions(+), 24 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/gcadapter/gc_poller.cpp b/src/input_common/gcadapter/gc_poller.cpp index ad8b4b431b..be7c600a26 100644 --- a/src/input_common/gcadapter/gc_poller.cpp +++ b/src/input_common/gcadapter/gc_poller.cpp @@ -14,8 +14,7 @@ namespace InputCommon { class GCButton final : public Input::ButtonDevice { public: - explicit GCButton(int port_, int button_, int axis_, - std::shared_ptr adapter) + explicit GCButton(int port_, int button_, int axis_, GCAdapter::Adapter* adapter) : port(port_), button(button_), gcadapter(adapter) {} ~GCButton() override; @@ -27,13 +26,13 @@ public: private: const int port; const int button; - std::shared_ptr gcadapter; + GCAdapter::Adapter* gcadapter; }; class GCAxisButton final : public Input::ButtonDevice { public: explicit GCAxisButton(int port_, int axis_, float threshold_, bool trigger_if_greater_, - std::shared_ptr adapter) + GCAdapter::Adapter* adapter) : port(port_), axis(axis_), threshold(threshold_), trigger_if_greater(trigger_if_greater_), gcadapter(adapter) {} @@ -50,11 +49,11 @@ private: const int axis; float threshold; bool trigger_if_greater; - std::shared_ptr gcadapter; + GCAdapter::Adapter* gcadapter; }; GCButtonFactory::GCButtonFactory(std::shared_ptr adapter_) - : adapter(adapter_) {} + : adapter(std::move(adapter_)) {} GCButton::~GCButton() = default; @@ -75,11 +74,12 @@ std::unique_ptr GCButtonFactory::Create(const Common::Param trigger_if_greater = true; LOG_ERROR(Input, "Unknown direction {}", direction_name); } - return std::make_unique(port, axis, threshold, trigger_if_greater, adapter); + return std::make_unique(port, axis, threshold, trigger_if_greater, + adapter.get()); } std::unique_ptr button = - std::make_unique(port, button_id, params.Get("axis", 0), adapter); + std::make_unique(port, button_id, params.Get("axis", 0), adapter.get()); return std::move(button); } @@ -171,8 +171,7 @@ void GCButtonFactory::EndConfiguration() { class GCAnalog final : public Input::AnalogDevice { public: - GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_, - std::shared_ptr adapter) + GCAnalog(int port_, int axis_x_, int axis_y_, float deadzone_, GCAdapter::Adapter* adapter) : port(port_), axis_x(axis_x_), axis_y(axis_y_), deadzone(deadzone_), gcadapter(adapter) {} float GetAxis(int axis) const { @@ -183,7 +182,7 @@ public: return (gcadapter->GetPadState()[port].axes.at(axis) - 128.0f) / 95.0f; } - std::tuple GetAnalog(int axis_x, int axis_y) const { + std::pair GetAnalog(int axis_x, int axis_y) const { float x = GetAxis(axis_x); float y = GetAxis(axis_y); @@ -196,17 +195,17 @@ public: y /= r; } - return std::make_tuple(x, y); + return {x, y}; } std::tuple GetStatus() const override { const auto [x, y] = GetAnalog(axis_x, axis_y); const float r = std::sqrt((x * x) + (y * y)); if (r > deadzone) { - return std::make_tuple(x / r * (r - deadzone) / (1 - deadzone), - y / r * (r - deadzone) / (1 - deadzone)); + return {x / r * (r - deadzone) / (1 - deadzone), + y / r * (r - deadzone) / (1 - deadzone)}; } - return std::make_tuple(0.0f, 0.0f); + return {0.0f, 0.0f}; } bool GetAnalogDirectionStatus(Input::AnalogDirection direction) const override { @@ -231,12 +230,12 @@ private: const int axis_y; const float deadzone; mutable std::mutex mutex; - std::shared_ptr gcadapter; + GCAdapter::Adapter* gcadapter; }; /// An analog device factory that creates analog devices from GC Adapter GCAnalogFactory::GCAnalogFactory(std::shared_ptr adapter_) - : adapter(adapter_) {} + : adapter(std::move(adapter_)) {} /** * Creates analog device from joystick axes @@ -246,13 +245,12 @@ GCAnalogFactory::GCAnalogFactory(std::shared_ptr adapter_) * - "axis_y": the index of the axis to be bind as y-axis */ std::unique_ptr GCAnalogFactory::Create(const Common::ParamPackage& params) { - const std::string guid = params.Get("guid", "0"); const int port = params.Get("port", 0); const int axis_x = params.Get("axis_x", 0); const int axis_y = params.Get("axis_y", 1); const float deadzone = std::clamp(params.Get("deadzone", 0.0f), 0.0f, .99f); - return std::make_unique(port, axis_x, axis_y, deadzone, adapter); + return std::make_unique(port, axis_x, axis_y, deadzone, adapter.get()); } void GCAnalogFactory::BeginConfiguration() { diff --git a/src/input_common/gcadapter/gc_poller.h b/src/input_common/gcadapter/gc_poller.h index d3a56da5be..e96af7d51a 100644 --- a/src/input_common/gcadapter/gc_poller.h +++ b/src/input_common/gcadapter/gc_poller.h @@ -6,6 +6,7 @@ #include #include "core/frontend/input.h" +#include "input_common/gcadapter/gc_adapter.h" namespace InputCommon { @@ -15,7 +16,7 @@ namespace InputCommon { */ class GCButtonFactory final : public Input::Factory { public: - GCButtonFactory(std::shared_ptr adapter_); + explicit GCButtonFactory(std::shared_ptr adapter_); /** * Creates a button device from a button press @@ -42,7 +43,8 @@ private: /// An analog device factory that creates analog devices from GC Adapter class GCAnalogFactory final : public Input::Factory { public: - GCAnalogFactory(std::shared_ptr adapter_); + explicit GCAnalogFactory(std::shared_ptr adapter_); + std::unique_ptr Create(const Common::ParamPackage& params) override; Common::ParamPackage GetNextInput(); diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index fc399db7e9..827a1a30c1 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -25,12 +25,11 @@ static std::shared_ptr motion_emu; static std::unique_ptr sdl; #endif static std::unique_ptr udp; -static std::shared_ptr gcadapter; static std::shared_ptr gcbuttons; static std::shared_ptr gcanalog; void Init() { - gcadapter = std::make_shared(); + std::shared_ptr gcadapter = std::make_shared(); gcbuttons = std::make_shared(gcadapter); Input::RegisterFactory("gcpad", gcbuttons); gcanalog = std::make_shared(gcadapter); diff --git a/src/input_common/main.h b/src/input_common/main.h index c26222f214..0e32856f6d 100644 --- a/src/input_common/main.h +++ b/src/input_common/main.h @@ -7,7 +7,6 @@ #include #include #include -#include "input_common/gcadapter/gc_adapter.h" #include "input_common/gcadapter/gc_poller.h" namespace Common { -- cgit v1.2.3 From 14bb562028682d731c911240f68e8de7e5d2731d Mon Sep 17 00:00:00 2001 From: ameerj <52414509+ameerj@users.noreply.github.com> Date: Mon, 22 Jun 2020 10:40:27 -0400 Subject: Update src/input_common/main.cpp Co-authored-by: LC update libusb submodule (hopefully windows build error fixed) --- externals/libusb | 2 +- src/input_common/main.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/externals/libusb b/externals/libusb index c5085fc4eb..71c3083fdd 160000 --- a/externals/libusb +++ b/externals/libusb @@ -1 +1 @@ -Subproject commit c5085fc4eb1a83e6a8921a43b8d77f162b9e3b41 +Subproject commit 71c3083fdd07a5a8c30a469800563bfbd9f9d4ad diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index 827a1a30c1..a9572c23cf 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -29,7 +29,7 @@ static std::shared_ptr gcbuttons; static std::shared_ptr gcanalog; void Init() { - std::shared_ptr gcadapter = std::make_shared(); + auto gcadapter = std::make_shared(); gcbuttons = std::make_shared(gcadapter); Input::RegisterFactory("gcpad", gcbuttons); gcanalog = std::make_shared(gcadapter); -- cgit v1.2.3 From ef0b52563d6e1278c0bb9270110dcf51941a9288 Mon Sep 17 00:00:00 2001 From: Ameer Date: Tue, 23 Jun 2020 12:47:58 -0400 Subject: Fix deallocation of GC Adapter --- src/input_common/gcadapter/gc_adapter.cpp | 10 +++++++--- src/input_common/gcadapter/gc_adapter.h | 1 - src/input_common/main.cpp | 3 +++ 3 files changed, 10 insertions(+), 4 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/gcadapter/gc_adapter.cpp b/src/input_common/gcadapter/gc_adapter.cpp index 745f1be276..887cde263e 100644 --- a/src/input_common/gcadapter/gc_adapter.cpp +++ b/src/input_common/gcadapter/gc_adapter.cpp @@ -130,6 +130,7 @@ void Adapter::Read() { if (payload_size != sizeof(controller_payload_copy) || controller_payload_copy[0] != LIBUSB_DT_HID) { + // TODO: It might be worthwhile to Shutdown GC Adapter if we encounter errors here LOG_ERROR(Input, "error reading payload (size: %d, type: %02x)", payload_size, controller_payload_copy[0]); } else { @@ -200,6 +201,7 @@ void Adapter::StartScanThread() { } void Adapter::StopScanThread() { + detect_thread_running = false; detect_thread.join(); } @@ -298,8 +300,6 @@ void Adapter::GetGCEndpoint(libusb_device* device) { Adapter::~Adapter() { StopScanThread(); Reset(); - - current_status = NO_ADAPTER_DETECTED; } void Adapter::Reset() { @@ -312,11 +312,11 @@ void Adapter::Reset() { } if (adapter_thread_running) { + adapter_thread_running = false; adapter_input_thread.join(); } adapter_controllers_status.fill(ControllerTypes::None); - current_status = NO_ADAPTER_DETECTED; if (usb_adapter_handle) { @@ -324,6 +324,10 @@ void Adapter::Reset() { libusb_close(usb_adapter_handle); usb_adapter_handle = nullptr; } + + if (libusb_ctx) { + libusb_exit(libusb_ctx); + } } bool Adapter::DeviceConnected(int port) { diff --git a/src/input_common/gcadapter/gc_adapter.h b/src/input_common/gcadapter/gc_adapter.h index ff0202e3ba..7aed0b4809 100644 --- a/src/input_common/gcadapter/gc_adapter.h +++ b/src/input_common/gcadapter/gc_adapter.h @@ -82,7 +82,6 @@ enum { ADAPTER_DETECTED = 1, }; -/// Singleton Adapter class class Adapter { public: /// Initialize the GC Adapter capture and read sequence diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index a9572c23cf..f13420b38f 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -59,7 +59,10 @@ void Shutdown() { #endif udp.reset(); Input::UnregisterFactory("gcpad"); + Input::UnregisterFactory("gcpad"); + gcbuttons.reset(); + gcanalog.reset(); } Keyboard* GetKeyboard() { -- cgit v1.2.3 From 33c08afba98538a2953e591ba783a991a752f547 Mon Sep 17 00:00:00 2001 From: Ameer Date: Thu, 2 Jul 2020 16:51:16 -0400 Subject: Fix unnecessary diffs --- src/input_common/keyboard.cpp | 3 +- src/input_common/main.cpp | 2 + src/input_common/sdl/sdl_impl.cpp | 1 - src/yuzu/configuration/configure_input_player.cpp | 50 +++++++++++------------ 4 files changed, 27 insertions(+), 29 deletions(-) (limited to 'src/input_common/main.cpp') diff --git a/src/input_common/keyboard.cpp b/src/input_common/keyboard.cpp index eb6c3112b8..afb8e6612c 100644 --- a/src/input_common/keyboard.cpp +++ b/src/input_common/keyboard.cpp @@ -49,9 +49,8 @@ public: void ChangeKeyStatus(int key_code, bool pressed) { std::lock_guard guard{mutex}; for (const KeyButtonPair& pair : list) { - if (pair.key_code == key_code) { + if (pair.key_code == key_code) pair.key_button->status.store(pressed); - } } } diff --git a/src/input_common/main.cpp b/src/input_common/main.cpp index f13420b38f..fd0af10193 100644 --- a/src/input_common/main.cpp +++ b/src/input_common/main.cpp @@ -45,6 +45,7 @@ void Init() { #ifdef HAVE_SDL2 sdl = SDL::Init(); #endif + udp = CemuhookUDP::Init(); } @@ -111,6 +112,7 @@ std::vector> GetPollers(DeviceType type) { #ifdef HAVE_SDL2 pollers = sdl->GetPollers(type); #endif + return pollers; } diff --git a/src/input_common/sdl/sdl_impl.cpp b/src/input_common/sdl/sdl_impl.cpp index 6b264f2a6f..675b477fa3 100644 --- a/src/input_common/sdl/sdl_impl.cpp +++ b/src/input_common/sdl/sdl_impl.cpp @@ -444,7 +444,6 @@ private: class SDLAnalogFactory final : public Input::Factory { public: explicit SDLAnalogFactory(SDLState& state_) : state(state_) {} - /** * Creates analog device from joystick axes * @param params contains parameters for creating the device: diff --git a/src/yuzu/configuration/configure_input_player.cpp b/src/yuzu/configuration/configure_input_player.cpp index 49b8c8386a..00433926d3 100644 --- a/src/yuzu/configuration/configure_input_player.cpp +++ b/src/yuzu/configuration/configure_input_player.cpp @@ -281,25 +281,24 @@ ConfigureInputPlayer::ConfigureInputPlayer(QWidget* parent, std::size_t player_i button->setContextMenuPolicy(Qt::CustomContextMenu); connect(button, &QPushButton::clicked, [=] { - HandleClick( - button_map[button_id], - [=](Common::ParamPackage params) { - // Workaround for ZL & ZR for analog triggers like on XBOX controllors. - // Analog triggers (from controllers like the XBOX controller) would not - // work due to a different range of their signals (from 0 to 255 on - // analog triggers instead of -32768 to 32768 on analog joysticks). The - // SDL driver misinterprets analog triggers as analog joysticks. - // TODO: reinterpret the signal range for analog triggers to map the - // values correctly. This is required for the correct emulation of the - // analog triggers of the GameCube controller. - if (button_id == Settings::NativeButton::ZL || - button_id == Settings::NativeButton::ZR) { - params.Set("direction", "+"); - params.Set("threshold", "0.5"); - } - buttons_param[button_id] = std::move(params); - }, - InputCommon::Polling::DeviceType::Button); + HandleClick(button_map[button_id], + [=](Common::ParamPackage params) { + // Workaround for ZL & ZR for analog triggers like on XBOX controllors. + // Analog triggers (from controllers like the XBOX controller) would not + // work due to a different range of their signals (from 0 to 255 on + // analog triggers instead of -32768 to 32768 on analog joysticks). The + // SDL driver misinterprets analog triggers as analog joysticks. + // TODO: reinterpret the signal range for analog triggers to map the + // values correctly. This is required for the correct emulation of the + // analog triggers of the GameCube controller. + if (button_id == Settings::NativeButton::ZL || + button_id == Settings::NativeButton::ZR) { + params.Set("direction", "+"); + params.Set("threshold", "0.5"); + } + buttons_param[button_id] = std::move(params); + }, + InputCommon::Polling::DeviceType::Button); }); connect(button, &QPushButton::customContextMenuRequested, [=](const QPoint& menu_location) { QMenu context_menu; @@ -325,13 +324,12 @@ ConfigureInputPlayer::ConfigureInputPlayer(QWidget* parent, std::size_t player_i analog_button->setContextMenuPolicy(Qt::CustomContextMenu); connect(analog_button, &QPushButton::clicked, [=]() { - HandleClick( - analog_map_buttons[analog_id][sub_button_id], - [=](const Common::ParamPackage& params) { - SetAnalogButton(params, analogs_param[analog_id], - analog_sub_buttons[sub_button_id]); - }, - InputCommon::Polling::DeviceType::Button); + HandleClick(analog_map_buttons[analog_id][sub_button_id], + [=](const Common::ParamPackage& params) { + SetAnalogButton(params, analogs_param[analog_id], + analog_sub_buttons[sub_button_id]); + }, + InputCommon::Polling::DeviceType::Button); }); connect(analog_button, &QPushButton::customContextMenuRequested, [=](const QPoint& menu_location) { -- cgit v1.2.3