LazyStack.cs 2.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677
  1. // Animancer // https://kybernetik.com.au/animancer // Copyright 2022 Kybernetik //
  2. using System.Collections.Generic;
  3. namespace Animancer
  4. {
  5. /// <summary>A simple stack implementation that tracks an active index without actually adding or removing objects.</summary>
  6. /// https://kybernetik.com.au/animancer/api/Animancer/LazyStack_1
  7. ///
  8. public class LazyStack<T> where T : new()
  9. {
  10. /************************************************************************************************************************/
  11. /// <summary>The underlying collection of objects.</summary>
  12. /// <remarks>
  13. /// This is not a <see cref="Stack{T}"/> because that class comes from a different assembly that might not
  14. /// otherwise need to be included in builds, so using a <see cref="List{T}"/> can slightly reduce build size.
  15. /// </remarks>
  16. private readonly List<T> Stack;
  17. /// <summary>The index of the <see cref="Current"/> object in the <see cref="Stack"/>.</summary>
  18. private int _CurrentIndex = -1;
  19. /// <summary>The object currently on the top of the stack.</summary>
  20. public T Current { get; private set; }
  21. /************************************************************************************************************************/
  22. /// <summary>Creates a new <see cref="LazyStack{T}"/> with a default internal list capacity of 16.</summary>
  23. public LazyStack()
  24. {
  25. Stack = new List<T>();
  26. }
  27. /// <summary>Creates a new <see cref="LazyStack{T}"/> with the specified internal list capacity.</summary>
  28. public LazyStack(int capacity)
  29. {
  30. Stack = new List<T>(capacity);
  31. for (int i = 0; i < capacity; i++)
  32. Stack[i] = new T();
  33. }
  34. /************************************************************************************************************************/
  35. /// <summary>Moves to the next object in the stack.</summary>
  36. public T Increment()
  37. {
  38. _CurrentIndex++;
  39. if (_CurrentIndex == Stack.Count)
  40. {
  41. Current = new T();
  42. Stack.Add(Current);
  43. }
  44. else
  45. {
  46. Current = Stack[_CurrentIndex];
  47. }
  48. return Current;
  49. }
  50. /************************************************************************************************************************/
  51. /// <summary>Moves to the previous object in the stack.</summary>
  52. public void Decrement()
  53. {
  54. _CurrentIndex--;
  55. if (_CurrentIndex >= 0)
  56. Current = Stack[_CurrentIndex];
  57. else
  58. Current = default;
  59. }
  60. /************************************************************************************************************************/
  61. }
  62. }