2019-01-15 13:46:13 -04:00
# include "mode.h"
# include "Plane.h"
bool ModeGuided : : _enter ( )
{
plane . guided_throttle_passthru = false ;
/*
when entering guided mode we set the target as the current
location . This matches the behaviour of the copter code
*/
2022-02-09 19:44:58 -04:00
Location loc { plane . current_loc } ;
2021-06-04 05:35:23 -03:00
2021-09-10 03:28:21 -03:00
# if HAL_QUADPLANE_ENABLED
2021-06-04 05:35:23 -03:00
if ( plane . quadplane . guided_mode_enabled ( ) ) {
/*
if using Q_GUIDED_MODE then project forward by the stopping distance
*/
2022-02-09 19:44:58 -04:00
loc . offset_bearing ( degrees ( plane . ahrs . groundspeed_vector ( ) . angle ( ) ) ,
plane . quadplane . stopping_distance ( ) ) ;
2021-06-04 05:35:23 -03:00
}
2021-09-10 03:28:21 -03:00
# endif
2022-10-10 18:58:30 -03:00
// set guided radius to WP_LOITER_RAD on mode change.
active_radius_m = 0 ;
2022-02-09 19:44:58 -04:00
plane . set_guided_WP ( loc ) ;
2019-01-15 13:46:13 -04:00
return true ;
}
void ModeGuided : : update ( )
{
2021-09-10 03:28:21 -03:00
# if HAL_QUADPLANE_ENABLED
2019-01-15 13:46:13 -04:00
if ( plane . auto_state . vtol_loiter & & plane . quadplane . available ( ) ) {
plane . quadplane . guided_update ( ) ;
2021-09-10 03:28:21 -03:00
return ;
2019-01-15 13:46:13 -04:00
}
2021-09-10 03:28:21 -03:00
# endif
plane . calc_nav_roll ( ) ;
plane . calc_nav_pitch ( ) ;
plane . calc_throttle ( ) ;
2019-01-15 13:46:13 -04:00
}
2020-08-19 04:51:00 -03:00
void ModeGuided : : navigate ( )
2020-07-29 12:01:34 -03:00
{
2022-10-10 18:58:30 -03:00
plane . update_loiter ( active_radius_m ) ;
2020-07-29 12:01:34 -03:00
}
2021-09-27 16:28:39 -03:00
bool ModeGuided : : handle_guided_request ( Location target_loc )
{
// add home alt if needed
2022-02-09 19:44:58 -04:00
if ( target_loc . relative_alt ) {
target_loc . alt + = plane . home . alt ;
target_loc . relative_alt = 0 ;
2021-09-27 16:28:39 -03:00
}
2022-02-09 19:44:58 -04:00
plane . set_guided_WP ( target_loc ) ;
2021-09-27 16:28:39 -03:00
return true ;
}
2022-10-10 18:58:30 -03:00
void ModeGuided : : set_radius_and_direction ( const float radius , const bool direction_is_ccw )
{
// constrain to (uint16_t) range for update_loiter()
active_radius_m = constrain_int32 ( fabsf ( radius ) , 0 , UINT16_MAX ) ;
plane . loiter . direction = direction_is_ccw ? - 1 : 1 ;
}
2022-12-22 15:02:17 -04:00
void ModeGuided : : update_target_altitude ( )
{
# if OFFBOARD_GUIDED == ENABLED
if ( ( ( plane . guided_state . target_alt_time_ms ! = 0 ) | | plane . guided_state . target_alt > - 0.001 ) ) { // target_alt now defaults to -1, and _time_ms defaults to zero.
// offboard altitude demanded
uint32_t now = AP_HAL : : millis ( ) ;
float delta = 1e-3 f * ( now - plane . guided_state . target_alt_time_ms ) ;
plane . guided_state . target_alt_time_ms = now ;
// determine delta accurately as a float
float delta_amt_f = delta * plane . guided_state . target_alt_accel ;
// then scale x100 to match last_target_alt and convert to a signed int32_t as it may be negative
int32_t delta_amt_i = ( int32_t ) ( 100.0 * delta_amt_f ) ;
Location temp { } ;
temp . alt = plane . guided_state . last_target_alt + delta_amt_i ; // ...to avoid floats here,
if ( is_positive ( plane . guided_state . target_alt_accel ) ) {
temp . alt = MIN ( plane . guided_state . target_alt , temp . alt ) ;
} else {
temp . alt = MAX ( plane . guided_state . target_alt , temp . alt ) ;
}
plane . guided_state . last_target_alt = temp . alt ;
plane . set_target_altitude_location ( temp ) ;
plane . altitude_error_cm = plane . calc_altitude_error_cm ( ) ;
} else
# endif // OFFBOARD_GUIDED == ENABLED
{
Mode : : update_target_altitude ( ) ;
}
}