@@ -50,45 +50,33 @@ impl Autonomy {
5050}
5151
5252pub fn autonomy ( ) -> impl Behavior < LunabotBlackboard > {
53- ParallelAny :: new ( (
54- Sequence :: new ( (
53+ WhileLoop :: new (
54+ |blackboard : & mut LunabotBlackboard | ( * blackboard. get_autonomy ( ) != Autonomy :: None ) . into ( ) ,
55+ ParallelAny :: new ( (
5556 AssertCancelSafe ( |blackboard : & mut LunabotBlackboard | {
56- blackboard. get_path_mut ( ) . clear ( ) ;
57- let pos = blackboard. get_robot_isometry ( ) . translation ;
58- let pos = Point3 :: new ( pos. x , pos. y , pos. z ) ;
59- blackboard. get_path_mut ( ) . extend_from_slice ( & [
60- pos,
61- // Point3::new(-0.9144, 0.0, -1.905),
62- Point3 :: new ( 1.905 , 0.0 , -1.5 ) ,
63- Point3 :: new ( 1.27 , 0.0 , -0.5 ) ,
64- ] ) ;
65- println ! ( "set path" , ) ;
66- Status :: Success
57+ if * blackboard. lunabase_disconnected ( ) {
58+ error ! ( "Lunabase disconnected" ) ;
59+ return Status :: Failure ;
60+ }
61+ while let Some ( msg) = blackboard. peek_from_lunabase ( ) {
62+ match msg {
63+ FromLunabase :: Steering ( _) => {
64+ * blackboard. get_autonomy ( ) = Autonomy :: None ;
65+ warn ! ( "Received steering message while in autonomy mode" ) ;
66+ return Status :: Success ;
67+ }
68+ FromLunabase :: SoftStop => {
69+ blackboard. pop_from_lunabase ( ) ;
70+ return Status :: Failure ;
71+ }
72+ _ => blackboard. pop_from_lunabase ( ) ,
73+ } ;
74+ }
75+ Status :: Running
6776 } ) ,
68- ares_bt :: converters :: InfallibleShim ( AssertCancelSafe ( follow_path ) )
77+ Sequence :: new ( ( dig ( ) , dump ( ) , traverse ( ) ) ) ,
6978 ) ) ,
70- AssertCancelSafe ( |blackboard : & mut LunabotBlackboard | {
71- if * blackboard. lunabase_disconnected ( ) {
72- error ! ( "Lunabase disconnected" ) ;
73- return Status :: Failure ;
74- }
75- while let Some ( msg) = blackboard. peek_from_lunabase ( ) {
76- match msg {
77- FromLunabase :: Steering ( _) => {
78- * blackboard. get_autonomy ( ) = Autonomy :: None ;
79- warn ! ( "Received steering message while in autonomy mode" ) ;
80- return Status :: Success ;
81- }
82- FromLunabase :: SoftStop => {
83- blackboard. pop_from_lunabase ( ) ;
84- return Status :: Failure ;
85- }
86- _ => blackboard. pop_from_lunabase ( ) ,
87- } ;
88- }
89- Status :: Running
90- } ) ,
91- ) )
79+ )
9280}
9381
9482fn follow_path ( blackboard : & mut LunabotBlackboard ) -> InfallibleStatus {
@@ -104,7 +92,6 @@ fn follow_path(blackboard: &mut LunabotBlackboard) -> InfallibleStatus {
10492
10593 match find_target_point ( pos, path) {
10694 Some ( target) => {
107- println ! ( "going to {} from {}" , target, pos) ;
10895 let heading_angle = heading. angle ( & Vector2 :: new ( 0.0 , -1.0 ) ) ;
10996 let to_first_point = ( target - pos) . normalize ( ) ;
11097
@@ -117,34 +104,16 @@ fn follow_path(blackboard: &mut LunabotBlackboard) -> InfallibleStatus {
117104
118105 * blackboard. get_poll_when ( ) =
119106 PollWhen :: Instant ( Instant :: now ( ) + Duration :: from_millis ( 16 ) ) ;
120- // PollWhen::Instant(Instant::now());
121-
122- // We reborrow path so that we can mutably access get_poll_when
123- // let path = blackboard.get_path_mut();
124107
125- // when approaching an arc turn gradually
126- // if distance(&pos, &target) < ARC_THRESHOLD { // && within_arc(path, target) {
127- // let (l, r) = scaled_clamp(
128- // -to_first_point.y + to_first_point.x,
129- // -to_first_point.y - to_first_point.x,
130- // 1,
131- // );
132- // blackboard.enqueue_action(Action::SetSteering(Steering::new_left_right(l, r)));
133- // return InfallibleStatus::Running;
134- // }
135- println ! ( "angle {} to next pt {}" , to_first_point. angle( & Vector2 :: new( 0.0 , -1.0 ) ) , to_first_point) ;
136108 if to_first_point. angle ( & Vector2 :: new ( 0.0 , -1.0 ) ) . to_degrees ( ) > 20.0 {
137109 if to_first_point. x > 0.0 {
138- println ! ( "turning right" , ) ;
139110 blackboard
140111 . enqueue_action ( Action :: SetSteering ( Steering :: new_left_right ( 1.0 , -1.0 ) ) )
141112 } else {
142- println ! ( "turning left" , ) ;
143113 blackboard
144114 . enqueue_action ( Action :: SetSteering ( Steering :: new_left_right ( -1.0 , 1.0 ) ) )
145115 }
146116 } else {
147- println ! ( "straight ahead " , ) ;
148117 let ( l, r) = scaled_clamp (
149118 -to_first_point. y + to_first_point. x * 1.2 ,
150119 -to_first_point. y - to_first_point. x * 1.2 ,
@@ -174,52 +143,15 @@ fn find_target_point(pos: Point2<f64>, path: &mut Vec<OPoint<f64, Const<3>>>) ->
174143 return None ;
175144 }
176145
177- // if the robot is near any point, delete all previous points
178- for ( i, point) in path. iter ( ) . enumerate ( ) . rev ( ) {
179- if distance ( & point. xz ( ) , & pos) < AT_POINT_THRESHOLD {
180- println ! ( "path follower: made it to point {}" , point) ;
181-
182- // let res = Some(path[i+1].xz());
183- path. drain ( 0 ..=i) ;
146+ let first_point = path[ 0 ] . xz ( ) ;
184147
185- println ! ( "drained path to {:?}" , path) ;
186- return Some ( path[ 0 ] . xz ( ) ) ;
187- }
148+ // if the robot is near the first point, delete it
149+ if distance ( & first_point, & pos) < AT_POINT_THRESHOLD {
150+ path. remove ( 0 ) ;
151+ return Some ( path[ 0 ] . xz ( ) ) ;
188152 }
189- //TODO: repeat for line segments
190-
191- Some ( path[ 0 ] . xz ( ) )
192-
193- // let mut min_dist = distance(&pos, &path[0].xz());
194- // let mut res = path[0].xz();
195153
196- // for i in 1..path.len() {
197- // let dist = dist_to_segment(pos, path[i - 1].xz(), path[i].xz());
198-
199- // if dist < min_dist {
200- // min_dist = dist;
201- // res = path[i].xz();
202- // }
203- // }
204- }
205-
206- fn dist_to_segment ( point : Point2 < f64 > , a : Point2 < f64 > , b : Point2 < f64 > ) -> f64 {
207- let mut line_from_origin = b - a; // move line segment to origin
208- let mut point = point - a; // move point the same amount
209-
210- let angle = -line_from_origin. y . signum ( ) * line_from_origin. angle ( & Vector2 :: new ( 1.0 , 0.0 ) ) ;
211-
212- // rotate both until segment lines up with the x axis
213- line_from_origin = rotate_v2_ccw ( line_from_origin, angle) ;
214- point = rotate_v2_ccw ( point, angle) ;
215-
216- return if point. x <= 0.0 {
217- point. magnitude ( )
218- } else if point. x >= line_from_origin. x {
219- ( point - Vector2 :: new ( line_from_origin. x , 0.0 ) ) . magnitude ( )
220- } else {
221- point. y . abs ( )
222- } ;
154+ Some ( first_point)
223155}
224156
225157fn rotate_v2_ccw ( vector2 : Vector2 < f64 > , theta : f64 ) -> Vector2 < f64 > {
@@ -232,20 +164,6 @@ fn rotate_v2_ccw(vector2: Vector2<f64>, theta: f64) -> Vector2<f64> {
232164 return rot * vector2;
233165}
234166
235- /// min distance for 2 path points to be considered part of an arc
236- const ARC_THRESHOLD : f64 = 0.3 ;
237-
238- /// is this point considered part of an arc?
239- fn within_arc ( path : & [ Point3 < f64 > ] , i : usize ) -> bool {
240- if path. len ( ) == 1 {
241- false
242- } else if i == path. len ( ) - 1 {
243- distance ( & path[ i] . xz ( ) , & path[ i - 1 ] . xz ( ) ) < ARC_THRESHOLD
244- } else {
245- distance ( & path[ i] . xz ( ) , & path[ i + 1 ] . xz ( ) ) < ARC_THRESHOLD
246- }
247- }
248-
249167/// clamps `a` and `b` so that `a.abs().max(b.abs) <= bound.abs()`,
250168/// while maintaining the ratio between `a` and `b`
251169fn scaled_clamp ( a : f64 , b : f64 , bound : f64 ) -> ( f64 , f64 ) {
0 commit comments