parallel_all_node.cpp
Go to the documentation of this file.
1 /* Copyright (C) 2023 Davide Faconti - All Rights Reserved
2 *
3 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"),
4 * to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense,
5 * and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
6 * The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
9 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
10 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
11 */
12 
13 #include <algorithm>
14 #include <cstddef>
15 
17 
18 namespace BT
19 {
20 
21 ParallelAllNode::ParallelAllNode(const std::string& name, const NodeConfig& config)
22  : ControlNode::ControlNode(name, config), failure_threshold_(1)
23 {}
24 
26 {
27  int max_failures = 0;
28  if(!getInput("max_failures", max_failures))
29  {
30  throw RuntimeError("Missing parameter [max_failures] in ParallelNode");
31  }
32  const size_t children_count = children_nodes_.size();
33  setFailureThreshold(max_failures);
34 
35  size_t skipped_count = 0;
36 
37  if(children_count < failure_threshold_)
38  {
39  throw LogicError("Number of children is less than threshold. Can never fail.");
40  }
41 
43 
44  // Routing the tree according to the sequence node's logic:
45  for(size_t index = 0; index < children_count; index++)
46  {
47  TreeNode* child_node = children_nodes_[index];
48 
49  // already completed
50  if(completed_list_.count(index) != 0)
51  {
52  continue;
53  }
54 
55  NodeStatus const child_status = child_node->executeTick();
56 
57  switch(child_status)
58  {
59  case NodeStatus::SUCCESS: {
60  completed_list_.insert(index);
61  }
62  break;
63 
64  case NodeStatus::FAILURE: {
65  completed_list_.insert(index);
67  }
68  break;
69 
70  case NodeStatus::RUNNING: {
71  // Still working. Check the next
72  }
73  break;
74 
75  case NodeStatus::SKIPPED: {
76  skipped_count++;
77  }
78  break;
79 
80  case NodeStatus::IDLE: {
81  throw LogicError("[", name(), "]: A children should not return IDLE");
82  }
83  }
84  }
85 
86  if(skipped_count == children_count)
87  {
88  return NodeStatus::SKIPPED;
89  }
90  if(skipped_count + completed_list_.size() >= children_count)
91  {
92  // DONE
93  haltChildren();
94  completed_list_.clear();
97  failure_count_ = 0;
98  return status;
99  }
100 
101  // Some children haven't finished, yet.
102  return NodeStatus::RUNNING;
103 }
104 
106 {
107  completed_list_.clear();
108  failure_count_ = 0;
110 }
111 
113 {
114  return failure_threshold_;
115 }
116 
118 {
119  if(threshold < 0)
120  {
121  failure_threshold_ = size_t(std::max(int(children_nodes_.size()) + threshold + 1, 0));
122  }
123  else
124  {
125  failure_threshold_ = size_t(threshold);
126  }
127 }
128 
129 } // namespace BT
BT::TreeNode::getInput
Result getInput(const std::string &key, T &destination) const
Definition: tree_node.h:547
BT
Definition: ex01_wrap_legacy.cpp:29
BT::ParallelAllNode::failure_threshold_
size_t failure_threshold_
Definition: parallel_all_node.h:54
BT::ParallelAllNode::completed_list_
std::set< size_t > completed_list_
Definition: parallel_all_node.h:56
BT::TreeNode::executeTick
virtual BT::NodeStatus executeTick()
The method that should be used to invoke tick() and setStatus();.
Definition: tree_node.cpp:71
BT::ParallelAllNode::tick
virtual BT::NodeStatus tick() override
Method to be implemented by the user.
Definition: parallel_all_node.cpp:25
BT::TreeNode
Abstract base class for Behavior Tree Nodes.
Definition: tree_node.h:118
BT::ControlNode::children_nodes_
std::vector< TreeNode * > children_nodes_
Definition: control_node.h:24
BT::LogicError
Definition: exceptions.h:45
BT::ParallelAllNode::setFailureThreshold
void setFailureThreshold(int threshold)
Definition: parallel_all_node.cpp:117
BT::TreeNode::status
NodeStatus status() const
Definition: tree_node.cpp:279
BT::NodeStatus::FAILURE
@ FAILURE
BT::TreeNode::setStatus
void setStatus(NodeStatus new_status)
setStatus changes the status of the node. it will throw if you try to change the status to IDLE,...
Definition: tree_node.cpp:154
BT::NodeStatus::SKIPPED
@ SKIPPED
BT::ParallelAllNode::failure_count_
size_t failure_count_
Definition: parallel_all_node.h:57
BT::RuntimeError
Definition: exceptions.h:58
BT::ParallelAllNode::ParallelAllNode
ParallelAllNode(const std::string &name, const NodeConfig &config)
Definition: parallel_all_node.cpp:21
BT::TreeNode::name
const std::string & name() const
Name of the instance, not the type.
Definition: tree_node.cpp:296
BT::NodeStatus::SUCCESS
@ SUCCESS
BT::NodeStatus::RUNNING
@ RUNNING
BT::ParallelAllNode::halt
virtual void halt() override
Definition: parallel_all_node.cpp:105
BT::ControlNode::haltChildren
void haltChildren()
same as resetChildren()
Definition: control_node.cpp:65
BT::NodeStatus::IDLE
@ IDLE
BT::ControlNode::halt
virtual void halt() override
Definition: control_node.cpp:32
BT::NodeConfig
Definition: tree_node.h:73
BT::ControlNode
Definition: control_node.h:21
BT::NodeStatus
NodeStatus
Definition: basic_types.h:33
parallel_all_node.h
BT::ParallelAllNode::failureThreshold
size_t failureThreshold() const
Definition: parallel_all_node.cpp:112


behaviortree_cpp_v4
Author(s): Davide Faconti
autogenerated on Fri Jun 28 2024 02:20:07