summaryrefslogtreecommitdiffstats
path: root/src/core/hle/service/hid
diff options
context:
space:
mode:
Diffstat (limited to 'src/core/hle/service/hid')
-rw-r--r--src/core/hle/service/hid/controllers/npad.cpp111
-rw-r--r--src/core/hle/service/hid/controllers/npad.h3
-rw-r--r--src/core/hle/service/hid/errors.h2
-rw-r--r--src/core/hle/service/hid/hid.cpp6
4 files changed, 57 insertions, 65 deletions
diff --git a/src/core/hle/service/hid/controllers/npad.cpp b/src/core/hle/service/hid/controllers/npad.cpp
index 5df49d22f..4095a0a3c 100644
--- a/src/core/hle/service/hid/controllers/npad.cpp
+++ b/src/core/hle/service/hid/controllers/npad.cpp
@@ -1275,77 +1275,66 @@ ResultCode Controller_NPad::GetSixAxisFusionParameters(
return ResultSuccess;
}
-void Controller_NPad::MergeSingleJoyAsDualJoy(Core::HID::NpadIdType npad_id_1,
- Core::HID::NpadIdType npad_id_2) {
+ResultCode Controller_NPad::MergeSingleJoyAsDualJoy(Core::HID::NpadIdType npad_id_1,
+ Core::HID::NpadIdType npad_id_2) {
if (!IsNpadIdValid(npad_id_1) || !IsNpadIdValid(npad_id_2)) {
LOG_ERROR(Service_HID, "Invalid NpadIdType npad_id_1:{}, npad_id_2:{}", npad_id_1,
npad_id_2);
- return;
+ return InvalidNpadId;
}
auto& controller_1 = GetControllerFromNpadIdType(npad_id_1);
auto& controller_2 = GetControllerFromNpadIdType(npad_id_2);
- const auto controller_style_1 = controller_1.device->GetNpadStyleIndex();
- const auto controller_style_2 = controller_2.device->GetNpadStyleIndex();
- bool merge_controllers = false;
+ auto controller_style_1 = controller_1.device->GetNpadStyleIndex();
+ auto controller_style_2 = controller_2.device->GetNpadStyleIndex();
+
+ // Simplify this code by converting dualjoycon with only a side connected to single joycons
+ if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual) {
+ if (controller_1.is_dual_left_connected && !controller_1.is_dual_right_connected) {
+ controller_style_1 = Core::HID::NpadStyleIndex::JoyconLeft;
+ }
+ if (!controller_1.is_dual_left_connected && controller_1.is_dual_right_connected) {
+ controller_style_1 = Core::HID::NpadStyleIndex::JoyconRight;
+ }
+ }
+ if (controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual) {
+ if (controller_2.is_dual_left_connected && !controller_2.is_dual_right_connected) {
+ controller_style_2 = Core::HID::NpadStyleIndex::JoyconLeft;
+ }
+ if (!controller_2.is_dual_left_connected && controller_2.is_dual_right_connected) {
+ controller_style_2 = Core::HID::NpadStyleIndex::JoyconRight;
+ }
+ }
- // If the controllers at both npad indices form a pair of left and right joycons, merge them.
- // Otherwise, do nothing.
+ // Invalid merge errors
+ if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual ||
+ controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual) {
+ return NpadIsDualJoycon;
+ }
if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconLeft &&
+ controller_style_2 == Core::HID::NpadStyleIndex::JoyconLeft) {
+ return NpadIsSameType;
+ }
+ if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconRight &&
controller_style_2 == Core::HID::NpadStyleIndex::JoyconRight) {
- merge_controllers = true;
- }
- if (controller_style_2 == Core::HID::NpadStyleIndex::JoyconLeft &&
- controller_style_1 == Core::HID::NpadStyleIndex::JoyconRight) {
- merge_controllers = true;
- }
- if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_2 == Core::HID::NpadStyleIndex::JoyconRight &&
- controller_1.is_dual_left_connected && !controller_1.is_dual_right_connected) {
- merge_controllers = true;
- }
- if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_2 == Core::HID::NpadStyleIndex::JoyconLeft &&
- !controller_1.is_dual_left_connected && controller_1.is_dual_right_connected) {
- merge_controllers = true;
- }
- if (controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_1 == Core::HID::NpadStyleIndex::JoyconRight &&
- controller_2.is_dual_left_connected && !controller_2.is_dual_right_connected) {
- merge_controllers = true;
- }
- if (controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_1 == Core::HID::NpadStyleIndex::JoyconLeft &&
- !controller_2.is_dual_left_connected && controller_2.is_dual_right_connected) {
- merge_controllers = true;
- }
- if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_1.is_dual_left_connected && !controller_1.is_dual_right_connected &&
- !controller_2.is_dual_left_connected && controller_2.is_dual_right_connected) {
- merge_controllers = true;
- }
- if (controller_style_1 == Core::HID::NpadStyleIndex::JoyconDual &&
- controller_style_2 == Core::HID::NpadStyleIndex::JoyconDual &&
- !controller_1.is_dual_left_connected && controller_1.is_dual_right_connected &&
- controller_2.is_dual_left_connected && !controller_2.is_dual_right_connected) {
- merge_controllers = true;
- }
-
- if (merge_controllers) {
- // Disconnect the joycon at the second id and connect the dual joycon at the first index.
- DisconnectNpad(npad_id_2);
- controller_1.is_dual_left_connected = true;
- controller_1.is_dual_right_connected = true;
- AddNewControllerAt(Core::HID::NpadStyleIndex::JoyconDual, npad_id_1);
- return;
+ return NpadIsSameType;
+ }
+
+ // These exceptions are handled as if they where dual joycon
+ if (controller_style_1 != Core::HID::NpadStyleIndex::JoyconLeft &&
+ controller_style_1 != Core::HID::NpadStyleIndex::JoyconRight) {
+ return NpadIsDualJoycon;
+ }
+ if (controller_style_2 != Core::HID::NpadStyleIndex::JoyconLeft &&
+ controller_style_2 != Core::HID::NpadStyleIndex::JoyconRight) {
+ return NpadIsDualJoycon;
}
- LOG_WARNING(Service_HID,
- "Controllers can't be merged npad_id_1:{}, npad_id_2:{}, type_1:{}, type_2:{}, "
- "dual_1(left/right):{}/{}, dual_2(left/right):{}/{}",
- npad_id_1, npad_id_2, controller_1.device->GetNpadStyleIndex(),
- controller_2.device->GetNpadStyleIndex(), controller_1.is_dual_left_connected,
- controller_1.is_dual_right_connected, controller_2.is_dual_left_connected,
- controller_2.is_dual_right_connected);
+
+ // Disconnect the joycon at the second id and connect the dual joycon at the first index.
+ DisconnectNpad(npad_id_2);
+ controller_1.is_dual_left_connected = true;
+ controller_1.is_dual_right_connected = true;
+ AddNewControllerAt(Core::HID::NpadStyleIndex::JoyconDual, npad_id_1);
+ return ResultSuccess;
}
void Controller_NPad::StartLRAssignmentMode() {
diff --git a/src/core/hle/service/hid/controllers/npad.h b/src/core/hle/service/hid/controllers/npad.h
index f03e9294d..5305e8cf8 100644
--- a/src/core/hle/service/hid/controllers/npad.h
+++ b/src/core/hle/service/hid/controllers/npad.h
@@ -174,7 +174,8 @@ public:
void ConnectAllDisconnectedControllers();
void ClearAllControllers();
- void MergeSingleJoyAsDualJoy(Core::HID::NpadIdType npad_id_1, Core::HID::NpadIdType npad_id_2);
+ ResultCode MergeSingleJoyAsDualJoy(Core::HID::NpadIdType npad_id_1,
+ Core::HID::NpadIdType npad_id_2);
void StartLRAssignmentMode();
void StopLRAssignmentMode();
ResultCode SwapNpadAssignment(Core::HID::NpadIdType npad_id_1, Core::HID::NpadIdType npad_id_2);
diff --git a/src/core/hle/service/hid/errors.h b/src/core/hle/service/hid/errors.h
index 279974ce9..d518fd069 100644
--- a/src/core/hle/service/hid/errors.h
+++ b/src/core/hle/service/hid/errors.h
@@ -9,6 +9,8 @@ namespace Service::HID {
constexpr ResultCode NpadInvalidHandle{ErrorModule::HID, 100};
constexpr ResultCode InvalidSixAxisFusionRange{ErrorModule::HID, 423};
+constexpr ResultCode NpadIsDualJoycon{ErrorModule::HID, 601};
+constexpr ResultCode NpadIsSameType{ErrorModule::HID, 602};
constexpr ResultCode InvalidNpadId{ErrorModule::HID, 709};
constexpr ResultCode NpadNotConnected{ErrorModule::HID, 710};
diff --git a/src/core/hle/service/hid/hid.cpp b/src/core/hle/service/hid/hid.cpp
index b41fc60d6..0520a8a38 100644
--- a/src/core/hle/service/hid/hid.cpp
+++ b/src/core/hle/service/hid/hid.cpp
@@ -1090,14 +1090,14 @@ void Hid::MergeSingleJoyAsDualJoy(Kernel::HLERequestContext& ctx) {
const auto npad_id_2{rp.PopEnum<Core::HID::NpadIdType>()};
const auto applet_resource_user_id{rp.Pop<u64>()};
- applet_resource->GetController<Controller_NPad>(HidController::NPad)
- .MergeSingleJoyAsDualJoy(npad_id_1, npad_id_2);
+ auto& controller = GetAppletResource()->GetController<Controller_NPad>(HidController::NPad);
+ const auto result = controller.MergeSingleJoyAsDualJoy(npad_id_1, npad_id_2);
LOG_DEBUG(Service_HID, "called, npad_id_1={}, npad_id_2={}, applet_resource_user_id={}",
npad_id_1, npad_id_2, applet_resource_user_id);
IPC::ResponseBuilder rb{ctx, 2};
- rb.Push(ResultSuccess);
+ rb.Push(result);
}
void Hid::StartLrAssignmentMode(Kernel::HLERequestContext& ctx) {