diff --git a/docs/Settings.md b/docs/Settings.md index 82c1399d219..b24760adcc4 100644 --- a/docs/Settings.md +++ b/docs/Settings.md @@ -356,6 +356,7 @@ | nav_position_timeout | 5 | If GPS fails wait for this much seconds before switching to emergency landing mode (0 - disable) | | nav_rth_abort_threshold | 50000 | RTH sanity checking feature will notice if distance to home is increasing during RTH and once amount of increase exceeds the threshold defined by this parameter, instead of continuing RTH machine will enter emergency landing, self-level and go down safely. Default is 500m which is safe enough for both multirotor machines and airplanes. [cm] | | nav_rth_allow_landing | ALWAYS | If set to ON drone will land as a last phase of RTH. | +| nav_rth_alt_control_override | OFF | If set to ON RTH altitude and CLIMB FIRST settings can be overridden during the RTH climb phase using full pitch or roll stick held for > 1 second. RTH altitude is reset to the current altitude using pitch down stick. RTH CLIMB FIRST is overridden using right roll stick so craft turns and heads directly to home (CLIMB FIRST override only works for fixed wing) | | nav_rth_alt_mode | AT_LEAST | Configure how the aircraft will manage altitude on the way home, see Navigation modes on wiki for more details | | nav_rth_altitude | 1000 | Used in EXTRA, FIXED and AT_LEAST rth alt modes [cm] (Default 1000 means 10 meters) | | nav_rth_climb_first | ON | If set to ON or ON_FW_SPIRAL aircraft will climb to nav_rth_altitude first before turning to head home. If set to OFF aircraft will turn and head home immediately climbing on the way. For a fixed wing ON will use a linear climb, ON_FW_SPIRAL will use a loiter turning climb with climb rate set by nav_auto_climb_rate, turn rate set by nav_fw_loiter_radius (ON_FW_SPIRAL is a fixed wing setting and behaves the same as ON for a multirotor) | diff --git a/src/main/fc/settings.yaml b/src/main/fc/settings.yaml index 834c2f06279..c475c5d72da 100644 --- a/src/main/fc/settings.yaml +++ b/src/main/fc/settings.yaml @@ -2340,6 +2340,11 @@ groups: default_value: "AT_LEAST" field: general.flags.rth_alt_control_mode table: nav_rth_alt_mode + - name: nav_rth_alt_control_override + description: "If set to ON RTH altitude and CLIMB FIRST settings can be overridden during the RTH climb phase using full pitch or roll stick held for > 1 second. RTH altitude is reset to the current altitude using pitch down stick. RTH CLIMB FIRST is overridden using right roll stick so craft turns and heads directly to home (CLIMB FIRST override only works for fixed wing)" + default_value: OFF + field: general.flags.rth_alt_control_override + type: bool - name: nav_rth_abort_threshold description: "RTH sanity checking feature will notice if distance to home is increasing during RTH and once amount of increase exceeds the threshold defined by this parameter, instead of continuing RTH machine will enter emergency landing, self-level and go down safely. Default is 500m which is safe enough for both multirotor machines and airplanes. [cm]" default_value: 50000 diff --git a/src/main/navigation/navigation.c b/src/main/navigation/navigation.c old mode 100755 new mode 100644 index 2ef4f5b6a66..01f522cb543 --- a/src/main/navigation/navigation.c +++ b/src/main/navigation/navigation.c @@ -107,6 +107,7 @@ PG_RESET_TEMPLATE(navConfig_t, navConfig, .rth_tail_first = SETTING_NAV_RTH_TAIL_FIRST_DEFAULT, .disarm_on_landing = SETTING_NAV_DISARM_ON_LANDING_DEFAULT, .rth_allow_landing = SETTING_NAV_RTH_ALLOW_LANDING_DEFAULT, + .rth_alt_control_override = SETTING_NAV_RTH_ALT_CONTROL_OVERRIDE_DEFAULT, // Override RTH Altitude and Climb First using Pitch and Roll stick .nav_overrides_motor_stop = SETTING_NAV_OVERRIDES_MOTOR_STOP_DEFAULT, }, @@ -235,6 +236,8 @@ static navigationFSMEvent_t nextForNonGeoStates(void); void initializeRTHSanityChecker(const fpVector3_t * pos); bool validateRTHSanityChecker(void); +static bool rthAltControlStickOverrideCheck(unsigned axis); + /*************************************************************************************************/ static navigationFSMEvent_t navOnEnteringState_NAV_STATE_IDLE(navigationFSMState_t previousState); static navigationFSMEvent_t navOnEnteringState_NAV_STATE_ALTHOLD_INITIALIZE(navigationFSMState_t previousState); @@ -1191,6 +1194,8 @@ static navigationFSMEvent_t navOnEnteringState_NAV_STATE_RTH_CLIMB_TO_SAFE_ALT(n { UNUSED(previousState); + rthAltControlStickOverrideCheck(PITCH); + if ((posControl.flags.estHeadingStatus == EST_NONE)) { return NAV_FSM_EVENT_SWITCH_TO_EMERGENCY_LANDING; } @@ -1206,7 +1211,7 @@ static navigationFSMEvent_t navOnEnteringState_NAV_STATE_RTH_CLIMB_TO_SAFE_ALT(n const float rthAltitudeMargin = MAX(FW_RTH_CLIMB_MARGIN_MIN_CM, (rthClimbMarginPercent/100.0) * fabsf(posControl.rthState.rthInitialAltitude - posControl.rthState.homePosition.pos.z)); // If we reached desired initial RTH altitude or we don't want to climb first - if (((navGetCurrentActualPositionAndVelocity()->pos.z - posControl.rthState.rthInitialAltitude) > -rthAltitudeMargin) || (navConfig()->general.flags.rth_climb_first == OFF)) { + if (((navGetCurrentActualPositionAndVelocity()->pos.z - posControl.rthState.rthInitialAltitude) > -rthAltitudeMargin) || (navConfig()->general.flags.rth_climb_first == OFF) || rthAltControlStickOverrideCheck(ROLL)) { // Delayed initialization for RTH sanity check on airplanes - allow to finish climb first as it can take some distance if (STATE(FIXED_WING_LEGACY)) { @@ -1270,6 +1275,8 @@ static navigationFSMEvent_t navOnEnteringState_NAV_STATE_RTH_HEAD_HOME(navigatio { UNUSED(previousState); + rthAltControlStickOverrideCheck(PITCH); + if ((posControl.flags.estHeadingStatus == EST_NONE)) { return NAV_FSM_EVENT_SWITCH_TO_EMERGENCY_LANDING; } @@ -2445,6 +2452,39 @@ void updateHomePosition(void) } } +/* ----------------------------------------------------------- + * Override RTH preset altitude and Climb First option + * using Pitch/Roll stick held for > 1 seconds + * Climb First override limited to Fixed Wing only + *-----------------------------------------------------------*/ +static bool rthAltControlStickOverrideCheck(unsigned axis) +{ + if (!navConfig()->general.flags.rth_alt_control_override || posControl.flags.forcedRTHActivated || (axis == ROLL && STATE(MULTIROTOR))) { + return false; + } + static timeMs_t rthOverrideStickHoldStartTime[2]; + + if (rxGetChannelValue(axis) > rxConfig()->maxcheck) { + timeDelta_t holdTime = millis() - rthOverrideStickHoldStartTime[axis]; + + if (!rthOverrideStickHoldStartTime[axis]) { + rthOverrideStickHoldStartTime[axis] = millis(); + } else if (ABS(1500 - holdTime) < 500) { // 1s delay to activate, activation duration limited to 1 sec + if (axis == PITCH) { // PITCH down to override preset altitude reset to current altitude + posControl.rthState.rthInitialAltitude = posControl.actualState.abs.pos.z; + posControl.rthState.rthFinalAltitude = posControl.rthState.rthInitialAltitude; + return true; + } else if (axis == ROLL) { // ROLL right to override climb first + return true; + } + } + } else { + rthOverrideStickHoldStartTime[axis] = 0; + } + + return false; +} + /*----------------------------------------------------------- * Update flight statistics *-----------------------------------------------------------*/ diff --git a/src/main/navigation/navigation.h b/src/main/navigation/navigation.h index 8123a771b02..0c649929c70 100755 --- a/src/main/navigation/navigation.h +++ b/src/main/navigation/navigation.h @@ -189,6 +189,7 @@ typedef struct navConfig_s { uint8_t disarm_on_landing; // uint8_t rth_allow_landing; // Enable landing as last stage of RTH. Use constants in navRTHAllowLanding_e. uint8_t rth_climb_ignore_emerg; // Option to ignore GPS loss on initial climb stage of RTH + uint8_t rth_alt_control_override; // Override RTH Altitude and Climb First settings using Pitch and Roll stick uint8_t nav_overrides_motor_stop; // Autonomous modes override motor_stop setting and user command to stop motor } flags;