From 7bbc7d5fbea204825fee3bb2d49f42d2a6b0258a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Kat=20March=C3=A1n?= <kzm@zkat.tech>
Date: Fri, 14 Jan 2022 22:22:36 -0800
Subject: [PATCH] doc: update docs for new API stuff

---
 README.md      | 66 ++++++++++++++----------------------
 src/actions.rs | 34 ++++++++++++++-----
 src/lib.rs     | 92 ++++++++++++++++++++------------------------------
 src/scorers.rs | 34 +++++++++----------
 4 files changed, 103 insertions(+), 123 deletions(-)

diff --git a/README.md b/README.md
index 676a5d5..9f838bc 100644
--- a/README.md
+++ b/README.md
@@ -27,40 +27,22 @@ See [the documentation](https://docs.rs/big-brain) for more details.
 
 ### Example
 
-First, you define actions and considerations, which are just plain old Bevy
-Components and Systems. As a developer, you write application-dependent code
-to define [`Scorers`](#scorers) and [`Actions`](#actions), and then put it
-all together like building blocks, using [`Thinkers`](#thinkers) that will
-define the actual behavior.
+As a developer, you write application-dependent code to define
+[`Scorers`](#scorers) and [`Actions`](#actions), and then put it all together
+like building blocks, using [`Thinkers`](#thinkers) that will define the
+actual behavior.
 
 #### Scorers
 
 `Scorer`s are entities that look at the world and evaluate into [`Score`](scorers::Score) values. You can think of them as the "eyes" of the AI system. They're a highly-parallel way of being able to look at the `World` and use it to make some decisions later.
 
-They are created by types that implement [`ScorerBuilder`](scorers::ScorerBuilder).
-
 ```rust
 use bevy::prelude::*;
 use big_brain::prelude::*;
 
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Component)]
 pub struct Thirsty;
 
-impl Thirsty {
-    fn build() -> ThirstyBuilder {
-        ThirstyBuilder
-    }
-}
-
-#[derive(Debug, Clone)]
-pub struct ThirstyBuilder;
-
-impl ScorerBuilder for ThirstyBuilder {
-    fn build(&self, cmd: &mut Commands, scorer: Entity, _actor: Entity) {
-        cmd.entity(scorer).insert(Thirsty);
-    }
-}
-
 pub fn thirsty_scorer_system(
     thirsts: Query<&Thirst>,
     mut query: Query<(&Actor, &mut Score), With<Thirsty>>,
@@ -75,30 +57,17 @@ pub fn thirsty_scorer_system(
 
 #### Actions
 
-`Action`s are the actual things your entities will _do_. They are connected to [`ActionState`](actions::ActionState)s, and are created by types implementing [`ActionBuilder`](actions::ActionBuilder).
+`Action`s are the actual things your entities will _do_. They are connected to
+[`ActionState`](actions::ActionState)s that represent the current execution
+state of the state machine.
 
 ```rust
 use bevy::prelude::*;
 use big_brain::prelude::*;
 
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Component)]
 pub struct Drink;
 
-impl Drink {
-    pub fn build() -> DrinkBuilder {
-        DrinkBuilder
-    }
-}
-
-#[derive(Debug, Clone)]
-pub struct DrinkBuilder;
-
-impl ActionBuilder for DrinkBuilder {
-    fn build(&self, cmd: &mut Commands, action: Entity, _actor: Entity) {
-        cmd.entity(action).insert(Drink);
-    }
-}
-
 fn drink_action_system(
     mut thirsts: Query<&mut Thirst>,
     mut query: Query<(&Actor, &mut ActionState), With<Drink>>,
@@ -129,10 +98,25 @@ regular Component:
 cmd.spawn().insert(Thirst::new(70.0, 2.0)).insert(
     Thinker::build()
         .picker(FirstToScore { threshold: 0.8 })
-        .when(Thirsty::build(), Drink::build()),
+        .when(Thirsty, Drink),
 );
 ```
 
+#### App
+
+Once all that's done, we just add our systems and off we go!
+
+```rust
+App::new()
+    .add_plugins(DefaultPlugins)
+    .add_plugin(BigBrainPlugin)
+    .add_startup_system(init_entities)
+    .add_system(thirst_system)
+    .add_system_to_stage(BigBrainStage::Actions, drink_action_system)
+    .add_system_to_stage(BigBrainStage::Scorers, thirsty_scorer_system)
+    .run();
+```
+
 ### Contributing
 
 1. Install the latest Rust toolchain (stable supported).
diff --git a/src/actions.rs b/src/actions.rs
index 609bdf7..0d6d5db 100644
--- a/src/actions.rs
+++ b/src/actions.rs
@@ -64,18 +64,34 @@ impl ActionBuilderWrapper {
 }
 
 /**
-Trait that must be defined by types in order to be `ActionBuilder`s. `ActionBuilder`s' job is to spawn new `Action` entities. In general, most of this is already done for you, and the only method you really have to implement is `.build()`.
+Trait that must be defined by types in order to be `ActionBuilder`s. `ActionBuilder`s' job is to spawn new `Action` entities on demand. In general, most of this is already done for you, and the only method you really have to implement is `.build()`.
 
 The `build()` method MUST be implemented for any `ActionBuilder`s you want to define.
 */
 pub trait ActionBuilder: std::fmt::Debug + Send + Sync {
     /**
-    MUST insert your concrete Action component into the `action` [`Entity`], using `cmd`. You _may_ use `actor`, but it's perfectly normal to just ignore it.
+
+    MUST insert your concrete Action component into the Scorer [`Entity`], using
+     `cmd`. You _may_ use `actor`, but it's perfectly normal to just ignore it.
+
+    Note that this method is automatically implemented for any Components that
+    implement Clone, so you don't need to define it yourself unless you want
+    more complex parameterization of your Actions.
 
     ### Example
 
+    Using `Clone` (the easy way):
+
+    ```no_run
+    #[derive(Debug, Clone, Component)]
+    struct MyAction;
+    ```
+
+    Implementing it manually:
+
     ```no_run
     struct MyBuilder;
+    #[derive(Debug, Component)]
     struct MyAction;
 
     impl ActionBuilder for MyBuilder {
@@ -155,8 +171,8 @@ Thinker::build()
     .when(
         MyScorer,
         Steps::build()
-            .step(MyAction::build())
-            .step(MyNextAction::build())
+            .step(MyAction)
+            .step(MyNextAction)
         )
 ```
 */
@@ -247,7 +263,7 @@ pub fn steps_system(
 }
 
 /**
-[`ActionBuilder`] for the [`Concurrent`] component. Constructed through `Concurrent::build()`.
+[`ActionBuilder`] for the [`Concurrently`] component. Constructed through `Concurrently::build()`.
 */
 #[derive(Debug)]
 pub struct ConcurrentlyBuilder {
@@ -292,8 +308,8 @@ Thinker::build()
     .when(
         MyScorer,
         Concurrent::build()
-            .push(MyAction::build())
-            .push(MyOtherAction::build())
+            .push(MyAction)
+            .push(MyOtherAction)
         )
 ```
 */
@@ -304,7 +320,7 @@ pub struct Concurrently {
 
 impl Concurrently {
     /**
-    Construct a new [`ConcurrentBuilder`] to define the actions to take.
+    Construct a new [`ConcurrentlyBuilder`] to define the actions to take.
     */
     pub fn build() -> ConcurrentlyBuilder {
         ConcurrentlyBuilder {
@@ -314,7 +330,7 @@ impl Concurrently {
 }
 
 /**
-System that takes care of executing any existing [`Concurrent`] Actions.
+System that takes care of executing any existing [`Concurrently`] Actions.
 */
 pub fn concurrent_system(
     concurrent_q: Query<(Entity, &Concurrently)>,
diff --git a/src/lib.rs b/src/lib.rs
index 9959c6f..3b11456 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -11,7 +11,7 @@ behavior.
 
 See [the documentation](https://docs.rs/big-brain) for more details.
 
-## Features
+### Features
 
 * Highly concurrent/parallelizable evaluation.
 * Integrates smoothly with Bevy.
@@ -24,42 +24,24 @@ See [the documentation](https://docs.rs/big-brain) for more details.
 * State machine-style continuous actions/behaviors.
 * Action cancellation.
 
-## Example
+### Example
 
-First, you define actions and considerations, which are just plain old Bevy
-Components and Systems. As a developer, you write application-dependent code
-to define [`Scorers`](#scorers) and [`Actions`](#actions), and then put it
-all together like building blocks, using [`Thinkers`](#thinkers) that will
-define the actual behavior.
+As a developer, you write application-dependent code to define
+[`Scorers`](#scorers) and [`Actions`](#actions), and then put it all together
+like building blocks, using [`Thinkers`](#thinkers) that will define the
+actual behavior.
 
-### Scorers
+#### Scorers
 
 `Scorer`s are entities that look at the world and evaluate into [`Score`](scorers::Score) values. You can think of them as the "eyes" of the AI system. They're a highly-parallel way of being able to look at the `World` and use it to make some decisions later.
 
-They are created by types that implement [`ScorerBuilder`](scorers::ScorerBuilder).
-
-```
+```rust
 use bevy::prelude::*;
 use big_brain::prelude::*;
 
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Component)]
 pub struct Thirsty;
 
-impl Thirsty {
-    fn build() -> ThirstyBuilder {
-        ThirstyBuilder
-    }
-}
-
-#[derive(Debug, Clone)]
-pub struct ThirstyBuilder;
-
-impl ScorerBuilder for ThirstyBuilder {
-    fn build(&self, cmd: &mut Commands, scorer: Entity, _actor: Entity) {
-        cmd.entity(scorer).insert(Thirsty);
-    }
-}
-
 pub fn thirsty_scorer_system(
     thirsts: Query<&Thirst>,
     mut query: Query<(&Actor, &mut Score), With<Thirsty>>,
@@ -72,32 +54,19 @@ pub fn thirsty_scorer_system(
 }
 ```
 
-### Actions
+#### Actions
 
-`Action`s are the actual things your entities will _do_. They are connected to [`ActionState`](actions::ActionState)s, and are created by types implementing [`ActionBuilder`](actions::ActionBuilder).
+`Action`s are the actual things your entities will _do_. They are connected to
+[`ActionState`](actions::ActionState)s that represent the current execution
+state of the state machine.
 
-```
+```rust
 use bevy::prelude::*;
 use big_brain::prelude::*;
 
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Component)]
 pub struct Drink;
 
-impl Drink {
-    pub fn build() -> DrinkBuilder {
-        DrinkBuilder
-    }
-}
-
-#[derive(Debug, Clone)]
-pub struct DrinkBuilder;
-
-impl ActionBuilder for DrinkBuilder {
-    fn build(&self, cmd: &mut Commands, action: Entity, _actor: Entity) {
-        cmd.entity(action).insert(Drink);
-    }
-}
-
 fn drink_action_system(
     mut thirsts: Query<&mut Thirst>,
     mut query: Query<(&Actor, &mut ActionState), With<Drink>>,
@@ -119,32 +88,43 @@ fn drink_action_system(
 }
 ```
 
-### Thinkers
+#### Thinkers
 
 Finally, you can use it when define the [`Thinker`](thinker::Thinker), which you can attach as a
 regular Component:
 
-```no_run
+```rust
 cmd.spawn().insert(Thirst::new(70.0, 2.0)).insert(
     Thinker::build()
         .picker(FirstToScore { threshold: 0.8 })
-        .when(Thirsty::build(), Drink::build()),
+        .when(Thirsty, Drink),
 );
 ```
 
-## Contributing
+#### App
+
+Once all that's done, we just add our systems and off we go!
+
+```rust
+App::new()
+    .add_plugins(DefaultPlugins)
+    .add_plugin(BigBrainPlugin)
+    .add_startup_system(init_entities)
+    .add_system(thirst_system)
+    .add_system_to_stage(BigBrainStage::Actions, drink_action_system)
+    .add_system_to_stage(BigBrainStage::Scorers, thirsty_scorer_system)
+    .run();
+```
+
+### Contributing
 
 1. Install the latest Rust toolchain (stable supported).
 2. `cargo run --example thirst`
 3. Happy hacking!
 
-## License
-
-This project is licensed under [the Parity License](LICENSE.md). Third-party contributions are licensed under Apache-2.0 and belong to their respective authors.
-
-The Parity License is a copyleft license that, unlike the GPL family, allows you to license derivative and connected works under permissive licenses like MIT or Apache-2.0. It's free to use provided the work you do is freely available!
+### License
 
-For proprietary use, please [contact me](mailto:kzm@zkat.tech?subject=big-brain%20license), or just [sponsor me on GitHub](https://github.com/users/zkat/sponsorship) under the appropriate tier to [acquire a proprietary-use license](LICENSE-PATRON.md)! This funding model helps me make my work sustainable and compensates me for the work it took to write this crate!
+This project is licensed under [the Apache-2.0 License](LICENSE.md).
 
 */
 
diff --git a/src/scorers.rs b/src/scorers.rs
index 12fd5af..a6ec194 100644
--- a/src/scorers.rs
+++ b/src/scorers.rs
@@ -46,12 +46,27 @@ The `build()` method MUST be implemented for any `ScorerBuilder`s you want to de
 */
 pub trait ScorerBuilder: std::fmt::Debug + Sync + Send {
     /**
-    MUST insert your concrete Scorer component into the Scorer [`Entity`], using `cmd`. You _may_ use `actor`, but it's perfectly normal to just ignore it.
+    MUST insert your concrete Scorer component into the Scorer [`Entity`], using
+     `cmd`. You _may_ use `actor`, but it's perfectly normal to just ignore it.
+
+    Note that this method is automatically implemented for any Components that
+    implement Clone, so you don't need to define it yourself unless you want
+    more complex parameterization of your Actions.
 
     ### Example
 
+    Using `Clone` (the easy way):
+
+    ```no_run
+    #[derive(Debug, Clone, Component)]
+    struct MyScorer;
+    ```
+
+    Implementing it manually:
+
     ```no_run
     struct MyBuilder;
+    #[derive(Debug, Component)]
     struct MyScorer;
 
     impl ScorerBuilder for MyBuilder {
@@ -91,27 +106,12 @@ Scorer that always returns the same, fixed score. Good for combining with things
 #[derive(Clone, Component, Debug)]
 pub struct FixedScore(f32);
 
-impl FixedScore {
-    pub fn build(score: f32) -> FixedScoreBuilder {
-        FixedScoreBuilder(score)
-    }
-}
-
 pub fn fixed_score_system(mut query: Query<(&FixedScore, &mut Score)>) {
     for (FixedScore(fixed), mut score) in query.iter_mut() {
         score.set(*fixed);
     }
 }
 
-#[derive(Clone, Component, Debug)]
-pub struct FixedScoreBuilder(f32);
-
-impl ScorerBuilder for FixedScoreBuilder {
-    fn build(&self, cmd: &mut Commands, action: Entity, _actor: Entity) {
-        cmd.entity(action).insert(FixedScore(self.0));
-    }
-}
-
 /**
 Composite Scorer that takes any number of other Scorers and returns the sum of their [`Score`] values if each _individual_ [`Score`] is at or above the configured `threshold`.
 
@@ -385,7 +385,7 @@ unlike other composite scorers, `EvaluatingScorer` only takes one scorer upon bu
 Thinker::build()
     .when(
         EvaluatingScorer::build(MyScorer, MyEvaluator),
-        MyAction::build());
+        MyAction);
 ```
  */
 #[derive(Clone, Component, Debug)]
-- 
GitLab