diff --git a/source/ControllerSwitch/SwitchAbstractedPadHandler.cpp b/source/ControllerSwitch/SwitchAbstractedPadHandler.cpp index 1410fa4..836a623 100644 --- a/source/ControllerSwitch/SwitchAbstractedPadHandler.cpp +++ b/source/ControllerSwitch/SwitchAbstractedPadHandler.cpp @@ -15,47 +15,39 @@ SwitchAbstractedPadHandler::~SwitchAbstractedPadHandler() Result SwitchAbstractedPadHandler::Initialize() { - Result rc = m_controllerHandler.Initialize(); - if (R_FAILED(rc)) - return rc; + R_TRY(m_controller->Initialize()); if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_NOTHING)) - return rc; + return 0; - rc = InitAbstractedPadState(); - if (R_FAILED(rc)) - return rc; + R_TRY(InitAbstractedPadState()); - if (DoesControllerSupport(m_controllerHandler.GetController()->GetType(), SUPPORTS_PAIRING)) + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_PAIRING)) { - rc = InitOutputThread(); - if (R_FAILED(rc)) - return rc; + R_TRY(InitOutputThread()); } - rc = InitInputThread(); - if (R_FAILED(rc)) - return rc; + R_TRY(InitInputThread()); - return rc; + return 0; } void SwitchAbstractedPadHandler::Exit() { if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_NOTHING)) { - m_controllerHandler.Exit(); + m_controller->Exit(); return; } ExitInputThread(); ExitOutputThread(); - m_controllerHandler.Exit(); + m_controller->Exit(); ExitAbstractedPadState(); } //Used to give out unique ids to abstracted pads -static std::array uniqueIDs{false}; +static std::array uniqueIDs{}; static s8 getUniqueId() { @@ -137,7 +129,7 @@ void SwitchAbstractedPadHandler::FillAbstractedState(const NormalizedButtonData daxis_y += data.buttons[14] ? -1.0f : 0.0f; //DDOWN daxis_x += data.buttons[15] ? -1.0f : 0.0f; //DLEFT - m_controllerHandler.ConvertAxisToSwitchAxis(daxis_x, daxis_y, 0, &m_state.state.joysticks[JOYSTICK_LEFT].dx, &m_state.state.joysticks[JOYSTICK_LEFT].dy); + ConvertAxisToSwitchAxis(daxis_x, daxis_y, 0, &m_state.state.joysticks[JOYSTICK_LEFT].dx, &m_state.state.joysticks[JOYSTICK_LEFT].dy); } else { @@ -146,10 +138,10 @@ void SwitchAbstractedPadHandler::FillAbstractedState(const NormalizedButtonData m_state.state.buttons |= (data.buttons[14] ? KEY_DDOWN : 0); m_state.state.buttons |= (data.buttons[15] ? KEY_DLEFT : 0); - m_controllerHandler.ConvertAxisToSwitchAxis(data.sticks[0].axis_x, data.sticks[0].axis_y, 0, &m_state.state.joysticks[JOYSTICK_LEFT].dx, &m_state.state.joysticks[JOYSTICK_LEFT].dy); + ConvertAxisToSwitchAxis(data.sticks[0].axis_x, data.sticks[0].axis_y, 0, &m_state.state.joysticks[JOYSTICK_LEFT].dx, &m_state.state.joysticks[JOYSTICK_LEFT].dy); } - m_controllerHandler.ConvertAxisToSwitchAxis(data.sticks[1].axis_x, data.sticks[1].axis_y, 0, &m_state.state.joysticks[JOYSTICK_RIGHT].dx, &m_state.state.joysticks[JOYSTICK_RIGHT].dy); + ConvertAxisToSwitchAxis(data.sticks[1].axis_x, data.sticks[1].axis_y, 0, &m_state.state.joysticks[JOYSTICK_RIGHT].dx, &m_state.state.joysticks[JOYSTICK_RIGHT].dy); m_state.state.buttons |= (data.buttons[16] ? KEY_CAPTURE : 0); m_state.state.buttons |= (data.buttons[17] ? KEY_HOME : 0); @@ -175,10 +167,10 @@ void SwitchAbstractedPadHandler::UpdateInput() void SwitchAbstractedPadHandler::UpdateOutput() { - if (R_SUCCEEDED(m_controllerHandler.GetController()->OutputBuffer())) + if (R_SUCCEEDED(m_controller->OutputBuffer())) return; - if (DoesControllerSupport(m_controllerHandler.GetController()->GetType(), SUPPORTS_RUMBLE)) + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_RUMBLE)) { Result rc; HidVibrationValue value; diff --git a/source/ControllerSwitch/SwitchAbstractedPadHandler.h b/source/ControllerSwitch/SwitchAbstractedPadHandler.h index d84fc0a..df48f67 100644 --- a/source/ControllerSwitch/SwitchAbstractedPadHandler.h +++ b/source/ControllerSwitch/SwitchAbstractedPadHandler.h @@ -2,7 +2,6 @@ #include "switch.h" #include "IController.h" -#include "SwitchControllerHandler.h" #include "SwitchVirtualGamepadHandler.h" //Wrapper for AbstractedPad for switch versions [5.0.0 - 8.1.0] diff --git a/source/ControllerSwitch/SwitchControllerHandler.cpp b/source/ControllerSwitch/SwitchControllerHandler.cpp deleted file mode 100644 index 79b7293..0000000 --- a/source/ControllerSwitch/SwitchControllerHandler.cpp +++ /dev/null @@ -1,52 +0,0 @@ -#include "SwitchControllerHandler.h" -#include - -static_assert( - JOYSTICK_MAX == 32767 && JOYSTICK_MIN == -32767, - "JOYSTICK_MAX and/or JOYSTICK_MIN has incorrect values. Update libnx" -); - -SwitchControllerHandler::SwitchControllerHandler(std::unique_ptr &&controller) - : m_controller(std::move(controller)) -{ -} - -SwitchControllerHandler::~SwitchControllerHandler() -{ -} - -Result SwitchControllerHandler::Initialize() -{ - Result rc = m_controller->Initialize(); - if (R_FAILED(rc)) - return rc; - return rc; -} - -void SwitchControllerHandler::Exit() -{ - m_controller->Exit(); -} - -void SwitchControllerHandler::ConvertAxisToSwitchAxis(float x, float y, float deadzone, s32 *x_out, s32 *y_out) -{ - float floatRange = 2.0f; - //JOYSTICK_MAX is 1 above and JOYSTICK_MIN is 1 below acceptable joystick values, causing crashes on various games including Xenoblade Chronicles 2 and Resident Evil 4 - float newRange = (JOYSTICK_MAX - JOYSTICK_MIN); - - *x_out = (((x + 1.0f) * newRange) / floatRange) + JOYSTICK_MIN; - *y_out = (((y + 1.0f) * newRange) / floatRange) + JOYSTICK_MIN; - /* - OldRange = (OldMax - OldMin) - NewRange = (NewMax - NewMin) - NewValue = (((OldValue - OldMin) * NewRange) / OldRange) + NewMin - */ -} - -Result SwitchControllerHandler::SetControllerVibration(float strong_mag, float weak_mag) -{ - strong_mag = std::max(0.0f, std::min(strong_mag, 1.0f)); - weak_mag = std::max(0.0f, std::min(weak_mag, 1.0f)); - - return m_controller->SetRumble(static_cast(strong_mag * 255.0f), static_cast(weak_mag * 255.0f)); -} \ No newline at end of file diff --git a/source/ControllerSwitch/SwitchControllerHandler.h b/source/ControllerSwitch/SwitchControllerHandler.h deleted file mode 100644 index c3016b4..0000000 --- a/source/ControllerSwitch/SwitchControllerHandler.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once - -#include "switch.h" -#include "IController.h" - -class SwitchControllerHandler -{ -private: - std::unique_ptr m_controller; - -public: - //Initialize the class with specified controller - SwitchControllerHandler(std::unique_ptr &&controller); - ~SwitchControllerHandler(); - - //Initialize controller and open a separate thread for input - Result Initialize(); - //Clean up everything associated with the controller, reset device, close threads, etc - void Exit(); - - void ConvertAxisToSwitchAxis(float x, float y, float deadzone, s32 *x_out, s32 *y_out); - - Result SetControllerVibration(float strong_mag, float weak_mag); - - //Get the raw controller pointer - inline IController *GetController() { return m_controller.get(); } -}; \ No newline at end of file diff --git a/source/ControllerSwitch/SwitchHDLHandler.cpp b/source/ControllerSwitch/SwitchHDLHandler.cpp index 8b91026..3d21079 100644 --- a/source/ControllerSwitch/SwitchHDLHandler.cpp +++ b/source/ControllerSwitch/SwitchHDLHandler.cpp @@ -14,42 +14,35 @@ SwitchHDLHandler::~SwitchHDLHandler() Result SwitchHDLHandler::Initialize() { - Result rc = m_controllerHandler.Initialize(); - if (R_FAILED(rc)) - return rc; - if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_NOTHING)) - return rc; + R_TRY(m_controller->Initialize()); - rc = InitHdlState(); - if (R_FAILED(rc)) - return rc; + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_NOTHING)) + return 0; - if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_PAIRING)) + R_TRY(InitHdlState()); + + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_PAIRING)) { - rc = InitOutputThread(); - if (R_FAILED(rc)) - return rc; + R_TRY(InitOutputThread()); } - rc = InitInputThread(); - if (R_FAILED(rc)) - return rc; + R_TRY(InitInputThread()); - return rc; + return 0; } void SwitchHDLHandler::Exit() { - if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_NOTHING)) + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_NOTHING)) { - m_controllerHandler.Exit(); + m_controller->Exit(); return; } ExitInputThread(); ExitOutputThread(); - m_controllerHandler.Exit(); + m_controller->Exit(); ExitHdlState(); } @@ -63,7 +56,7 @@ Result SwitchHDLHandler::InitHdlState() m_deviceInfo.deviceType = HidDeviceType_FullKey15; m_deviceInfo.npadInterfaceType = NpadInterfaceType_USB; // Set the controller colors. The grip colors are for Pro-Controller on [9.0.0+]. - ControllerConfig *config = GetController()->GetConfig(); + ControllerConfig *config = m_controller->GetConfig(); m_deviceInfo.singleColorBody = config->bodyColor.rgbaValue; m_deviceInfo.singleColorButtons = config->buttonsColor.rgbaValue; m_deviceInfo.colorLeftGrip = config->leftGripColor.rgbaValue; @@ -75,7 +68,7 @@ Result SwitchHDLHandler::InitHdlState() m_hdlState.joysticks[JOYSTICK_RIGHT].dx = 0x5678; m_hdlState.joysticks[JOYSTICK_RIGHT].dy = -0x5678; - if (GetController()->IsControllerActive()) + if (m_controller->IsControllerActive()) return hiddbgAttachHdlsVirtualDevice(&m_hdlHandle, &m_deviceInfo); return 0; @@ -122,7 +115,7 @@ void SwitchHDLHandler::FillHdlState(const NormalizedButtonData &data) m_hdlState.buttons |= (data.buttons[10] ? KEY_MINUS : 0); m_hdlState.buttons |= (data.buttons[11] ? KEY_PLUS : 0); - ControllerConfig *config = GetController()->GetConfig(); + ControllerConfig *config = m_controller->GetConfig(); if (config && config->swapDPADandLSTICK) { @@ -146,7 +139,7 @@ void SwitchHDLHandler::FillHdlState(const NormalizedButtonData &data) daxis_x *= ratio; daxis_y *= ratio; - m_controllerHandler.ConvertAxisToSwitchAxis(daxis_x, daxis_y, 0, &m_hdlState.joysticks[JOYSTICK_LEFT].dx, &m_hdlState.joysticks[JOYSTICK_LEFT].dy); + ConvertAxisToSwitchAxis(daxis_x, daxis_y, 0, &m_hdlState.joysticks[JOYSTICK_LEFT].dx, &m_hdlState.joysticks[JOYSTICK_LEFT].dy); } else { @@ -155,10 +148,10 @@ void SwitchHDLHandler::FillHdlState(const NormalizedButtonData &data) m_hdlState.buttons |= (data.buttons[14] ? KEY_DDOWN : 0); m_hdlState.buttons |= (data.buttons[15] ? KEY_DLEFT : 0); - m_controllerHandler.ConvertAxisToSwitchAxis(data.sticks[0].axis_x, data.sticks[0].axis_y, 0, &m_hdlState.joysticks[JOYSTICK_LEFT].dx, &m_hdlState.joysticks[JOYSTICK_LEFT].dy); + ConvertAxisToSwitchAxis(data.sticks[0].axis_x, data.sticks[0].axis_y, 0, &m_hdlState.joysticks[JOYSTICK_LEFT].dx, &m_hdlState.joysticks[JOYSTICK_LEFT].dy); } - m_controllerHandler.ConvertAxisToSwitchAxis(data.sticks[1].axis_x, data.sticks[1].axis_y, 0, &m_hdlState.joysticks[JOYSTICK_RIGHT].dx, &m_hdlState.joysticks[JOYSTICK_RIGHT].dy); + ConvertAxisToSwitchAxis(data.sticks[1].axis_x, data.sticks[1].axis_y, 0, &m_hdlState.joysticks[JOYSTICK_RIGHT].dx, &m_hdlState.joysticks[JOYSTICK_RIGHT].dy); m_hdlState.buttons |= (data.buttons[16] ? KEY_CAPTURE : 0); m_hdlState.buttons |= (data.buttons[17] ? KEY_HOME : 0); @@ -167,19 +160,19 @@ void SwitchHDLHandler::FillHdlState(const NormalizedButtonData &data) void SwitchHDLHandler::UpdateInput() { // We process any input packets here. If it fails, return and try again - Result rc = GetController()->GetInput(); + Result rc = m_controller->GetInput(); if (R_FAILED(rc)) return; // This is a check for controllers that can prompt themselves to go inactive - e.g. wireless Xbox 360 controllers - if (!GetController()->IsControllerActive()) + if (!m_controller->IsControllerActive()) { hiddbgDetachHdlsVirtualDevice(m_hdlHandle); } else { // We get the button inputs from the input packet and update the state of our controller - FillHdlState(GetController()->GetNormalizedButtonData()); + FillHdlState(m_controller->GetNormalizedButtonData()); rc = UpdateHdlState(); if (R_FAILED(rc)) return; @@ -189,17 +182,17 @@ void SwitchHDLHandler::UpdateInput() void SwitchHDLHandler::UpdateOutput() { // Process a single output packet from a buffer - if (R_SUCCEEDED(GetController()->OutputBuffer())) + if (R_SUCCEEDED(m_controller->OutputBuffer())) return; // Process rumble values if supported - if (DoesControllerSupport(GetController()->GetType(), SUPPORTS_RUMBLE)) + if (DoesControllerSupport(m_controller->GetType(), SUPPORTS_RUMBLE)) { Result rc; HidVibrationValue value; rc = hidGetActualVibrationValue(&m_vibrationDeviceHandle, &value); if (R_SUCCEEDED(rc)) - GetController()->SetRumble(static_cast(value.amp_high * 255.0f), static_cast(value.amp_low * 255.0f)); + m_controller->SetRumble(static_cast(value.amp_high * 255.0f), static_cast(value.amp_low * 255.0f)); } svcSleepThread(1e+7L); diff --git a/source/ControllerSwitch/SwitchHDLHandler.h b/source/ControllerSwitch/SwitchHDLHandler.h index bf0ac9e..a828ced 100644 --- a/source/ControllerSwitch/SwitchHDLHandler.h +++ b/source/ControllerSwitch/SwitchHDLHandler.h @@ -2,7 +2,6 @@ #include "switch.h" #include "IController.h" -#include "SwitchControllerHandler.h" #include "SwitchVirtualGamepadHandler.h" //Wrapper for HDL functions for switch versions [7.0.0+] diff --git a/source/ControllerSwitch/SwitchVirtualGamepadHandler.cpp b/source/ControllerSwitch/SwitchVirtualGamepadHandler.cpp index a284b8e..cb16ff3 100644 --- a/source/ControllerSwitch/SwitchVirtualGamepadHandler.cpp +++ b/source/ControllerSwitch/SwitchVirtualGamepadHandler.cpp @@ -1,7 +1,7 @@ #include "SwitchVirtualGamepadHandler.h" SwitchVirtualGamepadHandler::SwitchVirtualGamepadHandler(std::unique_ptr &&controller) - : m_controllerHandler(std::move(controller)) + : m_controller(std::move(controller)) { } @@ -11,25 +11,28 @@ SwitchVirtualGamepadHandler::~SwitchVirtualGamepadHandler() Result SwitchVirtualGamepadHandler::Initialize() { - return 0; + return m_controller->Initialize(); } void SwitchVirtualGamepadHandler::Exit() { + m_controller->Exit(); } void SwitchVirtualGamepadHandler::InputThreadLoop(void *handler) { - do { + do + { static_cast(handler)->UpdateInput(); - } while (static_cast(handler)->m_inputThreadIsRunning); + } while (static_cast(handler)->m_inputThreadIsRunning); } void SwitchVirtualGamepadHandler::OutputThreadLoop(void *handler) { - do { - static_cast(handler)->UpdateOutput(); - } while (static_cast(handler)->m_outputThreadIsRunning); + do + { + static_cast(handler)->UpdateOutput(); + } while (static_cast(handler)->m_outputThreadIsRunning); } Result SwitchVirtualGamepadHandler::InitInputThread() @@ -58,4 +61,30 @@ void SwitchVirtualGamepadHandler::ExitOutputThread() m_outputThreadIsRunning = false; m_outputThread.CancelSynchronization(); m_outputThread.Join(); +} + +static_assert(JOYSTICK_MAX == 32767 && JOYSTICK_MIN == -32767, + "JOYSTICK_MAX and/or JOYSTICK_MIN has incorrect values. Update libnx"); + +void SwitchVirtualGamepadHandler::ConvertAxisToSwitchAxis(float x, float y, float deadzone, s32 *x_out, s32 *y_out) +{ + float floatRange = 2.0f; + //JOYSTICK_MAX is 1 above and JOYSTICK_MIN is 1 below acceptable joystick values, causing crashes on various games including Xenoblade Chronicles 2 and Resident Evil 4 + float newRange = (JOYSTICK_MAX - JOYSTICK_MIN); + + *x_out = (((x + 1.0f) * newRange) / floatRange) + JOYSTICK_MIN; + *y_out = (((y + 1.0f) * newRange) / floatRange) + JOYSTICK_MIN; + /* + OldRange = (OldMax - OldMin) + NewRange = (NewMax - NewMin) + NewValue = (((OldValue - OldMin) * NewRange) / OldRange) + NewMin + */ +} + +Result SwitchVirtualGamepadHandler::SetControllerVibration(float strong_mag, float weak_mag) +{ + strong_mag = std::max(0.0f, std::min(strong_mag, 1.0f)); + weak_mag = std::max(0.0f, std::min(weak_mag, 1.0f)); + + return m_controller->SetRumble(static_cast(strong_mag * 255.0f), static_cast(weak_mag * 255.0f)); } \ No newline at end of file diff --git a/source/ControllerSwitch/SwitchVirtualGamepadHandler.h b/source/ControllerSwitch/SwitchVirtualGamepadHandler.h index 10a45f2..4905c02 100644 --- a/source/ControllerSwitch/SwitchVirtualGamepadHandler.h +++ b/source/ControllerSwitch/SwitchVirtualGamepadHandler.h @@ -1,7 +1,6 @@ #pragma once #include "switch.h" #include "IController.h" -#include "SwitchControllerHandler.h" #include //This class is a base class for SwitchHDLHandler and SwitchAbstractedPaadHandler. @@ -9,7 +8,7 @@ class SwitchVirtualGamepadHandler { protected: u32 m_vibrationDeviceHandle; - SwitchControllerHandler m_controllerHandler; + std::unique_ptr m_controller; ams::os::StaticThread<0x1'000> m_inputThread; ams::os::StaticThread<0x1'000> m_outputThread; @@ -44,8 +43,11 @@ public: //The function to call indefinitely by the output thread virtual void UpdateOutput() = 0; - //Get the raw controller handler pointer - inline SwitchControllerHandler *GetControllerHandler() { return &m_controllerHandler; } - inline IController *GetController() { return m_controllerHandler.GetController(); } + void ConvertAxisToSwitchAxis(float x, float y, float deadzone, s32 *x_out, s32 *y_out); + + Result SetControllerVibration(float strong_mag, float weak_mag); + + //Get the raw controller pointer + inline IController *GetController() { return m_controller.get(); } inline u32 *GetVibrationHandle() { return &m_vibrationDeviceHandle; } }; \ No newline at end of file