Add a small implementation of motion controls

This commit is contained in:
anirudhb
2020-04-28 17:13:41 -07:00
parent 72b73d22ab
commit bcba34ae7d
3 changed files with 61 additions and 6 deletions

View File

@@ -236,6 +236,8 @@ void Controller_NPad::OnLoadInputDevices() {
players[i].analogs.begin() + Settings::NativeAnalog::STICK_HID_END,
sticks[i].begin(), Input::CreateDevice<Input::AnalogDevice>);
}
motion_sensors[Settings::values.udp_pad_index] =
Input::CreateDevice<Input::MotionDevice>(Settings::values.motion_device);
}
void Controller_NPad::OnRelease() {}
@@ -338,6 +340,25 @@ void Controller_NPad::OnUpdate(const Core::Timing::CoreTiming& core_timing, u8*
cur_entry.timestamp2 = cur_entry.timestamp;
}
const std::array<SixAxisGeneric*, 6> controller_sixaxes{&npad.full, &npad._handheld,
&npad._left_dual, &npad._right_dual,
&npad._left, &npad._right};
for (auto* sixaxis : controller_sixaxes) {
sixaxis->common.entry_count = 16;
sixaxis->common.total_entry_count = 17;
const auto& last_entry = sixaxis->sixaxis[sixaxis->common.last_entry_index];
sixaxis->common.timestamp = core_timing.GetTicks();
sixaxis->common.last_entry_index = (sixaxis->common.last_entry_index + 1) % 17;
auto& cur_entry = sixaxis->sixaxis[sixaxis->common.last_entry_index];
cur_entry.timestamp = last_entry.timestamp + 1;
cur_entry.timestamp2 = cur_entry.timestamp;
}
const auto& controller_type = connected_controllers[i].type;
if (controller_type == NPadControllerType::None || !connected_controllers[i].is_connected) {
@@ -358,6 +379,7 @@ void Controller_NPad::OnUpdate(const Core::Timing::CoreTiming& core_timing, u8*
auto& pokeball_entry =
npad.pokeball_states.npad[npad.pokeball_states.common.last_entry_index];
auto& libnx_entry = npad.libnx.npad[npad.libnx.common.last_entry_index];
auto& sixaxis_entry = npad.full.sixaxis[npad.full.common.last_entry_index];
libnx_entry.connection_status.raw = 0;
@@ -434,6 +456,12 @@ void Controller_NPad::OnUpdate(const Core::Timing::CoreTiming& core_timing, u8*
libnx_entry.pad.l_stick = pad_state.l_stick;
libnx_entry.pad.r_stick = pad_state.r_stick;
// Set this entry regardless of the controller type, for now.
if (motion_sensors[i] && sixaxis_sensor_enabled) {
auto& sensor = motion_sensors[i];
std::tie(sixaxis_entry.accelerometer, sixaxis_entry.gyroscope) = sensor->GetStatus();
}
press_state |= static_cast<u32>(pad_state.pad_states.raw);
}
std::memcpy(data + NPAD_OFFSET, shared_memory_entries.data(),

View File

@@ -7,6 +7,7 @@
#include <array>
#include "common/bit_field.h"
#include "common/common_types.h"
#include "common/vector_math.h"
#include "core/frontend/input.h"
#include "core/hle/kernel/object.h"
#include "core/hle/kernel/writable_event.h"
@@ -236,6 +237,24 @@ private:
};
static_assert(sizeof(NPadGeneric) == 0x350, "NPadGeneric is an invalid size");
struct SixAxisState {
s64_le timestamp;
INSERT_PADDING_BYTES(8); // unknown
s64_le timestamp2;
Common::Vec3f accelerometer;
Common::Vec3f gyroscope;
INSERT_PADDING_BYTES(12); // unknown sensor data
std::array<Common::Vec3f, 3> orientation;
s64_le _always_one; // always 1
};
static_assert(sizeof(SixAxisState) == 0x68, "SixAxisState is an invalid size");
struct SixAxisGeneric {
CommonHeader common;
std::array<SixAxisState, 17> sixaxis;
};
static_assert(sizeof(SixAxisGeneric) == 0x708, "SixAxisGeneric is an invalid size");
enum class ColorReadError : u32_le {
ReadOk = 0,
ColorDoesntExist = 1,
@@ -284,9 +303,12 @@ private:
NPadGeneric pokeball_states;
NPadGeneric libnx; // TODO(ogniK): Find out what this actually is, libnx seems to only be
// relying on this for the time being
INSERT_PADDING_BYTES(
0x708 *
6); // TODO(ogniK): SixAxis states, require more information before implementation
SixAxisGeneric full; // used
SixAxisGeneric _handheld; // stub
SixAxisGeneric _left_dual; // stub
SixAxisGeneric _right_dual; // stub
SixAxisGeneric _left; // stub
SixAxisGeneric _right; // stub
NPadDevice device_type;
NPadProperties properties;
INSERT_PADDING_WORDS(1);
@@ -318,6 +340,8 @@ private:
std::array<std::unique_ptr<Input::AnalogDevice>, Settings::NativeAnalog::NUM_STICKS_HID>,
10>
sticks;
std::array<std::unique_ptr<Input::MotionDevice>, 10> motion_sensors;
bool sixaxis_sensor_enabled{true};
std::vector<u32> supported_npad_id_types{};
NpadHoldType hold_type{NpadHoldType::Vertical};
// Each controller should have their own styleset changed event

View File

@@ -31,6 +31,7 @@
#include "core/hle/service/hid/controllers/keyboard.h"
#include "core/hle/service/hid/controllers/mouse.h"
#include "core/hle/service/hid/controllers/npad.h"
#include "core/hle/service/hid/controllers/sixaxis.h"
#include "core/hle/service/hid/controllers/stubbed.h"
#include "core/hle/service/hid/controllers/touchscreen.h"
#include "core/hle/service/hid/controllers/xpad.h"
@@ -395,9 +396,10 @@ void Hid::StartSixAxisSensor(Kernel::HLERequestContext& ctx) {
const auto handle{rp.Pop<u32>()};
const auto applet_resource_user_id{rp.Pop<u64>()};
LOG_WARNING(Service_HID, "(STUBBED) called, handle={}, applet_resource_user_id={}", handle,
LOG_DEBUG(Service_HID, "called, handle={}, applet_resource_user_id={}", handle,
applet_resource_user_id);
applet_resource->ActivateController(HidController::SixAxisSensor);
IPC::ResponseBuilder rb{ctx, 2};
rb.Push(RESULT_SUCCESS);
}
@@ -825,8 +827,9 @@ void Hid::StopSixAxisSensor(Kernel::HLERequestContext& ctx) {
IPC::RequestParser rp{ctx};
const auto handle{rp.Pop<u32>()};
LOG_WARNING(Service_HID, "(STUBBED) called, handle={}", handle);
LOG_DEBUG(Service_HID, "called, handle={}", handle);
applet_resource->DeactivateController(HidController::SixAxisSensor);
IPC::ResponseBuilder rb{ctx, 2};
rb.Push(RESULT_SUCCESS);
}
@@ -1188,4 +1191,4 @@ void InstallInterfaces(SM::ServiceManager& service_manager, Core::System& system
std::make_shared<XCD_SYS>()->InstallAsService(service_manager);
}
} // namespace Service::HID
} // namespace Service::HID