in SharedContent/cpp/GameContent/MoveLookController.cpp [654:782]
void MoveLookController::UpdatePollingDevices()
{
if (m_gamepadsChanged)
{
m_gamepadsChanged = false;
unsigned int index = 0;
// Capture the list of gamepads so it won't change while we are studying it.
auto gamepads = Gamepad::Gamepads;
if (gamepads->Size == 0)
{
m_activeGamepad = nullptr;
}
// Check if the cached gamepad is still connected.
else if (!gamepads->IndexOf(m_activeGamepad, &index))
{
// MoveLookController is intended to handle input for a single player, so it
// defaults to the first active gamepad.
m_activeGamepad = gamepads->GetAt(0);
}
}
if (m_activeGamepad == nullptr)
{
return;
}
GamepadReading reading = m_activeGamepad->GetCurrentReading();
switch (m_state)
{
case MoveLookControllerState::WaitForInput:
if ((reading.Buttons & GamepadButtons::Menu) == GamepadButtons::Menu)
{
m_gamepadStartButtonInUse = true;
}
else if (m_gamepadStartButtonInUse)
{
// Trigger once only on button release.
m_gamepadStartButtonInUse = false;
m_buttonPressed = true;
}
break;
case MoveLookControllerState::Active:
if ((reading.Buttons & GamepadButtons::Menu) == GamepadButtons::Menu)
{
m_gamepadStartButtonInUse = true;
}
else if (m_gamepadStartButtonInUse)
{
// Trigger once only on button release.
m_gamepadStartButtonInUse = false;
m_pausePressed = true;
}
// Use the left thumbstick on the game controller to control
// the eye point position control. Thumbstick input is defined from [-1, 1].
// We use a deadzone in the middle range to avoid drift.
if (reading.LeftThumbstickX > THUMBSTICK_DEADZONE ||
reading.LeftThumbstickX < -THUMBSTICK_DEADZONE)
{
float x = static_cast<float>(reading.LeftThumbstickX);
m_moveCommand.x -= (x > 0) ? 1 : -1;
}
if (reading.LeftThumbstickY > THUMBSTICK_DEADZONE ||
reading.LeftThumbstickY < -THUMBSTICK_DEADZONE)
{
float y = static_cast<float>(reading.LeftThumbstickY);
m_moveCommand.y += (y > 0) ? 1 : -1;
}
// Use the right thumbstick on the game controller to control
// the look at control. Thumbstick input is defined from [-1, 1].
// We use a deadzone in the middle range to avoid drift.
XMFLOAT2 pointerDelta;
if (reading.RightThumbstickX > THUMBSTICK_DEADZONE ||
reading.RightThumbstickX < -THUMBSTICK_DEADZONE)
{
float x = static_cast<float>(reading.RightThumbstickX);
pointerDelta.x = x * x * x;
}
else
{
pointerDelta.x = 0.0f;
}
if (reading.RightThumbstickY > THUMBSTICK_DEADZONE ||
reading.RightThumbstickY < -THUMBSTICK_DEADZONE)
{
float y = static_cast<float>(reading.RightThumbstickY);
pointerDelta.y = y * y * y;
}
else
{
pointerDelta.y = 0.0f;
}
XMFLOAT2 rotationDelta;
rotationDelta.x = pointerDelta.x * 0.08f; // Scale for control sensitivity.
rotationDelta.y = pointerDelta.y * 0.08f;
// Update our orientation based on the command.
m_pitch += rotationDelta.y;
m_yaw += rotationDelta.x;
// Limit pitch to straight up or straight down.
m_pitch = __max(-XM_PI / 2.0f, m_pitch);
m_pitch = __min(+XM_PI / 2.0f, m_pitch);
// Check the state of the Right Trigger button. This is used to indicate fire control.
if (reading.RightTrigger > TRIGGER_DEADZONE)
{
if (!m_autoFire && !m_gamepadTriggerInUse)
{
m_firePressed = true;
}
m_gamepadTriggerInUse = true;
}
else
{
m_gamepadTriggerInUse = false;
}
break;
}
}