Skip to content

Commit 9fd3f2b

Browse files
committed
Added tick method with corresponding test to Tree
1 parent 72b556e commit 9fd3f2b

File tree

23 files changed

+277
-83
lines changed

23 files changed

+277
-83
lines changed

Assets/FluidBehaviorTree/Scripts/BehaviorTree/BehaviorTree.cs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,6 @@ public void AddNode (ITaskParent parent, ITask child) {
4040

4141
parent.AddChild(child);
4242
nodes.Add(child);
43-
child.Owner = this;
4443

4544
var item = child as IEventAwake;
4645
if (item != null) {

Assets/FluidBehaviorTree/Scripts/BehaviorTree/Editor/BehaviorTreeTest.cs

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ public void AddNode () {
7070

7171
[Test]
7272
public void Parent_node_is_added_to_the_child () {
73-
Assert.AreEqual(action, tree.Root.children[0]);
73+
Assert.AreEqual(action, tree.Root.Children[0]);
7474
}
7575

7676
[Test]
@@ -82,11 +82,6 @@ public void Add_child_node_to_node_list () {
8282
public void Add_child_node_to_nodes () {
8383
Assert.IsTrue(tree.nodes.Contains(action));
8484
}
85-
86-
[Test]
87-
public void Attaches_a_reference_to_the_behavior_tree () {
88-
action.Received().Owner = tree;
89-
}
9085
}
9186

9287
public class AddNodeMethodError : AddNodeMethod {
Lines changed: 166 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,166 @@
1+
using Adnc.FluidBT.TaskParents.Composites;
2+
using Adnc.FluidBT.Tasks;
3+
using NSubstitute;
4+
using NUnit.Framework;
5+
using UnityEngine;
6+
7+
namespace Adnc.FluidBT.Trees.Testing {
8+
public class TreeTest {
9+
private GameObject _gameObject;
10+
private Tree _tree;
11+
12+
[SetUp]
13+
public void SetBehaviorTree () {
14+
_gameObject = new GameObject("BT");
15+
_tree = new Tree(_gameObject);
16+
}
17+
18+
[TearDown]
19+
public void AfterEach () {
20+
Object.DestroyImmediate(_gameObject);
21+
}
22+
23+
public class RootSetup : TreeTest {
24+
[Test]
25+
public void It_should_set_the_root_node_Owner_by_default () {
26+
Assert.AreEqual(_gameObject, _tree.Root.Owner);
27+
}
28+
}
29+
30+
public class AddNodeMethod : TreeTest {
31+
[Test]
32+
public void Parent_adds_the_child_reference () {
33+
var action = Substitute.For<ITask>();
34+
action.Enabled.Returns(true);
35+
36+
_tree.AddNode(_tree.Root, action);
37+
38+
Assert.AreEqual(action, _tree.Root.Children[0]);
39+
}
40+
41+
[Test]
42+
public void Set_the_child_nodes_GameObject_reference () {
43+
var action = Substitute.For<ITask>();
44+
action.Enabled.Returns(true);
45+
46+
_tree.AddNode(_tree.Root, action);
47+
48+
_tree.Root.Children[0].Received(1).Owner = _gameObject;
49+
}
50+
}
51+
52+
public class TickMethod : TreeTest {
53+
private ITask _action;
54+
55+
[SetUp]
56+
public void ConfigureAction () {
57+
_action = Substitute.For<ITask>();
58+
_action.Enabled.Returns(true);
59+
}
60+
61+
public class RootWithSingleNode : TickMethod {
62+
[SetUp]
63+
public void AddNode () {
64+
_tree.AddNode(_tree.Root, _action);
65+
}
66+
67+
[Test]
68+
public void Update_the_first_child_task_on_update () {
69+
_tree.Tick();
70+
71+
_action.Received(1).Update();
72+
}
73+
74+
[Test]
75+
public void Runs_reset_on_2nd_run_if_success () {
76+
_tree.Tick();
77+
_tree.Tick();
78+
79+
_action.Received(1).Reset();
80+
}
81+
82+
[Test]
83+
public void Does_not_run_reset_on_2nd_run_if_continue_was_returned () {
84+
_action.Update().Returns(TaskStatus.Continue);
85+
86+
_tree.Tick();
87+
_tree.Tick();
88+
89+
_action.Received(0).Reset();
90+
}
91+
92+
[Test]
93+
public void Update_reruns_node_on_status_failure () {
94+
_action.Update().Returns(TaskStatus.Failure);
95+
96+
_tree.Tick();
97+
_tree.Tick();
98+
99+
_action.Received(2).Update();
100+
}
101+
102+
[Test]
103+
public void Update_reruns_node_on_status_success () {
104+
_action.Update().Returns(TaskStatus.Failure);
105+
106+
_tree.Tick();
107+
_tree.Tick();
108+
109+
_action.Received(2).Update();
110+
}
111+
}
112+
113+
public class RootWithSequenceTasks : TickMethod {
114+
private ITask _actionAlt;
115+
private Sequence _sequence;
116+
117+
[SetUp]
118+
public void AddNode () {
119+
_sequence = new Sequence();
120+
121+
_actionAlt = Substitute.For<ITask>();
122+
_actionAlt.Enabled.Returns(true);
123+
124+
_tree.AddNode(_tree.Root, _sequence);
125+
_tree.AddNode(_sequence, _action);
126+
_tree.AddNode(_sequence, _actionAlt);
127+
}
128+
129+
[Test]
130+
public void Runs_all_actions () {
131+
_tree.Tick();
132+
133+
_sequence.Children.ForEach((child) => child.Received(1).Update());
134+
}
135+
136+
[Test]
137+
public void Runs_all_actions_again_on_2nd_pass () {
138+
_tree.Tick();
139+
_tree.Tick();
140+
141+
_sequence.Children.ForEach((child) => child.Received(2).Update());
142+
}
143+
144+
[Test]
145+
public void Runs_reset_2x_on_first_action_if_it_fails () {
146+
_action.Update().Returns(TaskStatus.Failure);
147+
148+
_tree.Tick();
149+
_tree.Tick();
150+
151+
_action.Received(1).Reset();
152+
}
153+
154+
[Test]
155+
public void Does_not_run_reset_on_2nd_action_if_1st_fails () {
156+
_action.Update().Returns(TaskStatus.Failure);
157+
158+
_tree.Tick();
159+
_tree.Tick();
160+
161+
_actionAlt.Received(0).Reset();
162+
}
163+
}
164+
}
165+
}
166+
}

Assets/FluidBehaviorTree/Scripts/BehaviorTree/Editor/TreeTest.cs.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: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
using Adnc.FluidBT.TaskParents;
2+
using Adnc.FluidBT.Tasks;
3+
using UnityEngine;
4+
5+
namespace Adnc.FluidBT.Trees {
6+
public class Tree {
7+
private readonly GameObject _owner;
8+
private TaskStatus _lastStatus;
9+
private int _tickCount;
10+
11+
public TaskRoot Root { get; } = new TaskRoot();
12+
13+
public Tree (GameObject owner) {
14+
_owner = owner;
15+
Root.Owner = owner;
16+
}
17+
18+
public void AddNode (ITaskParent parent, ITask child) {
19+
parent.AddChild(child);
20+
child.Owner = _owner;
21+
}
22+
23+
public void Tick () {
24+
_lastStatus = Root.Update();
25+
_tickCount++;
26+
27+
// Possible way to automate triggering reset
28+
// _lastStatus = Root.Update(_tickCount != 0 && _lastStatus != TaskStatus.Continue);
29+
}
30+
}
31+
}

Assets/FluidBehaviorTree/Scripts/BehaviorTree/Tree.cs.meta

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

Assets/FluidBehaviorTree/Scripts/TaskParents/Composites/CompositeBase.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ public abstract class CompositeBase : TaskParentBase {
33
public int ChildIndex { get; protected set; }
44

55
public override void End () {
6-
if (ChildIndex < children.Count) {
7-
children[ChildIndex].End();
6+
if (ChildIndex < Children.Count) {
7+
Children[ChildIndex].End();
88
}
99
}
1010

Assets/FluidBehaviorTree/Scripts/TaskParents/Composites/Editor/CompositeBaseTest.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ public void Does_not_add_disabled_nodes () {
2727

2828
_composite.AddChild(child);
2929

30-
Assert.AreEqual(0, _composite.children.Count);
30+
Assert.AreEqual(0, _composite.Children.Count);
3131
}
3232
}
3333

Assets/FluidBehaviorTree/Scripts/TaskParents/Composites/Editor/ParallelTest.cs

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -30,14 +30,14 @@ public void Returns_success_when_all_children_return_success () {
3030
public void Ticks_all_children_at_once () {
3131
parallel.Update();
3232

33-
parallel.children.ForEach(child => { child.Received(1).Update(); });
33+
parallel.Children.ForEach(child => { child.Received(1).Update(); });
3434
}
3535

3636
[Test]
3737
public void Runs_end_on_all_children_when_complete () {
3838
parallel.Update();
3939

40-
parallel.children.ForEach(child => { child.Received(1).End(); });
40+
parallel.Children.ForEach(child => { child.Received(1).End(); });
4141
}
4242
}
4343

@@ -59,21 +59,21 @@ public void Reruns_continue_tasks () {
5959
parallel.Update();
6060
parallel.Update();
6161

62-
parallel.children[0].Received(2).Update();
62+
parallel.Children[0].Received(2).Update();
6363
}
6464

6565
[Test]
6666
public void Does_not_rerun_a_task_after_it_returns_success () {
6767
parallel.Update();
6868
parallel.Update();
6969

70-
parallel.children[1].Received(1).Update();
70+
parallel.Children[1].Received(1).Update();
7171
}
7272

7373
[Test]
7474
public void Returns_success_when_continue_changes_to_success () {
7575
parallel.Update();
76-
parallel.children[0].Update().Returns(TaskStatus.Success);
76+
parallel.Children[0].Update().Returns(TaskStatus.Success);
7777
parallel.Update();
7878

7979
Assert.AreEqual(TaskStatus.Success, parallel.Update());
@@ -82,10 +82,10 @@ public void Returns_success_when_continue_changes_to_success () {
8282
[Test]
8383
public void Runs_end_on_all_children_after_changing_to_success () {
8484
parallel.Update();
85-
parallel.children[0].Update().Returns(TaskStatus.Success);
85+
parallel.Children[0].Update().Returns(TaskStatus.Success);
8686
parallel.Update();
8787

88-
parallel.children.ForEach(child => { child.Received(1).End(); });
88+
parallel.Children.ForEach(child => { child.Received(1).End(); });
8989
}
9090
}
9191

@@ -106,13 +106,13 @@ public void Returns_failure_if_any_child_returns_failure () {
106106
public void Runs_failed_tasks_after_the_failed_node () {
107107
parallel.Update();
108108

109-
parallel.children[1].Received(1).Update();
109+
parallel.Children[1].Received(1).Update();
110110
}
111111

112112
[Test]
113113
public void Runs_end_on_all_children_when_complete () {
114114
parallel.Update();
115-
parallel.children.ForEach((child) => child.Received(1).End());
115+
parallel.Children.ForEach((child) => child.Received(1).End());
116116
}
117117
}
118118
}
@@ -126,7 +126,7 @@ public void Ends_all_ongoing_tasks () {
126126

127127
parallel.End();
128128

129-
parallel.children.ForEach((child) => child.Received(1).End());
129+
parallel.Children.ForEach((child) => child.Received(1).End());
130130
}
131131
}
132132

@@ -141,7 +141,7 @@ public void Does_not_recall_previous_node_status_after_usage () {
141141
parallel.Reset();
142142
parallel.Update();
143143

144-
parallel.children.ForEach((child) => child.Received(2).Update());
144+
parallel.Children.ForEach((child) => child.Received(2).Update());
145145
}
146146

147147
[Test]
@@ -152,7 +152,7 @@ public void Does_not_trigger_end_on_children () {
152152

153153
parallel.Reset();
154154

155-
parallel.children.ForEach((child) => child.Received(0).End());
155+
parallel.Children.ForEach((child) => child.Received(0).End());
156156
}
157157
}
158158
}

Assets/FluidBehaviorTree/Scripts/TaskParents/Composites/Editor/SelectorTest.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ public void SetSelector () {
1818

1919
public void CheckUpdateCalls (ITaskParent selector, List<int> updateCalls) {
2020
for (var i = 0; i < updateCalls.Count; i++) {
21-
var child = selector.children[i];
21+
var child = selector.Children[i];
2222
if (updateCalls[i] >= 0) {
2323
child.Received(updateCalls[i]).Update();
2424
}

0 commit comments

Comments
 (0)