Skip to content

Commit f2630f2

Browse files
committed
Added Singleton class with testing
1 parent 0e744b3 commit f2630f2

File tree

11 files changed

+196
-15
lines changed

11 files changed

+196
-15
lines changed

Assets/AdncAnimatorHelpers/Editor/Testing/AnimatorPlayback/TestAnimatorPlayback.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
using Adnc.AnimatorHelpers.Conditions;
22
using Adnc.AnimatorHelpers.Variables;
33
using Adnc.Utility.Testing;
4-
using AdncAnimatorHelpers.Editor.Testing.Utilities;
4+
using Adnc.AnimatorHelpers.Editors.Testing.Utilities;
55
using NUnit.Framework;
66
using UnityEngine;
77
using Object = UnityEngine.Object;

Assets/AdncAnimatorHelpers/Editor/Testing/AnimatorStub/TestAnimatorStub.cs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
1-
using AdncAnimatorHelpers.Editor.Testing.Utilities;
1+
using Adnc.Utility.Testing;
2+
using Adnc.AnimatorHelpers.Editors.Testing.Utilities;
23
using NUnit.Framework;
34
using UnityEngine;
45

5-
namespace Adnc.AnimatorHelpers.Editors.Testing.Examples {
6+
namespace Adnc.AnimatorHelpers.Editors.Testing {
67
[Category("Examples")]
7-
public class TestAnimatorStub {
8+
public class TestAnimatorStub : TestBase {
89
private GameObject _go;
910
private AnimatorStub _animStub;
1011

Assets/AdncAnimatorHelpers/Editor/Testing/Singleton.meta

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 106 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,108 @@
1-
namespace AdncAnimatorHelpers.Editor.Testing.Singleton {
2-
public class TestSingleton {
3-
1+
using Adnc.Utility.Testing;
2+
using Adnc.AnimatorHelpers.Stubs;
3+
using NUnit.Framework;
4+
using UnityEngine;
5+
6+
namespace Adnc.AnimatorHelpers.Editors.Testing {
7+
public class TestSingleton : TestBase {
8+
[TearDown]
9+
public void ClearSingleton () {
10+
SingletonStub.ClearSingleton();
11+
}
12+
13+
[Test]
14+
public void InstanceLazyLoadsWhenCalled () {
15+
Assert.IsNotNull(SingletonStub.Instance);
16+
}
17+
18+
[Test]
19+
public void SingletonAlwaysReturnsSameInstance () {
20+
var i = SingletonStub.Instance;
21+
22+
Assert.AreSame(i, SingletonStub.Instance);
23+
}
24+
25+
[Test]
26+
public void InstanceIsAutoInjectedIfComponentAlreadyExists () {
27+
var stub = new GameObject("ForceLoad")
28+
.AddComponent<SingletonStub>();
29+
30+
Assert.AreEqual(stub, SingletonStub.Instance);
31+
32+
Object.DestroyImmediate(stub.gameObject);
33+
}
34+
35+
[Test]
36+
public void PreMadeSingletonReturnsSameInstance () {
37+
var stub = new GameObject("ForceLoad")
38+
.AddComponent<SingletonStub>();
39+
var i = SingletonStub.Instance;
40+
41+
Assert.AreSame(i, SingletonStub.Instance);
42+
43+
Object.DestroyImmediate(stub.gameObject);
44+
}
45+
46+
[Test]
47+
public void MultipleInstancesStillReturnsInstance () {
48+
var stub1 = new GameObject("ForceLoad1")
49+
.AddComponent<SingletonStub>();
50+
var stub2 = new GameObject("ForceLoad2")
51+
.AddComponent<SingletonStub>();
52+
53+
Assert.IsNotNull(SingletonStub.Instance);
54+
55+
Object.DestroyImmediate(stub1.gameObject);
56+
Object.DestroyImmediate(stub2.gameObject);
57+
}
58+
59+
[Test]
60+
public void InstancePropertiesCanBeChangesGlobally () {
61+
var prop1 = SingletonStub.Instance.globalString;
62+
SingletonStub.Instance.globalString = "a";
63+
var prop2 = SingletonStub.Instance.globalString;
64+
65+
Assert.AreNotEqual(prop1, prop2);
66+
}
67+
68+
[Test]
69+
public void ClearSingletonWipesInstance () {
70+
var i = SingletonStub.Instance;
71+
72+
SingletonStub.ClearSingleton();
73+
74+
Assert.AreNotSame(i, SingletonStub.Instance);
75+
}
76+
77+
[Test]
78+
public void OnDestroyClearsInstance () {
79+
var i = SingletonStub.Instance;
80+
81+
CallPrivateMethod(SingletonStub.Instance, "OnDestroy");
82+
Object.DestroyImmediate(i.gameObject);
83+
84+
Assert.AreNotSame(i, SingletonStub.Instance);
85+
}
86+
87+
[Test]
88+
public void OnDestroySecondInstanceDoesNotClearInstance () {
89+
var stub1 = new GameObject("ForceLoad1")
90+
.AddComponent<SingletonStub>();
91+
SingletonStub.Instance.globalString = "changeToCache";
92+
var stub2 = new GameObject("ForceLoad2")
93+
.AddComponent<SingletonStub>();
94+
95+
CallPrivateMethod(stub2, "OnDestroy");
96+
Object.DestroyImmediate(stub2.gameObject);
97+
98+
Assert.AreSame(stub1, SingletonStub.Instance);
99+
100+
Object.DestroyImmediate(stub1.gameObject);
101+
}
102+
103+
[Test]
104+
public void LazyLoadSingletonNameMatchesComponentName () {
105+
Assert.AreEqual("SingletonStub", SingletonStub.Instance.name);
106+
}
4107
}
5108
}

Assets/AdncAnimatorHelpers/Editor/Testing/Utilities/AnimatorStub.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
using UnityEditor.Animations;
22
using UnityEngine;
33

4-
namespace AdncAnimatorHelpers.Editor.Testing.Utilities {
4+
namespace Adnc.AnimatorHelpers.Editors.Testing.Utilities {
55
public class AnimatorStub {
66
/// <summary>
77
/// Reference to the Animator attached to the passed GameObject

Assets/AdncAnimatorHelpers/Examples/Singleton.meta

Lines changed: 10 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Assets/AdncAnimatorHelpers/Scripts/AnimatorHelperManager.meta

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
1-
namespace AdncAnimatorHelpers.Scripts.AnimatorHelperManager {
2-
public class AnimatorHelperManager {
3-
1+
namespace Adnc.AnimatorHelpers {
2+
public class AnimatorHelperManager : Singleton<AnimatorHelperManager> {
43
}
54
}
Lines changed: 62 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,64 @@
1-
namespace Adnc.AnimatorHelpers {
2-
public class Singleton {
3-
1+
using System.Linq;
2+
using UnityEngine;
3+
4+
namespace Adnc.AnimatorHelpers {
5+
// @SRC http://wiki.unity3d.com/index.php/Singleton
6+
public class Singleton<T> : MonoBehaviour where T : MonoBehaviour {
7+
private static T _instance;
8+
9+
private static string SingletonName {
10+
get { return typeof(T).Name; }
11+
}
12+
13+
public static T Instance {
14+
get {
15+
if (_instance != null) {
16+
return _instance;
17+
}
18+
19+
var instances = FindObjectsOfType(typeof(T));
20+
if (instances.Length >= 1) {
21+
if (Application.isPlaying) {
22+
Debug.AssertFormat(
23+
instances.Length == 1,
24+
"{1} {0} singletons detected. There should only ever be one present",
25+
SingletonName,
26+
instances.Length);
27+
}
28+
29+
_instance = (T)instances[0];
30+
return _instance;
31+
}
32+
33+
var singleton = new GameObject(SingletonName);
34+
_instance = singleton.AddComponent<T>();
35+
36+
// Only add DontDestroyOnLoad if the user fails to manually implement the component in a scene
37+
// Thereby giving the user more control over the singleton lifecycle
38+
if (Application.isPlaying) {
39+
DontDestroyOnLoad(singleton);
40+
}
41+
42+
return _instance;
43+
}
44+
}
45+
46+
protected virtual void OnDestroy () {
47+
if (_instance == this) {
48+
_instance = null;
49+
}
50+
}
51+
52+
/// <summary>
53+
/// Test friendly method to prevent persisting singletons with editor tests
54+
/// </summary>
55+
public static void ClearSingleton () {
56+
if (Application.isPlaying || _instance == null) {
57+
return;
58+
}
59+
60+
DestroyImmediate(_instance);
61+
_instance = null;
62+
}
463
}
564
}

Assets/AdncAnimatorHelpers/Scripts/AnimatorHelperManager/SingletonStub.cs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
using Adnc.AnimatorHelpers;
22

3-
namespace Adnc.AnimatorHelpers.Editors.Testing.Stubs {
3+
namespace Adnc.AnimatorHelpers.Stubs {
4+
/// <summary>
5+
/// Testing only class
6+
/// </summary>
47
public class SingletonStub : Singleton<SingletonStub> {
58
public string globalString = "test";
69
}

0 commit comments

Comments
 (0)