Class DualSenseOutputWriter
Drives vibration, the LED AND both adaptive triggers on a DualSense in a SINGLE HID output report, over USB.
Stock Unity exposes no adaptive-trigger output, and its built-in DualSense vibration/LED reports do not address the trigger region — so any built-in vibration or color update CLOBBERS an active trigger effect (verified on hardware). The DualSense output report is monolithic (one report carries vibration + LED + both triggers), so the only clobber-free option is to own the whole report ourselves. This writer keeps per-device state as the single source of truth and re-emits the full report on every change, exactly like DualShock4OutputWriter does for the DS4.
Two report formats are emitted: the USB report (id 0x02, 48-byte payload) and the Bluetooth
report (id 0x31, 78 bytes, CRC32-suffixed). On Linux both buses are driven through a raw hidraw handle
(Unity's Linux backend routes no HID output). On Windows USB uses Unity's ExecuteCommand, while
Bluetooth — which Unity's built-in DualSense output does not support — is driven through a raw HID
handle that pads the 0x31 report to the OS output-report length (validated on hardware). macOS drives
USB only. Methods return false for non-DualSense pads and on unsupported platforms.
Implements
Inherited Members
Namespace: Serenity.Feedback.Infrastructure.Services
Assembly: Serenity.UnityFeedback.Infrastructure.dll
Syntax
public class DualSenseOutputWriter : IGamepadOutputBackend
Constructors
DualSenseOutputWriter()
Declaration
public DualSenseOutputWriter()
Methods
TryResetTrigger(Gamepad, AdaptiveTriggerSide)
If pad is a USB DualSense, clears the adaptive-trigger effect on the given
side (mode 0x00) while preserving vibration, LED, and the other trigger. Returns true when handled.
Declaration
public bool TryResetTrigger(Gamepad pad, AdaptiveTriggerSide side)
Parameters
| Type | Name | Description |
|---|---|---|
| Gamepad | pad | |
| AdaptiveTriggerSide | side |
Returns
| Type | Description |
|---|---|
| bool |
TrySetLed(Gamepad, Color)
If pad is a USB DualSense, updates its LED color (preserving vibration and
triggers) and sends the combined report. Returns true when handled.
Declaration
public bool TrySetLed(Gamepad pad, Color color)
Parameters
| Type | Name | Description |
|---|---|---|
| Gamepad | pad | |
| Color | color |
Returns
| Type | Description |
|---|---|
| bool |
TrySetTrigger(Gamepad, AdaptiveTriggerSide, byte, byte, byte, byte)
If pad is a USB DualSense, applies an adaptive-trigger effect to the given
side (preserving vibration, LED, and the other trigger) and sends the combined report.
Returns true when handled.
Declaration
public bool TrySetTrigger(Gamepad pad, AdaptiveTriggerSide side, byte mode, byte p0, byte p1, byte p2)
Parameters
| Type | Name | Description |
|---|---|---|
| Gamepad | pad | Target gamepad. |
| AdaptiveTriggerSide | side | Which trigger(s) to drive. |
| byte | mode | DualSense effect mode byte (0x00 off, 0x01 resistance, 0x02 weapon, 0x06 vibration). |
| byte | p0 | Effect parameter 0 (e.g. start position). |
| byte | p1 | Effect parameter 1 (e.g. end position / amplitude). |
| byte | p2 | Effect parameter 2 (e.g. force / frequency). |
Returns
| Type | Description |
|---|---|
| bool |
TrySetVibration(Gamepad, float, float)
If pad is a USB DualSense, updates its motor speeds (preserving LED and
triggers) and sends the combined report. Returns true when handled.
Declaration
public bool TrySetVibration(Gamepad pad, float low, float high)
Parameters
| Type | Name | Description |
|---|---|---|
| Gamepad | pad | |
| float | low | |
| float | high |
Returns
| Type | Description |
|---|---|
| bool |