SDL: Added joystick handling.

This commit is contained in:
Branimir Karadžić 2016-01-24 22:17:49 -08:00
parent 008bc72d6f
commit c63b61870a

View File

@ -82,6 +82,22 @@ namespace entry
return GamepadAxis::Enum(s_translateGamepadAxis[_sdl]); return GamepadAxis::Enum(s_translateGamepadAxis[_sdl]);
} }
struct AxisDpadRemap
{
Key::Enum first;
Key::Enum second;
};
static AxisDpadRemap s_axisDpad[] =
{
{ Key::GamepadLeft, Key::GamepadRight },
{ Key::GamepadUp, Key::GamepadDown },
{ Key::None, Key::None },
{ Key::GamepadLeft, Key::GamepadRight },
{ Key::GamepadUp, Key::GamepadDown },
{ Key::None, Key::None },
};
struct GamepadSDL struct GamepadSDL
{ {
GamepadSDL() GamepadSDL()
@ -99,17 +115,59 @@ namespace entry
m_deadzone[GamepadAxis::RightZ] = 30; m_deadzone[GamepadAxis::RightZ] = 30;
} }
void create(int32_t _jid) void create(const SDL_JoyDeviceEvent& _jev)
{ {
m_controller = SDL_GameControllerOpen(_jid); m_joystick = SDL_JoystickOpen(_jev.which);
SDL_Joystick* joystick = m_joystick;
m_jid = SDL_JoystickInstanceID(joystick);
}
void create(const SDL_ControllerDeviceEvent& _cev)
{
m_controller = SDL_GameControllerOpen(_cev.which);
SDL_Joystick* joystick = SDL_GameControllerGetJoystick(m_controller); SDL_Joystick* joystick = SDL_GameControllerGetJoystick(m_controller);
m_jid = SDL_JoystickInstanceID(joystick); m_jid = SDL_JoystickInstanceID(joystick);
} }
void update(EventQueue& _eventQueue, WindowHandle _handle, GamepadHandle _gamepad, GamepadAxis::Enum _axis, int32_t _value)
{
if (filter(_axis, &_value) )
{
_eventQueue.postAxisEvent(_handle, _gamepad, _axis, _value);
if (Key::None != s_axisDpad[_axis].first)
{
if (_value == 0)
{
_eventQueue.postKeyEvent(_handle, s_axisDpad[_axis].first, 0, false);
_eventQueue.postKeyEvent(_handle, s_axisDpad[_axis].second, 0, false);
}
else
{
_eventQueue.postKeyEvent(_handle
, 0 > _value ? s_axisDpad[_axis].first : s_axisDpad[_axis].second
, 0
, true
);
}
}
}
}
void destroy() void destroy()
{ {
SDL_GameControllerClose(m_controller); if (NULL != m_controller)
m_controller = NULL; {
SDL_GameControllerClose(m_controller);
m_controller = NULL;
}
if (NULL != m_joystick)
{
SDL_JoystickClose(m_joystick);
m_joystick = NULL;
}
m_jid = INT32_MAX; m_jid = INT32_MAX;
} }
@ -127,6 +185,7 @@ namespace entry
int32_t m_value[GamepadAxis::Count]; int32_t m_value[GamepadAxis::Count];
int32_t m_deadzone[GamepadAxis::Count]; int32_t m_deadzone[GamepadAxis::Count];
SDL_Joystick* m_joystick;
SDL_GameController* m_controller; SDL_GameController* m_controller;
// SDL_Haptic* m_haptic; // SDL_Haptic* m_haptic;
SDL_JoystickID m_jid; SDL_JoystickID m_jid;
@ -334,7 +393,6 @@ namespace entry
m_mte.m_argv = _argv; m_mte.m_argv = _argv;
SDL_Init(0 SDL_Init(0
| SDL_INIT_VIDEO
| SDL_INIT_GAMECONTROLLER | SDL_INIT_GAMECONTROLLER
); );
@ -547,6 +605,18 @@ namespace entry
} }
break; break;
case SDL_JOYAXISMOTION:
{
const SDL_JoyAxisEvent& jev = event.jaxis;
GamepadHandle handle = findGamepad(jev.which);
if (isValid(handle) )
{
GamepadAxis::Enum axis = translateGamepadAxis(jev.axis);
m_gamepad[handle.idx].update(m_eventQueue, defaultWindow, handle, axis, jev.value);
}
}
break;
case SDL_CONTROLLERAXISMOTION: case SDL_CONTROLLERAXISMOTION:
{ {
const SDL_ControllerAxisEvent& aev = event.caxis; const SDL_ControllerAxisEvent& aev = event.caxis;
@ -554,10 +624,23 @@ namespace entry
if (isValid(handle) ) if (isValid(handle) )
{ {
GamepadAxis::Enum axis = translateGamepadAxis(aev.axis); GamepadAxis::Enum axis = translateGamepadAxis(aev.axis);
int32_t value = aev.value; m_gamepad[handle.idx].update(m_eventQueue, defaultWindow, handle, axis, aev.value);
if (m_gamepad[handle.idx].filter(axis, &value) ) }
}
break;
case SDL_JOYBUTTONDOWN:
case SDL_JOYBUTTONUP:
{
const SDL_JoyButtonEvent& bev = event.jbutton;
GamepadHandle handle = findGamepad(bev.which);
if (isValid(handle) )
{
Key::Enum key = translateGamepad(bev.button);
if (Key::Count != key)
{ {
m_eventQueue.postAxisEvent(defaultWindow, handle, axis, value); m_eventQueue.postKeyEvent(defaultWindow, key, 0, event.type == SDL_JOYBUTTONDOWN);
} }
} }
} }
@ -579,14 +662,38 @@ namespace entry
} }
break; break;
case SDL_CONTROLLERDEVICEADDED: case SDL_JOYDEVICEADDED:
{ {
const SDL_ControllerDeviceEvent& cev = event.cdevice;
GamepadHandle handle = { m_gamepadAlloc.alloc() }; GamepadHandle handle = { m_gamepadAlloc.alloc() };
if (isValid(handle) ) if (isValid(handle) )
{ {
m_gamepad[handle.idx].create(cev.which); const SDL_JoyDeviceEvent& jev = event.jdevice;
m_gamepad[handle.idx].create(jev);
m_eventQueue.postGamepadEvent(defaultWindow, handle, true);
}
}
break;
case SDL_JOYDEVICEREMOVED:
{
const SDL_JoyDeviceEvent& jev = event.jdevice;
GamepadHandle handle = findGamepad(jev.which);
if (isValid(handle) )
{
m_gamepad[handle.idx].destroy();
m_gamepadAlloc.free(handle.idx);
m_eventQueue.postGamepadEvent(defaultWindow, handle, false);
}
}
break;
case SDL_CONTROLLERDEVICEADDED:
{
GamepadHandle handle = { m_gamepadAlloc.alloc() };
if (isValid(handle) )
{
const SDL_ControllerDeviceEvent& cev = event.cdevice;
m_gamepad[handle.idx].create(cev);
m_eventQueue.postGamepadEvent(defaultWindow, handle, true); m_eventQueue.postGamepadEvent(defaultWindow, handle, true);
} }
} }