behavior_tree 0.1.10 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: da63d959db3394cf36424a76f36a06d4b30c3ccd97e2f8a0c2dbfabff0b55819
4
- data.tar.gz: d433e361299388c9ad10c2c51f20a71a39dc66927939b748486633f3d3cad645
3
+ metadata.gz: 97c05c7c3c6b0316fe40d4bd20acd66189b3dc34265b45061ac87e7daabd1f15
4
+ data.tar.gz: 6a5ef7dfca3096d744a005aa9e6a60c9c932b69c77c05e63d18be882d010ee44
5
5
  SHA512:
6
- metadata.gz: 4d7bc4c9956c6b9228bff0c87f843543ab933ad1e58a94f47f83421426eebd56cf91d6e15325eef15359716dce0ac56c6fff0aac0b5ba90b18a077d2a02a25f2
7
- data.tar.gz: 53b998db96a7976336ecb1fc3e6e0315def2c97485aeedfb40fd3d03abc1ec654b781e32f7bc1df14a413f9a3ca8fceb83ec3241f46dd3b1db73d2ac0d1e8444
6
+ metadata.gz: d1367b71529a3257493aa12ed119bb05901c5094b24042e9ee86a9ff8a1d422cd97649a7c226e6b88ad32efce17fd1d348864bd328907f0f7ecdb44279da30c8
7
+ data.tar.gz: 5cdc8673bb4927e399ac6a79938114cc26bd178e7fcef71d2b04bd4986728be735c5d3f08f5e5b97557ffd85ae02e24270612e754d61e652ef573cac7e917b82
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- behavior_tree (0.1.10)
4
+ behavior_tree (1.0.0)
5
5
  colorize (~> 0.8.1)
6
6
 
7
7
  GEM
data/README.md CHANGED
@@ -181,6 +181,8 @@ In simple words, it's a modular way to describe your program's control flow, in
181
181
 
182
182
  ### Ticking the tree
183
183
 
184
+ The tick is the most important part of using a behavior tree. When you tick the root node of a tree, it will propagate it by ticking its children, which in turn will tick their children. Tasks (leaf nodes) are executed when the tick reaches them. Non-leaf nodes would execute their own logic when they are ticked (e.g. decoration logic, executing a sequence, etc).
185
+
184
186
  ```ruby
185
187
  my_tree.tick!
186
188
 
@@ -191,7 +193,7 @@ my_tree.tick!
191
193
 
192
194
  Each node has a status, which can have three possible values:
193
195
 
194
- 1. `success` which is usually returned by a task when it completes successfully, by conditional nodes when the condition they evaluate is true, or when nodes have never been set to run. Since this is the default status of all nodes, a node is in `success` status if it has never been ticked, or if it has been halted (using `halt!`).
196
+ 1. `success` which is returned in certain situations depending on the node type, but usually indicating that the operation they are in charge of was completed. Tasks usually return `success` when they execute/complete successfully, sequences return `success` when the entire sequence is executed successfully, and so on. Since this is the default status of all nodes, a node is in `success` status if it has never been ticked, or if it has been halted (using `halt!`).
195
197
  2. `running` which is returned by nodes that are currently executing.
196
198
  3. `failure` which is returned to signal that execution failed.
197
199
 
@@ -259,11 +261,11 @@ end
259
261
 
260
262
  #### Control nodes
261
263
 
262
- A control node decides the flow of the execution. In simpler words, it uses a certain logic to decide which branch to execute. This is where most of the similarities with a simple `if-else` come from.
264
+ A control node decides the flow of the execution. In simpler words, it uses a certain logic to decide which branch to execute. It could be one branch, multiple branches, or all of them.
263
265
 
264
266
  A control node cannot be a leaf (i.e. it must have children).
265
267
 
266
- There are two types of control nodes, and custom ones can be easily created ([see examples of custom control nodes](#custom-control-node)).
268
+ By default, there are two types of control nodes, and custom ones can be easily created. (See: [Examples of custom control nodes](#custom-control-node)).
267
269
 
268
270
  1. **Sequence:**
269
271
  a. Begins executing the first child node.
@@ -327,7 +329,7 @@ By default the decorator nodes present in this library are:
327
329
  | Repeater | `BehaviorTree::Decorators::Repeater` | `repeater` or `rep` | Ticks the child again N times while it's returning `success`. |
328
330
  | Retry | `BehaviorTree::Decorators::Retry` | `re_try` | Ticks the child again N times while it's returning `failure`. |
329
331
 
330
- **Example #1: Creating a tree with many decorators**
332
+ **Example #1: Creating a tree with some decorators**
331
333
 
332
334
  ```ruby
