Skip to content

Commit

Permalink
Fix issues with controller in entry_sdl.cpp. (#3321)
Browse files Browse the repository at this point in the history
SDL2's concept of GameController is a like a PS or Xbox controller, two sticks, four face buttons, etc. These are the same as the bgfx example's Gamepad.

SDL also has a concept of Joystick, which could be anything, like a flight stick. Game Controllers are implemented by these lower level joystick's.

Entry SDL gets duplicate events, for both controller and the joystick implementing it. Game controller buttons are remapped to bgfx gamepad, but joystick buttons are not. This causes incorrect button presses.

Additionally, the joystick z axis behaves differently than game controller or bgfx gamepad. With at-rest value being negative, not zero.

Due to all of this, it seems like the best approach would be to ignore joystick events and only handle game controller events.

Also, minor additional fix to get handle's index when using it as array index. Fixes compilation in Visual Studio.
  • Loading branch information
elvencache authored Jul 8, 2024
1 parent 6f79fe0 commit 74e7edc
Showing 1 changed file with 8 additions and 68 deletions.
76 changes: 8 additions & 68 deletions examples/common/entry/entry_sdl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -217,22 +217,6 @@ namespace entry
{
_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
);
}
}
}
}

Expand Down Expand Up @@ -702,16 +686,14 @@ namespace entry
}
break;

// Ignore Joystick events. Example's Gamepad concept mirrors SDL Game Controller.
// Game Controllers are higher level wrapper around Joystick and both events come through.
// Respond to only the controller events. Controller events are properly remapped.
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);
}
}
case SDL_JOYBUTTONDOWN:
case SDL_JOYBUTTONUP:
case SDL_JOYDEVICEADDED:
case SDL_JOYDEVICEREMOVED:
break;

case SDL_CONTROLLERAXISMOTION:
Expand All @@ -726,23 +708,6 @@ namespace entry
}
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.postKeyEvent(defaultWindow, key, 0, event.type == SDL_JOYBUTTONDOWN);
}
}
}
break;

case SDL_CONTROLLERBUTTONDOWN:
case SDL_CONTROLLERBUTTONUP:
{
Expand All @@ -759,31 +724,6 @@ namespace entry
}
break;

case SDL_JOYDEVICEADDED:
{
GamepadHandle handle = { m_gamepadAlloc.alloc() };
if (isValid(handle) )
{
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() };
Expand Down Expand Up @@ -1164,7 +1104,7 @@ namespace entry
{
SDL_SysWMinfo wmi;
SDL_VERSION(&wmi.version);
if (!SDL_GetWindowWMInfo(s_ctx.m_window[kDefaultWindowHandle], &wmi) )
if (!SDL_GetWindowWMInfo(s_ctx.m_window[kDefaultWindowHandle.idx], &wmi) )
{
return bgfx::NativeWindowHandleType::Default;
}
Expand Down

0 comments on commit 74e7edc

Please sign in to comment.