Merge pull request #2226 from musshorn/main

Expose more battery and power connection state
This commit is contained in:
Sasha Szpakowski
2025-10-16 21:51:34 -03:00
committed by GitHub
7 changed files with 161 additions and 1 deletions
+2
View File
@@ -29,6 +29,8 @@ Released: N/A
* Added Joystick:hasSensor.
* Added Joystick:isSensorEnabled and Joystick:setSensorEnabled.
* Added Joystick:getSensorData.
* Added Joystick:getPowerInfo which exposes infomation about batteries in a controller are and if they're charging.
* Added Joystick:getConnectionState which indicates if a joystick is connected wired or wireless.
* Added new Gamepad API buttons: "misc1", "paddle1", "paddle2", "paddle3", "paddle4". and "touchpad".
* Added World:getFixturesInArea().
* Added support for saving .exr image files via ImageData:encode.
+18
View File
@@ -135,5 +135,23 @@ STRINGMAP_CLASS_BEGIN(Joystick, Joystick::InputType, Joystick::INPUT_TYPE_MAX_EN
}
STRINGMAP_CLASS_END(Joystick, Joystick::InputType, Joystick::INPUT_TYPE_MAX_ENUM, inputType)
STRINGMAP_CLASS_BEGIN(Joystick, Joystick::PowerType, Joystick::POWER_MAX_ENUM, powerState)
{
{ "unknown", Joystick::POWER_UNKNOWN },
{ "onbattery", Joystick::POWER_ON_BATTERY },
{ "nobattery", Joystick::POWER_NO_BATTERY },
{ "charging", Joystick::POWER_CHARGING },
{ "charged", Joystick::POWER_CHARGED },
}
STRINGMAP_CLASS_END(Joystick, Joystick::PowerType, Joystick::POWER_MAX_ENUM, powerState)
STRINGMAP_CLASS_BEGIN(Joystick, Joystick::ConnectionType, Joystick::CONNECTION_MAX_ENUM, connectionState)
{
{ "unknown", Joystick::CONNECTION_UNKNOWN },
{ "wired", Joystick::CONNECTION_WIRED },
{ "wireless", Joystick::CONNECTION_WIRELESS },
}
STRINGMAP_CLASS_END(Joystick, Joystick::ConnectionType, Joystick::CONNECTION_MAX_ENUM, connectionState)
} // joystick
} // love
+22
View File
@@ -144,6 +144,24 @@ public:
INPUT_TYPE_MAX_ENUM
};
enum PowerType
{
POWER_UNKNOWN, /**< cannot determine power status */
POWER_ON_BATTERY, /**< Not plugged in, running on the battery */
POWER_NO_BATTERY, /**< Plugged in, no battery available */
POWER_CHARGING, /**< Plugged in, charging battery */
POWER_CHARGED, /**< Plugged in, battery charged */
POWER_MAX_ENUM
};
enum ConnectionType
{
CONNECTION_UNKNOWN,
CONNECTION_WIRED,
CONNECTION_WIRELESS,
CONNECTION_MAX_ENUM
};
// Represents a gamepad input value, e.g. the "x" button or the left trigger.
struct GamepadInput
{
@@ -223,6 +241,8 @@ public:
virtual bool isSensorEnabled(Sensor::SensorType type) const = 0;
virtual void setSensorEnabled(Sensor::SensorType type, bool enabled) = 0;
virtual std::vector<float> getSensorData(Sensor::SensorType type) const = 0;
virtual PowerType getPowerInfo(int &batteryPercent) const = 0;
virtual ConnectionType getConnectionState() const = 0;
STRINGMAP_CLASS_DECLARE(Hat);
STRINGMAP_CLASS_DECLARE(JoystickType);
@@ -230,6 +250,8 @@ public:
STRINGMAP_CLASS_DECLARE(GamepadAxis);
STRINGMAP_CLASS_DECLARE(GamepadButton);
STRINGMAP_CLASS_DECLARE(InputType);
STRINGMAP_CLASS_DECLARE(PowerType);
STRINGMAP_CLASS_DECLARE(ConnectionType);
static float clampval(float x);
+70
View File
@@ -462,6 +462,36 @@ void Joystick::getDeviceInfo(int &vendorID, int &productID, int &productVersion)
}
}
Joystick::PowerType Joystick::getPowerInfo(int& batteryPercent) const
{
// Gets the battery state of a joystick/gamepad
Joystick::PowerType powerState = Joystick::PowerType::POWER_UNKNOWN;
SDL_PowerState batteryState;
if (!isConnected())
return powerState;
batteryState = SDL_GetJoystickPowerInfo(joyhandle, &batteryPercent);
getConstant(batteryState, powerState);
return powerState;
}
Joystick::ConnectionType Joystick::getConnectionState() const
{
// Gets the connection state of a joystick/gamepad (wired / wireless etc)
Joystick::ConnectionType connectionState = Joystick::ConnectionType::CONNECTION_UNKNOWN;
SDL_JoystickConnectionState sdlConnectionState;
if (!isConnected())
return connectionState;
sdlConnectionState = SDL_GetJoystickConnectionState(joyhandle);
getConstant(sdlConnectionState, connectionState);
return connectionState;
}
bool Joystick::isVibrationSupported()
{
if (!isConnected())
@@ -614,6 +644,26 @@ bool Joystick::getConstant(Joystick::GamepadButton in, SDL_GamepadButton &out)
return gpButtons.find(in, out);
}
bool Joystick::getConstant(SDL_PowerState in, Joystick::PowerType &out)
{
return powerStates.find(in, out);
}
bool Joystick::getConstant(Joystick::PowerType in, SDL_PowerState &out)
{
return powerStates.find(in, out);
}
bool Joystick::getConstant(SDL_JoystickConnectionState in, Joystick::ConnectionType &out)
{
return connectionStates.find(in, out);
}
bool Joystick::getConstant(Joystick::ConnectionType in, SDL_JoystickConnectionState &out)
{
return connectionStates.find(in, out);
}
EnumMap<Joystick::Hat, Uint8, Joystick::HAT_MAX_ENUM>::Entry Joystick::hatEntries[] =
{
{Joystick::HAT_CENTERED, SDL_HAT_CENTERED},
@@ -668,6 +718,26 @@ EnumMap<Joystick::GamepadButton, SDL_GamepadButton, Joystick::GAMEPAD_BUTTON_MAX
EnumMap<Joystick::GamepadButton, SDL_GamepadButton, Joystick::GAMEPAD_BUTTON_MAX_ENUM> Joystick::gpButtons(Joystick::gpButtonEntries, sizeof(Joystick::gpButtonEntries));
EnumMap<Joystick::PowerType, SDL_PowerState, Joystick::POWER_MAX_ENUM>::Entry Joystick::powerEntries[] =
{
{Joystick::POWER_UNKNOWN, SDL_POWERSTATE_UNKNOWN},
{Joystick::POWER_ON_BATTERY, SDL_POWERSTATE_ON_BATTERY},
{Joystick::POWER_NO_BATTERY, SDL_POWERSTATE_NO_BATTERY},
{Joystick::POWER_CHARGING, SDL_POWERSTATE_CHARGING},
{Joystick::POWER_CHARGED, SDL_POWERSTATE_CHARGED},
};
EnumMap<Joystick::PowerType, SDL_PowerState, Joystick::POWER_MAX_ENUM> Joystick::powerStates(Joystick::powerEntries, sizeof(Joystick::powerEntries));
EnumMap<Joystick::ConnectionType, SDL_JoystickConnectionState, Joystick::CONNECTION_MAX_ENUM>::Entry Joystick::connectionStateEntries[] =
{
{Joystick::CONNECTION_UNKNOWN, SDL_JOYSTICK_CONNECTION_UNKNOWN},
{Joystick::CONNECTION_WIRED, SDL_JOYSTICK_CONNECTION_WIRED},
{Joystick::CONNECTION_WIRELESS, SDL_JOYSTICK_CONNECTION_WIRELESS},
};
EnumMap<Joystick::ConnectionType, SDL_JoystickConnectionState, Joystick::CONNECTION_MAX_ENUM> Joystick::connectionStates(Joystick::connectionStateEntries, sizeof(Joystick::connectionStateEntries));
} // sdl
} // joystick
} // love
+13
View File
@@ -84,6 +84,8 @@ public:
int getID() const override;
void getDeviceInfo(int &vendorID, int &productID, int &productVersion) const override;
PowerType getPowerInfo(int& batteryPercent) const override;
ConnectionType getConnectionState() const override;
bool isVibrationSupported() override;
bool setVibration(float left, float right, float duration = -1.0f) override;
@@ -104,6 +106,12 @@ public:
static bool getConstant(SDL_GamepadButton in, GamepadButton &out);
static bool getConstant(GamepadButton in, SDL_GamepadButton &out);
static bool getConstant(SDL_PowerState in, PowerType &out);
static bool getConstant(PowerType in, SDL_PowerState &out);
static bool getConstant(SDL_JoystickConnectionState in, ConnectionType &out);
static bool getConstant(ConnectionType in, SDL_JoystickConnectionState &out);
private:
Joystick() {}
@@ -129,6 +137,11 @@ private:
static EnumMap<GamepadButton, SDL_GamepadButton, GAMEPAD_BUTTON_MAX_ENUM>::Entry gpButtonEntries[];
static EnumMap<GamepadButton, SDL_GamepadButton, GAMEPAD_BUTTON_MAX_ENUM> gpButtons;
static EnumMap<PowerType, SDL_PowerState, POWER_MAX_ENUM>::Entry powerEntries[];
static EnumMap<PowerType, SDL_PowerState, POWER_MAX_ENUM> powerStates;
static EnumMap<ConnectionType, SDL_JoystickConnectionState, CONNECTION_MAX_ENUM>::Entry connectionStateEntries[];
static EnumMap<ConnectionType, SDL_JoystickConnectionState, CONNECTION_MAX_ENUM> connectionStates;
};
} // sdl
+1 -1
View File
@@ -49,7 +49,7 @@ JoystickModule::JoystickModule()
int count = 0;
SDL_JoystickID *sticks = SDL_GetJoysticks(&count);
for (int i = 0; i < count; i++)
addJoystick((int64) sticks[i]);
addJoystick((int64)sticks[i]);
SDL_free(sticks);
// Start joystick event watching. Joysticks are automatically added and
+35
View File
@@ -447,6 +447,39 @@ int w_Joystick_getSensorData(lua_State *L)
return (int) data.size();
}
int w_Joystick_getDevicePowerInfo(lua_State *L)
{
Joystick *j = luax_checkjoystick(L, 1);
int batteryPercent = 0;
const char *str;
Joystick::PowerType state = j->getPowerInfo(batteryPercent);
if (!Joystick::getConstant(state, str))
str = "unknown";
lua_pushstring(L, str);
if (batteryPercent >= 0)
lua_pushnumber(L, batteryPercent);
else
lua_pushnil(L);
return 2;
}
int w_Joystick_getDeviceConnectionState(lua_State *L)
{
Joystick *j = luax_checkjoystick(L, 1);
const char *str = "unknown";
Joystick::getConstant(j->getConnectionState(), str);
lua_pushstring(L, str);
return 1;
}
#endif // LOVE_ENABLE_SENSOR
// List of functions to wrap.
@@ -457,6 +490,8 @@ static const luaL_Reg w_Joystick_functions[] =
{ "getID", w_Joystick_getID },
{ "getGUID", w_Joystick_getGUID },
{ "getDeviceInfo", w_Joystick_getDeviceInfo },
{ "getDevicePowerInfo", w_Joystick_getDevicePowerInfo },
{ "getDeviceConnectionState", w_Joystick_getDeviceConnectionState },
{ "getJoystickType", w_Joystick_getJoystickType },
{ "getAxisCount", w_Joystick_getAxisCount },
{ "getButtonCount", w_Joystick_getButtonCount },