File size: 2,731 Bytes
18a519f | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 | using System;
namespace UnityEngine.InputSystem.Utilities
{
/// <summary>
/// Provides type erasure and an abstraction of a saved state that
/// will (must) be restored at a later point.
/// </summary>
internal interface ISavedState
{
/// <summary>
/// Dispose current state, should be invoked before RestoreSavedState()
/// to dispose the current state before restoring a saved state.
/// </summary>
void StaticDisposeCurrentState();
/// <summary>
/// Restore previous state, should be invoked after StaticDisposeCurrentState().
/// </summary>
void RestoreSavedState();
}
/// <summary>
/// Provides functionality to store and support later restoration of a saved
/// state. The state is expected to be a value-type. If the state is not restored
/// it must be disposed to not leak resources.
/// </summary>
/// <typeparam name="T">The value-type representing the state to be stored.</typeparam>
internal sealed class SavedStructState<T> : ISavedState where T : struct
{
public delegate void TypedRestore(ref T state);
/// <summary>
/// Constructs a SavedStructState.
/// </summary>
/// <param name="state">The value-type state to be saved.</param>
/// <param name="restoreAction">The action to be carried out to restore state.</param>
/// <param name="staticDisposeCurrentState">The action to be carried out to dispose current state. May be null.</param>
internal SavedStructState(ref T state, TypedRestore restoreAction, Action staticDisposeCurrentState = null)
{
Debug.Assert(restoreAction != null, "Restore action is required");
m_State = state; // copy
m_RestoreAction = restoreAction;
m_StaticDisposeCurrentState = staticDisposeCurrentState;
}
public void StaticDisposeCurrentState()
{
if (m_StaticDisposeCurrentState != null)
{
m_StaticDisposeCurrentState();
m_StaticDisposeCurrentState = null;
}
}
public void RestoreSavedState()
{
Debug.Assert(m_StaticDisposeCurrentState == null,
$"Should have been disposed via {nameof(StaticDisposeCurrentState)} before invoking {nameof(RestoreSavedState)}");
Debug.Assert(m_RestoreAction != null, $"Only invoke {nameof(RestoreSavedState)} once ");
m_RestoreAction(ref m_State);
m_RestoreAction = null;
}
private T m_State;
private TypedRestore m_RestoreAction;
private Action m_StaticDisposeCurrentState;
}
}
|