333
335
  my_tree = BehaviorTree::Builder.build do
@@ -523,7 +525,7 @@ class AllOrNothing < ControlNodeBase
523
525
  end
524
526
  ```
525
527
 
526
- Note that under the hood, `tick_each_children` uses the strategy defined (i.e. `shuffle` method), and traverses its children while also ticking them. You don't need to send `tick!` manually to the child. The code defined in `on_tick` is executed *right after* the child is ticked.
528
+ Note that under the hood, `tick_each_children` uses the strategy defined (i.e. `shuffle` method), and traverses its children while also ticking them. You don't need to send `tick!` manually to the child. The code in the block given to `tick_each_children` is executed *right after* the child is ticked.
527
529
 
528
530
  ### Custom decorator
529
531
 
@@ -560,7 +562,7 @@ class CustomCondition < BehaviorTree::Decorators::Condition
560
562
  end
561
563
  ```
562
564
 
563
- Or using inline logic in the DSL. When using the DSL, before starting the block (i.e. where the child is defined), you must pass a `lambda` which receives two parameters (both optional), `context` and `node` (the `self` of the condition node).
565
+ Or create condition nodes using inline lambdas in the DSL. When using the DSL, before starting the block (i.e. where the child is defined), you must pass a `lambda` which receives two parameters (both optional), `context` and `node` (which is the `self` of the condition node).
564
566
 
565
567
  ```ruby
566
568
  my_tree = BehaviorTree::Builder.build do
@@ -583,7 +585,7 @@ my_tree.print
583
585
  # └─task success (0 ticks)
584
586
  ```
585
587
 
586
- **Note:** Other behavior tree implementations prefer the use of `sequence` control nodes, and placing conditional nodes as a leaves, but with the role of simply returning `failure` or `success`. Since sequences execute the next node only if the previous one succeeded, this also works as a conditional node. In this implementation, however, both patterns are available and you are free to choose which one to use.
588
+ **Note:** Other behavior tree implementations prefer the use of `sequence` control nodes, and placing conditional nodes as leaves, but with the role of simply returning `failure` or `success`. Since sequences execute the next node only if the previous one succeeded, it would also behave like a conditional node, preventing the next nodes in the sequence from executing if the condition failed. In this implementation, however, both patterns are available and you are free to choose which one to use.
587
589
 
588
590
  ## Node API
589
591
 
@@ -698,12 +700,16 @@ The second line of the output is the `puts` of the actual task logic. The third
698
700
 
699
701
  **on_started_running**
700
702
 
701
- Similar to `on_status_change`, but only triggers when the node has been set to `running`.
703
+ Similar to `on_status_change`, but only triggers when the node has been set to `running` (changed from a status other than `running`.
704
+
705
+ In some implementations, this is called `initialization`.
702
706
 
703
707
  **on_finished_running**
704
708
 
705
709
  Similar to `on_status_change`, but only triggers when the node has been set to a status other than `running`.
706
710
 
711
+ In some implementations, this is called `shutdown`.
712
+
707
713
  ## Add custom nodes to the DSL
708
714
 
709
715
  You can register new nodes to be used in the DSL, take for example the following code:
@@ -5,15 +5,21 @@ module BehaviorTree
5
5
  # If there's at least one node with 'running' status, then iterate starting from there, in order.
6
6
  # Else, iterate all nodes.
7
7
  module PrioritizeRunning
8
+ private
9
+
8
10
  def prioritize_running
9
- idx = @children.find_index { |child| child.status.running? }.to_i
11
+ @first_running_idx = children.find_index { |child| child.status.running? }.to_i if must_recompute_idx?
10
12
 
11
13
  Enumerator.new do |y|
12
- @children[idx..].each do |child|
14
+ children[@first_running_idx..].each do |child|
13
15
  y << child
14
16
  end
15
17
  end
16
18
  end
19
+
20
+ def must_recompute_idx?
21
+ !@first_running_idx || !children[@first_running_idx].status.running?
22
+ end
17
23
  end
18
24
  end
19
25
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module BehaviorTree
4
- VERSION = '0.1.10'
4
+ VERSION = '1.0.0'
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: behavior_tree
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.10
4
+ version: 1.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Felo Vilches
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-07-16 00:00:00.000000000 Z
11
+ date: 2021-07-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: colorize