Add controller charge state and ext button support (#159)

* Add controller charge state and ext button support

* revert field rename

* Make button fields consistent

* Actually add PADGetBatteryState

* Fix PADGetBatteryState return value

* Handle SDL_GetGamepadPowerInfo returning -1

* Use u32 instead of u16 for extButton so constants don't collide

* Add PADExtButton typedef
This commit is contained in:
Phillip Stephens
2026-05-06 01:37:26 -07:00
committed by GitHub
parent 4cd8d2f009
commit b78bbf3f58
2 changed files with 81 additions and 7 deletions
+38 -7
View File
@@ -40,6 +40,24 @@
#define PAD_BUTTON_Y 0x0800
#define PAD_BUTTON_MENU 0x1000
#define PAD_BUTTON_START 0x1000
#ifdef TARGET_PC
#define PAD_BUTTON_BACK 0x0002000
#define PAD_BUTTON_GUIDE 0x0004000
#define PAD_BUTTON_MISC1 0x0008000
#define PAD_BUTTON_MISC2 0x0010000
#define PAD_BUTTON_MISC3 0x0020000
#define PAD_BUTTON_MISC4 0x0040000
#define PAD_BUTTON_MISC5 0x0080000
#define PAD_BUTTON_MISC6 0x0100000
#define PAD_BUTTON_RIGHT_PADDLE1 0x0200000
#define PAD_BUTTON_LEFT_PADDLE1 0x0400000
#define PAD_BUTTON_RIGHT_PADDLE2 0x0800000
#define PAD_BUTTON_LEFT_PADDLE2 0x1000000
#define PAD_BUTTON_RIGHT_STICK 0x2000000
#define PAD_BUTTON_LEFT_STICK 0x4000000
#define PAD_BUTTON_TOUCHPAD 0x8000000
#define PAD_EXT_BUTTON_COUNT 15
#endif
#define PAD_BUTTON_COUNT 12
@@ -82,6 +100,9 @@ typedef struct PADStatus {
u8 analogA;
u8 analogB;
s8 err;
#ifdef TARGET_PC
u32 extButton;
#endif
} PADStatus;
typedef enum PADAxisSign {
@@ -108,13 +129,14 @@ void PADControlAllMotors(const u32* cmdArr);
void PADSetAnalogMode(u32 mode);
#ifdef TARGET_PC
#define PAD_KEY_INVALID (-1)
#define PAD_KEY_MOUSE_LEFT (-2)
#define PAD_KEY_INVALID (-1)
#define PAD_KEY_MOUSE_LEFT (-2)
#define PAD_KEY_MOUSE_MIDDLE (-3)
#define PAD_KEY_MOUSE_RIGHT (-4)
#define PAD_KEY_MOUSE_X1 (-5)
#define PAD_KEY_MOUSE_X2 (-6)
#define PAD_KEY_MOUSE_RIGHT (-4)
#define PAD_KEY_MOUSE_X1 (-5)
#define PAD_KEY_MOUSE_X2 (-6)
typedef u16 PADButton;
typedef u32 PADExtButton;
typedef u16 PADAxis;
typedef struct PADKeyButtonBinding {
@@ -138,13 +160,11 @@ typedef struct PADDeadZones {
u16 rightTriggerActivationZone;
} PADDeadZones;
typedef struct PADButtonMapping {
u32 nativeButton;
PADButton padButton;
} PADButtonMapping;
typedef struct PADAxisMapping {
PADSignedNativeAxis nativeAxis;
s32 nativeButton;
@@ -232,6 +252,17 @@ BOOL PADSetRumbleIntensity(u32 port, u16 low, u16 high);
BOOL PADGetRumbleIntensity(u32 port, u16* low, u16* high);
BOOL PADSupportsRumbleIntensity(u32 port);
typedef enum PADBatteryState {
PAD_BATTERYSTATE_ERROR = -1,
PAD_BATTERYSTATE_UNKNOWN,
PAD_BATTERYSTATE_ON_BATTERY,
PAD_BATTERYSTATE_NO_BATTERY,
PAD_BATTERYSTATE_CHARGING,
PAD_BATTERYSTATE_CHARGED,
} PADBatteryState;
PADBatteryState PADGetBatteryState(u32 port, f32* perc);
#endif
#ifdef __cplusplus
+43
View File
@@ -461,6 +461,33 @@ uint32_t PADRead(PADStatus* status) {
status[i].button |= mapping.padButton;
}
});
// TODO: Add serializable mappings for these (probably not necessary)?
static constexpr std::array<std::pair<SDL_GamepadButton, PADExtButton>, PAD_EXT_BUTTON_COUNT> kExtButtonMappings{
{
{SDL_GAMEPAD_BUTTON_BACK, PAD_BUTTON_BACK},
{SDL_GAMEPAD_BUTTON_GUIDE, PAD_BUTTON_GUIDE},
{SDL_GAMEPAD_BUTTON_MISC1, PAD_BUTTON_MISC1},
{SDL_GAMEPAD_BUTTON_MISC2, PAD_BUTTON_MISC2},
{SDL_GAMEPAD_BUTTON_MISC3, PAD_BUTTON_MISC3},
{SDL_GAMEPAD_BUTTON_MISC4, PAD_BUTTON_MISC4},
{SDL_GAMEPAD_BUTTON_MISC5, PAD_BUTTON_MISC5},
{SDL_GAMEPAD_BUTTON_MISC6, PAD_BUTTON_MISC6},
{SDL_GAMEPAD_BUTTON_RIGHT_PADDLE1, PAD_BUTTON_RIGHT_PADDLE1},
{SDL_GAMEPAD_BUTTON_LEFT_PADDLE1, PAD_BUTTON_LEFT_PADDLE1},
{SDL_GAMEPAD_BUTTON_RIGHT_PADDLE2, PAD_BUTTON_RIGHT_PADDLE2},
{SDL_GAMEPAD_BUTTON_LEFT_PADDLE2, PAD_BUTTON_LEFT_PADDLE2},
{SDL_GAMEPAD_BUTTON_RIGHT_STICK, PAD_BUTTON_RIGHT_STICK},
{SDL_GAMEPAD_BUTTON_LEFT_STICK, PAD_BUTTON_LEFT_STICK},
{SDL_GAMEPAD_BUTTON_TOUCHPAD, PAD_BUTTON_TOUCHPAD},
}
};
for (const auto& mapping : kExtButtonMappings) {
if (SDL_GetGamepadButton(controller->m_controller, mapping.first)) {
status[i].extButton |= mapping.second;
}
}
Sint16 xlPos = _get_axis_value(controller, PAD_AXIS_LEFT_X_POS);
Sint16 xlNeg = _get_axis_value(controller, PAD_AXIS_LEFT_X_NEG);
@@ -1266,3 +1293,19 @@ BOOL PADIsGCAdapter(u32 port) {
}
return ctrl->m_isGameCube;
}
PADBatteryState PADGetBatteryState(u32 port, f32* perc) {
const auto* ctrl = aurora::input::get_controller_for_player(port);
if (ctrl == nullptr) {
return PAD_BATTERYSTATE_ERROR;
}
int tmp = 0;
const auto ret = SDL_GetGamepadPowerInfo(ctrl->m_controller, &tmp);
if (tmp != -1) {
*perc = static_cast<float>(tmp) / 100.f;
} else {
*perc = static_cast<float>(tmp);
}
return static_cast<PADBatteryState>(ret);
}