More HidServer progress
This commit is contained in:
parent
ca6a667853
commit
818467012c
8 changed files with 184 additions and 499 deletions
|
@ -40,12 +40,5 @@ namespace Ryujinx.HLE.HOS.Services.Hid.HidServer
|
|||
_ => throw new ArgumentOutOfRangeException(nameof(index)),
|
||||
#pragma warning restore IDE0055
|
||||
};
|
||||
|
||||
public static bool IsValidNpadIdType(NpadIdType npadIdType)
|
||||
{
|
||||
return (npadIdType >= NpadIdType.Player1 && npadIdType <= NpadIdType.Player8) ||
|
||||
npadIdType == NpadIdType.Handheld ||
|
||||
npadIdType == NpadIdType.Unknown;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -76,19 +76,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(32)]
|
||||
// SendKeyboardLockKeyEvent(uint flags, pid)
|
||||
public ResultCode SendKeyboardLockKeyEvent(ServiceCtx context)
|
||||
{
|
||||
uint flags = context.RequestData.ReadUInt32();
|
||||
|
||||
// NOTE: This signal the keyboard driver about lock events.
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { flags });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(40)]
|
||||
// AcquireXpadIdEventHandle(ulong XpadId) -> nn::sf::NativeHandle
|
||||
public ResultCode AcquireXpadIdEventHandle(ServiceCtx context)
|
||||
|
@ -120,29 +107,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(55)]
|
||||
// GetXpadIds() -> long IdsCount, buffer<array<nn::hid::BasicXpadId>, type: 0xa>
|
||||
public ResultCode GetXpadIds(ServiceCtx context)
|
||||
{
|
||||
// There is any Xpad, so we return 0 and write nothing inside the type-0xa buffer.
|
||||
context.ResponseData.Write(0L);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(56)]
|
||||
// ActivateJoyXpad(nn::hid::JoyXpadId)
|
||||
public ResultCode ActivateJoyXpad(ServiceCtx context)
|
||||
{
|
||||
int joyXpadId = context.RequestData.ReadInt32();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(58)]
|
||||
// GetJoyXpadLifoHandle(nn::hid::JoyXpadId) -> nn::sf::NativeHandle
|
||||
public ResultCode GetJoyXpadLifoHandle(ServiceCtx context)
|
||||
|
@ -158,40 +122,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(59)]
|
||||
// GetJoyXpadIds() -> long IdsCount, buffer<array<nn::hid::JoyXpadId>, type: 0xa>
|
||||
public ResultCode GetJoyXpadIds(ServiceCtx context)
|
||||
{
|
||||
// There is any JoyXpad, so we return 0 and write nothing inside the type-0xa buffer.
|
||||
context.ResponseData.Write(0L);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(60)]
|
||||
// ActivateSixAxisSensor(nn::hid::BasicXpadId)
|
||||
public ResultCode ActivateSixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int basicXpadId = context.RequestData.ReadInt32();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { basicXpadId });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(61)]
|
||||
// DeactivateSixAxisSensor(nn::hid::BasicXpadId)
|
||||
public ResultCode DeactivateSixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int basicXpadId = context.RequestData.ReadInt32();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { basicXpadId });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(62)]
|
||||
// GetSixAxisSensorLifoHandle(nn::hid::BasicXpadId) -> nn::sf::NativeHandle
|
||||
public ResultCode GetSixAxisSensorLifoHandle(ServiceCtx context)
|
||||
|
@ -207,28 +137,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(63)]
|
||||
// ActivateJoySixAxisSensor(nn::hid::JoyXpadId)
|
||||
public ResultCode ActivateJoySixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int joyXpadId = context.RequestData.ReadInt32();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(64)]
|
||||
// DeactivateJoySixAxisSensor(nn::hid::JoyXpadId)
|
||||
public ResultCode DeactivateJoySixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int joyXpadId = context.RequestData.ReadInt32();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(65)]
|
||||
// GetJoySixAxisSensorLifoHandle(nn::hid::JoyXpadId) -> nn::sf::NativeHandle
|
||||
public ResultCode GetJoySixAxisSensorLifoHandle(ServiceCtx context)
|
||||
|
@ -244,144 +152,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(66)]
|
||||
// StartSixAxisSensor(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId)
|
||||
public ResultCode StartSixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(67)]
|
||||
// StopSixAxisSensor(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId)
|
||||
public ResultCode StopSixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(68)]
|
||||
// IsSixAxisSensorFusionEnabled(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId) -> bool IsEnabled
|
||||
public ResultCode IsSixAxisSensorFusionEnabled(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
context.ResponseData.Write(_sixAxisSensorFusionEnabled);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sixAxisSensorFusionEnabled });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(69)]
|
||||
// EnableSixAxisSensorFusion(bool Enabled, nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId)
|
||||
public ResultCode EnableSixAxisSensorFusion(ServiceCtx context)
|
||||
{
|
||||
_sixAxisSensorFusionEnabled = context.RequestData.ReadUInt32() != 0;
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sixAxisSensorFusionEnabled });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(70)]
|
||||
// SetSixAxisSensorFusionParameters(nn::hid::SixAxisSensorHandle, float RevisePower, float ReviseRange, nn::applet::AppletResourceUserId)
|
||||
public ResultCode SetSixAxisSensorFusionParameters(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
|
||||
_sensorFusionParams = new SensorFusionParameters
|
||||
{
|
||||
RevisePower = context.RequestData.ReadInt32(),
|
||||
ReviseRange = context.RequestData.ReadInt32(),
|
||||
};
|
||||
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(71)]
|
||||
// GetSixAxisSensorFusionParameters(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId) -> float RevisePower, float ReviseRange)
|
||||
public ResultCode GetSixAxisSensorFusionParameters(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
context.ResponseData.Write(_sensorFusionParams.RevisePower);
|
||||
context.ResponseData.Write(_sensorFusionParams.ReviseRange);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(72)]
|
||||
// ResetSixAxisSensorFusionParameters(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId)
|
||||
public ResultCode ResetSixAxisSensorFusionParameters(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
_sensorFusionParams.RevisePower = 0;
|
||||
_sensorFusionParams.ReviseRange = 0;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(82)]
|
||||
// IsSixAxisSensorAtRest(nn::hid::SixAxisSensorHandle, nn::applet::AppletResourceUserId) -> bool IsAsRest
|
||||
public ResultCode IsSixAxisSensorAtRest(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
bool isAtRest = true;
|
||||
|
||||
context.ResponseData.Write(isAtRest);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, isAtRest });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(83)] // 6.0.0+
|
||||
// IsFirmwareUpdateAvailableForSixAxisSensor(nn::hid::AppletResourceUserId, nn::hid::SixAxisSensorHandle, pid) -> bool UpdateAvailable
|
||||
public ResultCode IsFirmwareUpdateAvailableForSixAxisSensor(ServiceCtx context)
|
||||
{
|
||||
int sixAxisSensorHandle = context.RequestData.ReadInt32();
|
||||
context.RequestData.BaseStream.Position += 4; // Padding
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
context.ResponseData.Write(_isFirmwareUpdateAvailableForSixAxisSensor);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _isFirmwareUpdateAvailableForSixAxisSensor });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(84)] // 13.0.0+
|
||||
// EnableSixAxisSensorUnalteredPassthrough(nn::applet::AppletResourceUserId, nn::hid::SixAxisSensorHandle, u8 enabled)
|
||||
public ResultCode EnableSixAxisSensorUnalteredPassthrough(ServiceCtx context)
|
||||
|
@ -816,129 +586,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(200)]
|
||||
// GetVibrationDeviceInfo(nn::hid::VibrationDeviceHandle) -> nn::hid::VibrationDeviceInfo
|
||||
public ResultCode GetVibrationDeviceInfo(ServiceCtx context)
|
||||
{
|
||||
VibrationDeviceHandle deviceHandle = context.RequestData.ReadStruct<VibrationDeviceHandle>();
|
||||
NpadStyleIndex deviceType = (NpadStyleIndex)deviceHandle.DeviceType;
|
||||
NpadIdType npadIdType = (NpadIdType)deviceHandle.PlayerId;
|
||||
|
||||
if (deviceType < NpadStyleIndex.System || deviceType >= NpadStyleIndex.FullKey)
|
||||
{
|
||||
if (!HidUtils.IsValidNpadIdType(npadIdType))
|
||||
{
|
||||
return ResultCode.InvalidNpadIdType;
|
||||
}
|
||||
|
||||
if (deviceHandle.Position > 1)
|
||||
{
|
||||
return ResultCode.InvalidDeviceIndex;
|
||||
}
|
||||
|
||||
VibrationDeviceType vibrationDeviceType = VibrationDeviceType.None;
|
||||
|
||||
if (Enum.IsDefined(deviceType))
|
||||
{
|
||||
vibrationDeviceType = VibrationDeviceType.LinearResonantActuator;
|
||||
}
|
||||
else if ((uint)deviceType == 8)
|
||||
{
|
||||
vibrationDeviceType = VibrationDeviceType.GcErm;
|
||||
}
|
||||
|
||||
VibrationDevicePosition vibrationDevicePosition = VibrationDevicePosition.None;
|
||||
|
||||
if (vibrationDeviceType == VibrationDeviceType.LinearResonantActuator)
|
||||
{
|
||||
if (deviceHandle.Position == 0)
|
||||
{
|
||||
vibrationDevicePosition = VibrationDevicePosition.Left;
|
||||
}
|
||||
else if (deviceHandle.Position == 1)
|
||||
{
|
||||
vibrationDevicePosition = VibrationDevicePosition.Right;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidOperationException($"{nameof(deviceHandle.Position)} contains an invalid value: {deviceHandle.Position}");
|
||||
}
|
||||
}
|
||||
|
||||
VibrationDeviceValue deviceInfo = new()
|
||||
{
|
||||
DeviceType = vibrationDeviceType,
|
||||
Position = vibrationDevicePosition,
|
||||
};
|
||||
|
||||
context.ResponseData.WriteStruct(deviceInfo);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
return ResultCode.InvalidNpadDeviceType;
|
||||
}
|
||||
|
||||
[CommandCmif(201)]
|
||||
// SendVibrationValue(nn::hid::VibrationDeviceHandle, nn::hid::VibrationValue, nn::applet::AppletResourceUserId)
|
||||
public ResultCode SendVibrationValue(ServiceCtx context)
|
||||
{
|
||||
VibrationDeviceHandle deviceHandle = new()
|
||||
{
|
||||
DeviceType = context.RequestData.ReadByte(),
|
||||
PlayerId = context.RequestData.ReadByte(),
|
||||
Position = context.RequestData.ReadByte(),
|
||||
Reserved = context.RequestData.ReadByte(),
|
||||
};
|
||||
|
||||
VibrationValue vibrationValue = new()
|
||||
{
|
||||
AmplitudeLow = context.RequestData.ReadSingle(),
|
||||
FrequencyLow = context.RequestData.ReadSingle(),
|
||||
AmplitudeHigh = context.RequestData.ReadSingle(),
|
||||
FrequencyHigh = context.RequestData.ReadSingle(),
|
||||
};
|
||||
|
||||
#pragma warning disable IDE0059 // Remove unnecessary value assignment
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
#pragma warning restore IDE0059
|
||||
|
||||
Dictionary<byte, VibrationValue> dualVibrationValues = new()
|
||||
{
|
||||
[deviceHandle.Position] = vibrationValue,
|
||||
};
|
||||
|
||||
context.Device.Hid.Npads.UpdateRumbleQueue((PlayerIndex)deviceHandle.PlayerId, dualVibrationValues);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(202)]
|
||||
// GetActualVibrationValue(nn::hid::VibrationDeviceHandle, nn::applet::AppletResourceUserId) -> nn::hid::VibrationValue
|
||||
public ResultCode GetActualVibrationValue(ServiceCtx context)
|
||||
{
|
||||
VibrationDeviceHandle deviceHandle = new()
|
||||
{
|
||||
DeviceType = context.RequestData.ReadByte(),
|
||||
PlayerId = context.RequestData.ReadByte(),
|
||||
Position = context.RequestData.ReadByte(),
|
||||
Reserved = context.RequestData.ReadByte(),
|
||||
};
|
||||
|
||||
#pragma warning disable IDE0059 // Remove unnecessary value assignment
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
#pragma warning restore IDE0059
|
||||
|
||||
VibrationValue vibrationValue = context.Device.Hid.Npads.GetLastVibrationValue((PlayerIndex)deviceHandle.PlayerId, deviceHandle.Position);
|
||||
|
||||
context.ResponseData.Write(vibrationValue.AmplitudeLow);
|
||||
context.ResponseData.Write(vibrationValue.FrequencyLow);
|
||||
context.ResponseData.Write(vibrationValue.AmplitudeHigh);
|
||||
context.ResponseData.Write(vibrationValue.FrequencyHigh);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(203)]
|
||||
// CreateActiveVibrationDeviceList() -> object<nn::hid::IActiveVibrationDeviceList>
|
||||
public ResultCode CreateActiveVibrationDeviceList(ServiceCtx context)
|
||||
|
@ -948,26 +595,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(204)]
|
||||
// PermitVibration(bool Enable)
|
||||
public ResultCode PermitVibration(ServiceCtx context)
|
||||
{
|
||||
_vibrationPermitted = context.RequestData.ReadBoolean();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { _vibrationPermitted });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(205)]
|
||||
// IsVibrationPermitted() -> bool IsEnabled
|
||||
public ResultCode IsVibrationPermitted(ServiceCtx context)
|
||||
{
|
||||
context.ResponseData.Write(_vibrationPermitted);
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(206)]
|
||||
// SendVibrationValues(nn::applet::AppletResourceUserId, buffer<array<nn::hid::VibrationDeviceHandle>, type: 9>, buffer<array<nn::hid::VibrationValue>, type: 9>)
|
||||
public ResultCode SendVibrationValues(ServiceCtx context)
|
||||
|
@ -1013,47 +640,6 @@ namespace Ryujinx.HLE.HOS.Services.Hid
|
|||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(207)] // 4.0.0+
|
||||
// SendVibrationGcErmCommand(nn::hid::VibrationDeviceHandle, nn::hid::VibrationGcErmCommand, nn::applet::AppletResourceUserId)
|
||||
public ResultCode SendVibrationGcErmCommand(ServiceCtx context)
|
||||
{
|
||||
int vibrationDeviceHandle = context.RequestData.ReadInt32();
|
||||
long vibrationGcErmCommand = context.RequestData.ReadInt64();
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, vibrationDeviceHandle, vibrationGcErmCommand });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(208)] // 4.0.0+
|
||||
// GetActualVibrationGcErmCommand(nn::hid::VibrationDeviceHandle, nn::applet::AppletResourceUserId) -> nn::hid::VibrationGcErmCommand
|
||||
public ResultCode GetActualVibrationGcErmCommand(ServiceCtx context)
|
||||
{
|
||||
int vibrationDeviceHandle = context.RequestData.ReadInt32();
|
||||
long appletResourceUserId = context.RequestData.ReadInt64();
|
||||
|
||||
context.ResponseData.Write(_vibrationGcErmCommand);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, vibrationDeviceHandle, _vibrationGcErmCommand });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(406)] // 4.0.0+
|
||||
// GetNpadLeftRightInterfaceType(uint NpadId) -> uchar LeftInterfaceType, uchar RightInterfaceType
|
||||
public ResultCode GetNpadLeftRightInterfaceType(ServiceCtx context)
|
||||
{
|
||||
int npadId = context.RequestData.ReadInt32();
|
||||
|
||||
context.ResponseData.Write((byte)0);
|
||||
context.ResponseData.Write((byte)0);
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { npadId, LeftInterfaceType = 0, RightInterfaceType = 0 });
|
||||
|
||||
return ResultCode.Success;
|
||||
}
|
||||
|
||||
[CommandCmif(500)] // 5.0.0+
|
||||
// GetPalmaConnectionHandle(uint Unknown0, nn::applet::AppletResourceUserId) -> nn::hid::PalmaConnectionHandle
|
||||
public ResultCode GetPalmaConnectionHandle(ServiceCtx context)
|
||||
|
|
14
src/Ryujinx.Horizon/Hid/HidResult.cs
Normal file
14
src/Ryujinx.Horizon/Hid/HidResult.cs
Normal file
|
@ -0,0 +1,14 @@
|
|||
using Ryujinx.Horizon.Common;
|
||||
|
||||
namespace Ryujinx.Horizon.Hid
|
||||
{
|
||||
class HidResult
|
||||
{
|
||||
private const int ModuleId = 202;
|
||||
|
||||
public static Result InvalidNpadDeviceType => new Result(ModuleId, 122);
|
||||
public static Result InvalidNpadIdType => new Result(ModuleId, 123);
|
||||
public static Result InvalidDeviceIndex => new Result(ModuleId, 124);
|
||||
public static Result InvalidBufferSize => new Result(ModuleId, 131);
|
||||
}
|
||||
}
|
|
@ -9,6 +9,7 @@ using Ryujinx.Horizon.Sdk.Hid.Vibration;
|
|||
using Ryujinx.Horizon.Sdk.Sf;
|
||||
using Ryujinx.Horizon.Sdk.Sf.Hipc;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ryujinx.Horizon.Hid
|
||||
{
|
||||
|
@ -35,6 +36,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
|
||||
private long _npadCommunicationMode;
|
||||
private uint _accelerometerPlayMode;
|
||||
private readonly VibrationGcErmCommand _vibrationGcErmCommand;
|
||||
private float _sevenSixAxisSensorFusionStrength;
|
||||
|
||||
private SensorFusionParameters _sensorFusionParams;
|
||||
|
@ -151,7 +153,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(40)]
|
||||
public Result AcquireXpadIdEventHandle([CopyHandle] out int arg0, ulong xpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { xpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -159,7 +161,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(41)]
|
||||
public Result ReleaseXpadIdEventHandle(ulong xpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { xpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -186,7 +188,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(56)]
|
||||
public Result ActivateJoyXpad(uint joyXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -194,39 +196,42 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(58)]
|
||||
public Result GetJoyXpadLifoHandle([CopyHandle] out int arg0, uint joyXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(59)]
|
||||
public Result GetJoyXpadIds(out long arg0, [Buffer(HipcBufferFlags.Out | HipcBufferFlags.Pointer)] Span<uint> joyXpadIds)
|
||||
public Result GetJoyXpadIds(out long idCount, [Buffer(HipcBufferFlags.Out | HipcBufferFlags.Pointer)] Span<uint> joyXpadIds)
|
||||
{
|
||||
// There aren't any JoyXpad, so we return 0 and write nothing inside the buffer.
|
||||
idCount = 0;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(60)]
|
||||
public Result ActivateSixAxisSensor(uint basixXpadId)
|
||||
public Result ActivateSixAxisSensor(uint basicXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { basicXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(61)]
|
||||
public Result DeactivateSixAxisSensor(uint basixXpadId)
|
||||
public Result DeactivateSixAxisSensor(uint basicXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { basicXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(62)]
|
||||
public Result GetSixAxisSensorLifoHandle([CopyHandle] out int arg0, uint basixXpadId)
|
||||
public Result GetSixAxisSensorLifoHandle([CopyHandle] out int arg0, uint basicXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { basicXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -234,7 +239,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(63)]
|
||||
public Result ActivateJoySixAxisSensor(uint joyXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -242,7 +247,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(64)]
|
||||
public Result DeactivateJoySixAxisSensor(uint joyXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -250,7 +255,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(65)]
|
||||
public Result GetJoySixAxisSensorLifoHandle([CopyHandle] out int arg0, uint joyXpadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { joyXpadId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -258,7 +263,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(66)]
|
||||
public Result StartSixAxisSensor(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -266,39 +271,52 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(67)]
|
||||
public Result StopSixAxisSensor(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(68)]
|
||||
public Result IsSixAxisSensorFusionEnabled(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
public Result IsSixAxisSensorFusionEnabled(out bool sixAxisSensorFusionEnabled, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
sixAxisSensorFusionEnabled = _sixAxisSensorFusionEnabled;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sixAxisSensorFusionEnabled });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(69)]
|
||||
public Result EnableSixAxisSensorFusion(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, bool arg2, [ClientProcessId] ulong pid)
|
||||
public Result EnableSixAxisSensorFusion(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, bool sixAxisSensorFusionEnabled, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
_sixAxisSensorFusionEnabled = sixAxisSensorFusionEnabled;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sixAxisSensorFusionEnabled });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(70)]
|
||||
public Result SetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, float arg2, float arg3, [ClientProcessId] ulong pid)
|
||||
public Result SetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, float revisePower, float reviseRange, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
_sensorFusionParams = new SensorFusionParameters
|
||||
{
|
||||
RevisePower = revisePower,
|
||||
ReviseRange = reviseRange
|
||||
};
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(71)]
|
||||
public Result GetSixAxisSensorFusionParameters(out float arg0, out float arg1, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
public Result GetSixAxisSensorFusionParameters(out float revisePower, out float reviseRange, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
revisePower = _sensorFusionParams.RevisePower;
|
||||
reviseRange = _sensorFusionParams.ReviseRange;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -306,7 +324,10 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(72)]
|
||||
public Result ResetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
_sensorFusionParams.RevisePower = 0;
|
||||
_sensorFusionParams.ReviseRange = 0;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _sensorFusionParams.RevisePower, _sensorFusionParams.ReviseRange });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -408,17 +429,21 @@ namespace Ryujinx.Horizon.Hid
|
|||
}
|
||||
|
||||
[CmifCommand(82)]
|
||||
public Result IsSixAxisSensorAtRest(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
public Result IsSixAxisSensorAtRest(out bool isAtRest, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
isAtRest = true;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, isAtRest });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(83)]
|
||||
public Result IsFirmwareUpdateAvailableForSixAxisSensor(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
public Result IsFirmwareUpdateAvailableForSixAxisSensor(out bool isFirmwareUpdateAvailableForSixAxisSensor, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
isFirmwareUpdateAvailableForSixAxisSensor = _isFirmwareUpdateAvailableForSixAxisSensor;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, sixAxisSensorHandle, _isFirmwareUpdateAvailableForSixAxisSensor });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -698,23 +723,80 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(200)]
|
||||
public Result GetVibrationDeviceInfo(out VibrationDeviceInfoForIpc vibrationDeviceInfoForIpc, VibrationDeviceHandle vibrationDeviceHandle)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
NpadStyleIndex deviceType = vibrationDeviceHandle.DeviceType;
|
||||
NpadIdType npadIdType = vibrationDeviceHandle.PlayerId;
|
||||
vibrationDeviceInfoForIpc = new();
|
||||
|
||||
return Result.Success;
|
||||
if (deviceType < NpadStyleIndex.System || deviceType >= NpadStyleIndex.FullKey)
|
||||
{
|
||||
if (!IsValidNpadIdType(npadIdType))
|
||||
{
|
||||
return HidResult.InvalidNpadIdType;
|
||||
}
|
||||
|
||||
if (vibrationDeviceHandle.Position > 1)
|
||||
{
|
||||
return HidResult.InvalidDeviceIndex;
|
||||
}
|
||||
|
||||
VibrationDeviceType vibrationDeviceType = VibrationDeviceType.None;
|
||||
|
||||
if (Enum.IsDefined(deviceType))
|
||||
{
|
||||
vibrationDeviceType = VibrationDeviceType.LinearResonantActuator;
|
||||
}
|
||||
else if ((uint)deviceType == 8)
|
||||
{
|
||||
vibrationDeviceType = VibrationDeviceType.GcErm;
|
||||
}
|
||||
|
||||
VibrationDevicePosition vibrationDevicePosition = VibrationDevicePosition.None;
|
||||
|
||||
if (vibrationDeviceType == VibrationDeviceType.LinearResonantActuator)
|
||||
{
|
||||
if (vibrationDeviceHandle.Position == 0)
|
||||
{
|
||||
vibrationDevicePosition = VibrationDevicePosition.Left;
|
||||
}
|
||||
else if (vibrationDeviceHandle.Position == 1)
|
||||
{
|
||||
vibrationDevicePosition = VibrationDevicePosition.Right;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidOperationException($"{nameof(vibrationDeviceHandle.Position)} contains an invalid value: {vibrationDeviceHandle.Position}");
|
||||
}
|
||||
}
|
||||
|
||||
vibrationDeviceInfoForIpc = new()
|
||||
{
|
||||
DeviceType = vibrationDeviceType,
|
||||
Position = vibrationDevicePosition,
|
||||
};
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
return HidResult.InvalidNpadDeviceType;
|
||||
}
|
||||
|
||||
[CmifCommand(201)]
|
||||
public Result SendVibrationValue(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationValue arg2, [ClientProcessId] ulong pid)
|
||||
public Result SendVibrationValue(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationValue vibrationValue, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Dictionary<byte, VibrationValue> dualVibrationValues = new()
|
||||
{
|
||||
[vibrationDeviceHandle.Position] = vibrationValue,
|
||||
};
|
||||
|
||||
Npads.UpdateRumbleQueue(vibrationDeviceHandle.PlayerId, dualVibrationValues);
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(202)]
|
||||
public Result GetActualVibrationValue(out VibrationValue arg0, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, [ClientProcessId] ulong pid)
|
||||
public Result GetActualVibrationValue(out VibrationValue vibrationValue, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
vibrationValue = Npads.GetLastVibrationValue(vibrationDeviceHandle.PlayerId, vibrationDeviceHandle.Position);
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -728,17 +810,19 @@ namespace Ryujinx.Horizon.Hid
|
|||
}
|
||||
|
||||
[CmifCommand(204)]
|
||||
public Result PermitVibration(bool arg0)
|
||||
public Result PermitVibration(bool vibrationPermitted)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
_vibrationPermitted = vibrationPermitted;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { _vibrationPermitted });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(205)]
|
||||
public Result IsVibrationPermitted(out bool arg0)
|
||||
public Result IsVibrationPermitted(out bool vibrationPermitted)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
vibrationPermitted = _vibrationPermitted;
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -754,7 +838,7 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(207)]
|
||||
public Result SendVibrationGcErmCommand(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationGcErmCommand vibrationGcErmCommand, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, vibrationDeviceHandle, vibrationGcErmCommand });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -762,7 +846,9 @@ namespace Ryujinx.Horizon.Hid
|
|||
[CmifCommand(208)]
|
||||
public Result GetActualVibrationGcErmCommand(out VibrationGcErmCommand vibrationGcErmCommand, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
vibrationGcErmCommand = _vibrationGcErmCommand;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { appletResourceUserId, vibrationDeviceHandle, _vibrationGcErmCommand });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -958,15 +1044,18 @@ namespace Ryujinx.Horizon.Hid
|
|||
}
|
||||
|
||||
[CmifCommand(406)]
|
||||
public Result GetNpadLeftRightInterfaceType(out byte arg0, out byte arg1, uint arg2)
|
||||
public Result GetNpadLeftRightInterfaceType(out byte leftInterfaceType, out byte rightInterfaceType, uint npadId)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
leftInterfaceType = 0;
|
||||
rightInterfaceType = 0;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { npadId, LeftInterfaceType = 0, RightInterfaceType = 0 });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
[CmifCommand(407)]
|
||||
public Result GetNpadOfHighestBatteryLevel(out uint arg0, [Buffer(HipcBufferFlags.In | HipcBufferFlags.Pointer)] ReadOnlySpan<uint> arg1, AppletResourceUserId appletResourceUserId, [ClientProcessId] ulong pid)
|
||||
public Result GetNpadOfHighestBatteryLevel(out uint npadId, [Buffer(HipcBufferFlags.In | HipcBufferFlags.Pointer)] ReadOnlySpan<uint> arg1, AppletResourceUserId appletResourceUserId, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
|
||||
|
@ -1242,9 +1331,11 @@ namespace Ryujinx.Horizon.Hid
|
|||
}
|
||||
|
||||
[CmifCommand(1003)]
|
||||
public Result IsFirmwareUpdateNeededForNotification(out bool arg0, int arg1, AppletResourceUserId appletResourceUserId, [ClientProcessId] ulong pid)
|
||||
public Result IsFirmwareUpdateNeededForNotification(out bool isFirmwareUpdateNeededForNotification, int unknown, AppletResourceUserId appletResourceUserId, [ClientProcessId] ulong pid)
|
||||
{
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid);
|
||||
isFirmwareUpdateNeededForNotification = false;
|
||||
|
||||
Logger.Stub?.PrintStub(LogClass.ServiceHid, new { IsFirmwareUpdateNeededForNotification = false, unknown, appletResourceUserId });
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
@ -1256,5 +1347,12 @@ namespace Ryujinx.Horizon.Hid
|
|||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
private static bool IsValidNpadIdType(NpadIdType npadIdType)
|
||||
{
|
||||
return (npadIdType >= NpadIdType.Player1 && npadIdType <= NpadIdType.Player8) ||
|
||||
npadIdType == NpadIdType.Handheld ||
|
||||
npadIdType == NpadIdType.Unknown;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,8 +33,8 @@ namespace Ryujinx.Horizon.Sdk.Hid.HidDevices
|
|||
internal bool SixAxisActive = false; // TODO: link to hidserver when implemented
|
||||
internal NpadStyleTag SupportedStyleSets { get; set; }
|
||||
|
||||
public Dictionary<PlayerIndex, ConcurrentQueue<(VibrationValue, VibrationValue)>> RumbleQueues = new();
|
||||
public Dictionary<PlayerIndex, (VibrationValue, VibrationValue)> LastVibrationValues = new();
|
||||
public Dictionary<NpadIdType, ConcurrentQueue<(VibrationValue, VibrationValue)>> RumbleQueues = new();
|
||||
public Dictionary<NpadIdType, (VibrationValue, VibrationValue)> LastVibrationValues = new();
|
||||
|
||||
public NpadDevices(bool active = true) : base(active)
|
||||
{
|
||||
|
@ -596,7 +596,7 @@ namespace Ryujinx.Horizon.Sdk.Hid.HidDevices
|
|||
WriteNewSixInputEntry(ref currentNpad.JoyRightSixAxisSensor, ref newState);
|
||||
}
|
||||
|
||||
public void UpdateRumbleQueue(PlayerIndex index, Dictionary<byte, VibrationValue> dualVibrationValues)
|
||||
public void UpdateRumbleQueue(NpadIdType index, Dictionary<byte, VibrationValue> dualVibrationValues)
|
||||
{
|
||||
if (RumbleQueues.TryGetValue(index, out ConcurrentQueue<(VibrationValue, VibrationValue)> currentQueue))
|
||||
{
|
||||
|
@ -619,7 +619,7 @@ namespace Ryujinx.Horizon.Sdk.Hid.HidDevices
|
|||
}
|
||||
}
|
||||
|
||||
public VibrationValue GetLastVibrationValue(PlayerIndex index, byte position)
|
||||
public VibrationValue GetLastVibrationValue(NpadIdType index, byte position)
|
||||
{
|
||||
if (!LastVibrationValues.TryGetValue(index, out (VibrationValue, VibrationValue) dualVibrationValue))
|
||||
{
|
||||
|
@ -629,7 +629,7 @@ namespace Ryujinx.Horizon.Sdk.Hid.HidDevices
|
|||
return (position == 0) ? dualVibrationValue.Item1 : dualVibrationValue.Item2;
|
||||
}
|
||||
|
||||
public ConcurrentQueue<(VibrationValue, VibrationValue)> GetRumbleQueue(PlayerIndex index)
|
||||
public ConcurrentQueue<(VibrationValue, VibrationValue)> GetRumbleQueue(NpadIdType index)
|
||||
{
|
||||
if (!RumbleQueues.TryGetValue(index, out ConcurrentQueue<(VibrationValue, VibrationValue)> rumbleQueue))
|
||||
{
|
||||
|
|
|
@ -21,19 +21,19 @@ namespace Ryujinx.Horizon.Sdk.Hid
|
|||
Result GetXpadIds(out long idCount, Span<uint> basicXpadIds);
|
||||
Result ActivateJoyXpad(uint joyXpadId);
|
||||
Result GetJoyXpadLifoHandle(out int arg0, uint joyXpadId);
|
||||
Result GetJoyXpadIds(out long arg0, Span<uint> joyXpadIds);
|
||||
Result ActivateSixAxisSensor(uint basixXpadId);
|
||||
Result DeactivateSixAxisSensor(uint basixXpadId);
|
||||
Result GetSixAxisSensorLifoHandle(out int arg0, uint basixXpadId);
|
||||
Result GetJoyXpadIds(out long idCount, Span<uint> joyXpadIds);
|
||||
Result ActivateSixAxisSensor(uint basicXpadId);
|
||||
Result DeactivateSixAxisSensor(uint basicXpadId);
|
||||
Result GetSixAxisSensorLifoHandle(out int arg0, uint basicXpadId);
|
||||
Result ActivateJoySixAxisSensor(uint joyXpadId);
|
||||
Result DeactivateJoySixAxisSensor(uint joyXpadId);
|
||||
Result GetJoySixAxisSensorLifoHandle(out int arg0, uint joyXpadId);
|
||||
Result StartSixAxisSensor(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result StopSixAxisSensor(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsSixAxisSensorFusionEnabled(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result EnableSixAxisSensorFusion(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, bool arg2, ulong pid);
|
||||
Result SetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, float arg2, float arg3, ulong pid);
|
||||
Result GetSixAxisSensorFusionParameters(out float arg0, out float arg1, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsSixAxisSensorFusionEnabled(out bool sixAxisSensorFusionEnabled, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result EnableSixAxisSensorFusion(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, bool sixAxisSensorFusionEnabled, ulong pid);
|
||||
Result SetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, float revisePower, float reviseRange, ulong pid);
|
||||
Result GetSixAxisSensorFusionParameters(out float revisePower, out float reviseRange, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result ResetSixAxisSensorFusionParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result SetAccelerometerParameters(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, float x, float y, ulong pid);
|
||||
Result GetAccelerometerParameters(out float x, out float y, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
|
@ -44,8 +44,8 @@ namespace Ryujinx.Horizon.Sdk.Hid
|
|||
Result SetGyroscopeZeroDriftMode(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, GyroscopeZeroDriftMode gyroscopeZeroDriftMode, ulong pid);
|
||||
Result GetGyroscopeZeroDriftMode(out GyroscopeZeroDriftMode gyroscopeZeroDriftMode, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result ResetGyroscopeZeroDriftMode(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsSixAxisSensorAtRest(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsFirmwareUpdateAvailableForSixAxisSensor(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsSixAxisSensorAtRest(out bool isAtRest, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result IsFirmwareUpdateAvailableForSixAxisSensor(out bool isFirmwareUpdateAvailableForSixAxisSensor, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result EnableSixAxisSensorUnalteredPassthrough(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, bool arg2, ulong pid);
|
||||
Result IsSixAxisSensorUnalteredPassthroughEnabled(out bool arg0, AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, ulong pid);
|
||||
Result StoreSixAxisSensorCalibrationParameter(AppletResourceUserId appletResourceUserId, SixAxisSensorHandle sixAxisSensorHandle, in SixAxisSensorCalibrationParameter sixAxisSensorCalibrationParameter, ulong pid);
|
||||
|
@ -80,11 +80,11 @@ namespace Ryujinx.Horizon.Sdk.Hid
|
|||
Result SetNpadCaptureButtonAssignment(AppletResourceUserId appletResourceUserId, NpadStyleTag arg1, NpadButton arg2, ulong pid);
|
||||
Result ClearNpadCaptureButtonAssignment(AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result GetVibrationDeviceInfo(out VibrationDeviceInfoForIpc vibrationDeviceInfoForIpc, VibrationDeviceHandle vibrationDeviceHandle);
|
||||
Result SendVibrationValue(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationValue arg2, ulong pid);
|
||||
Result GetActualVibrationValue(out VibrationValue arg0, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, ulong pid);
|
||||
Result SendVibrationValue(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationValue vibrationValue, ulong pid);
|
||||
Result GetActualVibrationValue(out VibrationValue vibrationValue, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, ulong pid);
|
||||
Result CreateActiveVibrationDeviceList(out IActiveVibrationDeviceList arg0);
|
||||
Result PermitVibration(bool arg0);
|
||||
Result IsVibrationPermitted(out bool arg0);
|
||||
Result PermitVibration(bool vibrationPermitted);
|
||||
Result IsVibrationPermitted(out bool vibrationPermitted);
|
||||
Result SendVibrationValues(AppletResourceUserId appletResourceUserId, ReadOnlySpan<VibrationDeviceHandle> vibrationDeviceHandles, ReadOnlySpan<VibrationValue> vibrationValues);
|
||||
Result SendVibrationGcErmCommand(AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, VibrationGcErmCommand vibrationGcErmCommand, ulong pid);
|
||||
Result GetActualVibrationGcErmCommand(out VibrationGcErmCommand vibrationGcErmCommand, AppletResourceUserId appletResourceUserId, VibrationDeviceHandle vibrationDeviceHandle, ulong pid);
|
||||
|
@ -109,8 +109,8 @@ namespace Ryujinx.Horizon.Sdk.Hid
|
|||
Result HasBattery(out bool hasBattery, uint npadId);
|
||||
Result HasLeftRightBattery(out bool hasLeftBattery, out bool hasRightBattery, uint npadId);
|
||||
Result GetNpadInterfaceType(out byte npadInterfaceType, uint npadId);
|
||||
Result GetNpadLeftRightInterfaceType(out byte arg0, out byte arg1, uint arg2);
|
||||
Result GetNpadOfHighestBatteryLevel(out uint arg0, ReadOnlySpan<uint> arg1, AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result GetNpadLeftRightInterfaceType(out byte leftInterfaceType, out byte rightInterfaceType, uint npadId);
|
||||
Result GetNpadOfHighestBatteryLevel(out uint npadId, ReadOnlySpan<uint> arg1, AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result GetPalmaConnectionHandle(out PalmaConnectionHandle palmaConnectionHandle, uint arg1, AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result InitializePalma(PalmaConnectionHandle palmaConnectionHandle);
|
||||
Result AcquirePalmaOperationCompleteEvent(out int arg0, PalmaConnectionHandle palmaConnectionHandle);
|
||||
|
@ -144,7 +144,7 @@ namespace Ryujinx.Horizon.Sdk.Hid
|
|||
Result SetNpadCommunicationMode(AppletResourceUserId appletResourceUserId, long npadCommunicationMode, ulong pid);
|
||||
Result GetNpadCommunicationMode(out long npadCommunicationMode);
|
||||
Result SetTouchScreenConfiguration(AppletResourceUserId appletResourceUserId, TouchScreenConfigurationForNx touchScreenConfigurationForNx, ulong pid);
|
||||
Result IsFirmwareUpdateNeededForNotification(out bool arg0, int arg1, AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result IsFirmwareUpdateNeededForNotification(out bool isFirmwareUpdateNeededForNotification, int unknown, AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
Result ActivateDigitizer(AppletResourceUserId appletResourceUserId, ulong pid);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,9 +1,11 @@
|
|||
using Ryujinx.Horizon.Sdk.Hid.Npad;
|
||||
|
||||
namespace Ryujinx.Horizon.Sdk.Hid.Vibration
|
||||
{
|
||||
public struct VibrationDeviceHandle
|
||||
{
|
||||
public byte DeviceType;
|
||||
public byte PlayerId;
|
||||
public NpadStyleIndex DeviceType;
|
||||
public NpadIdType PlayerId;
|
||||
public byte Position;
|
||||
public byte Reserved;
|
||||
}
|
||||
|
|
|
@ -1,8 +0,0 @@
|
|||
namespace Ryujinx.Horizon.Sdk.Hid.Vibration
|
||||
{
|
||||
struct VibrationDeviceValue
|
||||
{
|
||||
public VibrationDeviceType DeviceType;
|
||||
public VibrationDevicePosition Position;
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue