triton.h 3.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061
  1. // triton.h -- the controller's native input as it comes off the RF link, and the decoders for it.
  2. //
  3. // "Triton" is the Steam Controller 2 controller. Its HID input report 0x45 is what the puck relays; rf_link.cpp
  4. // decodes one into the shared g_in struct each fresh frame, and every USB personality (the IController
  5. // implementations in mode_*.cpp) reads g_in to build its own host report. report 0x45 layout:
  6. // [0]=0x45 [1]=seq [2..5]=buttons u32; analog offsets below are from the buttons low byte (rep[2]).
  7. #pragma once
  8. #include <stdint.h>
  9. // ---- Triton button masks (the 32-bit field at rep[2..5]) ----
  10. #define TB_A 0x1u
  11. #define TB_B 0x2u
  12. #define TB_X 0x4u
  13. #define TB_Y 0x8u
  14. #define TB_R3 0x20u
  15. #define TB_VIEW 0x40u
  16. #define TB_R4 0x80u
  17. #define TB_R5 0x100u
  18. #define TB_RB 0x200u
  19. #define TB_DDN 0x400u
  20. #define TB_DRT 0x800u
  21. #define TB_DLF 0x1000u
  22. #define TB_DUP 0x2000u
  23. #define TB_MENU 0x4000u
  24. #define TB_L3 0x8000u
  25. #define TB_STEAM 0x10000u
  26. #define TB_L4 0x20000u
  27. #define TB_L5 0x40000u
  28. #define TB_LB 0x80000u
  29. #define TB_RPADT 0x200000u
  30. #define TB_RPADC 0x400000u
  31. #define TB_LPADT 0x2000000u
  32. #define TB_LPADC 0x4000000u
  33. // all four back paddles held -> mode-switch chord guard
  34. #define CHORD_BACK4 (TB_R4|TB_L4|TB_R5|TB_L5)
  35. #define SW_TRIG_ON 40 // analog-trigger fraction (of 0xFF) at which digital ZL/ZR (Switch) etc. trip
  36. // ---- report 0x45 field decoders (offsets relative to rep[2], the buttons low byte) ----
  37. static inline int s16off(const uint8_t* r,int off){ int v=r[2+off]|(r[2+off+1]<<8); return (v&0x8000)?v-0x10000:v; }
  38. static inline int u16off(const uint8_t* r,int off){ return r[2+off]|(r[2+off+1]<<8); }
  39. // Controller trigger analog: the u16 in report 0x45 tops out near half-scale (~0x8000) at a full pull, so a
  40. // straight >>8 reads only ~0x80 (host sees a half-pressed trigger). Scale x2 (>>7) and saturate so a full
  41. // pull maps to the full 0xFF.
  42. static inline uint8_t trigU8(int u16v){ int v=u16v>>7; return (uint8_t)(v>255?255:v); }
  43. static inline uint32_t btnsOf(const uint8_t* r){ return (uint32_t)r[2]|((uint32_t)r[3]<<8)|((uint32_t)r[4]<<16)|((uint32_t)r[5]<<24); }
  44. // report 0x45 IMU offsets (PROTOCOL.md §8): accel @0x22, gyro @0x28 from report start.
  45. void imuFrom45(const uint8_t* r, int16_t* ax, int16_t* ay, int16_t* az, int16_t* gx, int16_t* gy, int16_t* gz);
  46. // ---- shared decoded input (filled by rf_link.cpp once per fresh report 0x45, read by every mode) ----
  47. // This single struct replaces the per-mode duplicates the firmware used to carry (the IMU/stick/button state
  48. // was copied verbatim into g_swPro*, g_ps5*, and g_gyro*). One source, many consumers.
  49. struct PuckInput {
  50. uint32_t buttons; // raw Triton buttons (TB_*); per-mode builders apply their own chord masking
  51. int16_t lx, ly, rx, ry; // sticks (int16, center 0)
  52. uint8_t lt, rt; // triggers scaled 0..255 (trigU8)
  53. int16_t lpx, lpy, rpx, rpy; // left / right trackpad coords (int16)
  54. int16_t ax, ay, az; // accelerometer
  55. int16_t gx, gy, gz; // gyroscope
  56. };
  57. extern PuckInput g_in;