Skip to content

Commit f21ad55

Browse files
committed
Discard events received while out focus
1 parent e0d9edc commit f21ad55

File tree

1 file changed

+63
-16
lines changed

1 file changed

+63
-16
lines changed

Packages/com.unity.inputsystem/InputSystem/InputManager.cs

Lines changed: 63 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -2244,6 +2244,8 @@ internal struct AvailableDevice
22442244
private bool m_NativeBeforeUpdateHooked;
22452245
private bool m_HaveDevicesWithStateCallbackReceivers;
22462246
private bool m_HasFocus;
2247+
private bool m_DiscardOutOfFocusEvents;
2248+
private double m_FocusRegainedTime;
22472249
private InputEventStream m_InputEventStream;
22482250

22492251
// We want to sync devices when the editor comes back into focus. Unfortunately, there's no
@@ -3032,6 +3034,8 @@ internal void OnFocusChanged(bool focus)
30323034
}
30333035
else
30343036
{
3037+
m_DiscardOutOfFocusEvents = true;
3038+
m_FocusRegainedTime = m_Runtime.currentTime;
30353039
// On focus gain, reenable and sync devices.
30363040
for (var i = 0; i < m_DevicesCount; ++i)
30373041
{
@@ -3319,23 +3323,10 @@ private unsafe void OnUpdate(InputUpdateType updateType, ref InputEventBuffer ev
33193323
}
33203324
#endif
33213325

3322-
// In the editor, we discard all input events that occur in-between exiting edit mode and having
3323-
// entered play mode as otherwise we'll spill a bunch of UI events that have occurred while the
3324-
// UI was sort of neither in this mode nor in that mode. This would usually lead to the game receiving
3325-
// an accumulation of spurious inputs right in one of its first updates.
3326-
//
3327-
// NOTE: There's a chance the solution here will prove inadequate on the long run. We may do things
3328-
// here such as throwing partial touches away and then letting the rest of a touch go through.
3329-
// Could be that ultimately we need to issue a full reset of all devices at the beginning of
3330-
// play mode in the editor.
3326+
33313327
#if UNITY_EDITOR
3332-
if ((currentEventType == StateEvent.Type ||
3333-
currentEventType == DeltaStateEvent.Type) &&
3334-
(updateType & InputUpdateType.Editor) == 0 &&
3335-
InputSystem.s_SystemObject.exitEditModeTime > 0 &&
3336-
currentEventTimeInternal >= InputSystem.s_SystemObject.exitEditModeTime &&
3337-
(currentEventTimeInternal < InputSystem.s_SystemObject.enterPlayModeTime ||
3338-
InputSystem.s_SystemObject.enterPlayModeTime == 0))
3328+
// Decide to skip events based on timing or focus state
3329+
if (ShouldDiscardEventInEditor(currentEventType, currentEventTimeInternal, updateType))
33393330
{
33403331
m_InputEventStream.Advance(false);
33413332
continue;
@@ -3678,6 +3669,8 @@ private unsafe void OnUpdate(InputUpdateType updateType, ref InputEventBuffer ev
36783669
break;
36793670
}
36803671

3672+
m_DiscardOutOfFocusEvents = false;
3673+
36813674
m_Metrics.totalEventProcessingTime +=
36823675
((double)(Stopwatch.GetTimestamp() - processingStartTime)) / Stopwatch.Frequency;
36833676
m_Metrics.totalEventLagTime += totalEventLag;
@@ -3706,6 +3699,60 @@ private unsafe void OnUpdate(InputUpdateType updateType, ref InputEventBuffer ev
37063699
m_CurrentUpdate = default;
37073700
}
37083701

3702+
#if UNITY_EDITOR
3703+
/// <summary>
3704+
/// Determines if an event should be discarded based on timing or focus state.
3705+
/// </summary>
3706+
/// <param name="eventType">The type of the current event</param>
3707+
/// <param name="eventTime">The internal time of the current event</param>
3708+
/// <param name="updateType">The current update type</param>
3709+
/// <returns>True if the event should be discarded, false otherwise.</returns>
3710+
private bool ShouldDiscardEventInEditor(FourCC eventType, double eventTime, InputUpdateType updateType)
3711+
{
3712+
// Check if this is an event that occurred during edit mode transition
3713+
if (ShouldDiscardEditModeTransitionEvent(eventType, eventTime, updateType))
3714+
return true;
3715+
3716+
// Check if this is an out-of-focus event that should be discarded
3717+
if (ShouldDiscardOutOfFocusEvent(eventTime))
3718+
return true;
3719+
3720+
return false;
3721+
}
3722+
3723+
/// <summary>
3724+
/// In the editor, we discard all input events that occur in-between exiting edit mode and having
3725+
/// entered play mode as otherwise we'll spill a bunch of UI events that have occurred while the
3726+
/// UI was sort of neither in this mode nor in that mode. This would usually lead to the game receiving
3727+
/// an accumulation of spurious inputs right in one of its first updates.
3728+
///
3729+
/// NOTE: There's a chance the solution here will prove inadequate on the long run. We may do things
3730+
/// here such as throwing partial touches away and then letting the rest of a touch go through.
3731+
/// Could be that ultimately we need to issue a full reset of all devices at the beginning of
3732+
/// play mode in the editor.
3733+
/// </summary>
3734+
private bool ShouldDiscardEditModeTransitionEvent(FourCC eventType, double eventTime, InputUpdateType updateType)
3735+
{
3736+
return (eventType == StateEvent.Type || eventType == DeltaStateEvent.Type) &&
3737+
(updateType & InputUpdateType.Editor) == 0 &&
3738+
InputSystem.s_SystemObject.exitEditModeTime > 0 &&
3739+
eventTime >= InputSystem.s_SystemObject.exitEditModeTime &&
3740+
(eventTime < InputSystem.s_SystemObject.enterPlayModeTime ||
3741+
InputSystem.s_SystemObject.enterPlayModeTime == 0);
3742+
}
3743+
3744+
/// <summary>
3745+
/// Checks if an event should be discarded because it occurred while out of focus, under specific settings.
3746+
/// </summary>
3747+
private bool ShouldDiscardOutOfFocusEvent(double eventTime)
3748+
{
3749+
if (gameHasFocus && m_Settings.backgroundBehavior != InputSettings.BackgroundBehavior.IgnoreFocus)
3750+
return m_DiscardOutOfFocusEvents && eventTime < m_FocusRegainedTime;
3751+
return false;
3752+
}
3753+
3754+
#endif
3755+
37093756
bool AreMaximumEventBytesPerUpdateExceeded(uint totalEventBytesProcessed)
37103757
{
37113758
if (m_Settings.maxEventBytesPerUpdate > 0 &&

0 commit comments

Comments
 (0)