Skip to content

Commit 8674077

Browse files
committed
Plane: added fast attitude recovery in Q modes
when we start the VTOL motor stabilisation with an attitude beyond normal attitude limits we set a flag to use fixed wing attitude control (slaving VTOL rate control to fixed wing rate control) until we have recovered this avoids an issue with the shaping in the VTOL attitude controller and also fixes an issue with the VTOL controller bringing the nose down, which can cause a lot of height loss in quadplanes
1 parent aea8155 commit 8674077

File tree

2 files changed

+37
-2
lines changed

2 files changed

+37
-2
lines changed

ArduPlane/quadplane.cpp

Lines changed: 34 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -875,7 +875,7 @@ void QuadPlane::run_esc_calibration(void)
875875
*/
876876
void QuadPlane::multicopter_attitude_rate_update(float yaw_rate_cds)
877877
{
878-
bool use_multicopter_control = in_vtol_mode() && !tailsitter.in_vtol_transition();
878+
bool use_multicopter_control = in_vtol_mode() && !tailsitter.in_vtol_transition() && !force_fw_control_recovery;
879879
bool use_yaw_target = false;
880880

881881
float yaw_target_cd = 0.0;
@@ -1937,7 +1937,38 @@ void QuadPlane::motors_output(bool run_rate_controller)
19371937
if (now - last_att_control_ms > 100) {
19381938
// relax if have been inactive
19391939
relax_attitude_control();
1940+
/*
1941+
when starting the VTOL motors force use of the fixed
1942+
wing controller for attitude control if we are outside
1943+
of the Q_ANGLE_MAX limit. We keep it forced until we
1944+
have recovered to within the limit
1945+
1946+
This avoids an issue with the attitude controller
1947+
limiting the rate of recovery and also an issue with the
1948+
quaternion controller trying to fix the attitude in a
1949+
way that is bad for fixed wing aircraft (eg. putting
1950+
nose down when inverted, leading to rapid loss of
1951+
height)
1952+
1953+
we don't do this in QACRO or tailsitter modes, as this
1954+
type of attitude is expected
1955+
*/
1956+
if (!tailsitter.enabled() &&
1957+
plane.control_mode != &plane.mode_qacro &&
1958+
(abs(ahrs_view->roll_sensor) > aparm.angle_max ||
1959+
abs(ahrs_view->pitch_sensor) > aparm.angle_max)) {
1960+
force_fw_control_recovery = true;
1961+
}
19401962
}
1963+
if (force_fw_control_recovery) {
1964+
// see if we have recovered attitude
1965+
if (abs(ahrs_view->roll_sensor) <= aparm.angle_max &&
1966+
abs(ahrs_view->pitch_sensor) <= aparm.angle_max) {
1967+
force_fw_control_recovery = false;
1968+
relax_attitude_control();
1969+
}
1970+
}
1971+
19411972
// run low level rate controllers that only require IMU data and set loop time
19421973
const float last_loop_time_s = AP::scheduler().get_last_loop_time_s();
19431974
motors->set_dt(last_loop_time_s);
@@ -4192,7 +4223,8 @@ bool QuadPlane::use_fw_attitude_controllers(void) const
41924223
motors->get_desired_spool_state() >= AP_Motors::DesiredSpoolState::THROTTLE_UNLIMITED &&
41934224
in_vtol_mode() &&
41944225
!tailsitter.enabled() &&
4195-
poscontrol.get_state() != QPOS_AIRBRAKE) {
4226+
poscontrol.get_state() != QPOS_AIRBRAKE &&
4227+
!force_fw_control_recovery) {
41964228
// we want the desired rates for fixed wing slaved to the
41974229
// multicopter rates
41984230
return false;

ArduPlane/quadplane.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -632,6 +632,9 @@ class QuadPlane
632632
// ignored unless OPTION_DELAY_ARMING or OPTION_TILT_DISARMED is set
633633
bool delay_arming;
634634

635+
// should we force use of fixed wing controller for attitude upset recovery?
636+
bool force_fw_control_recovery;
637+
635638
/*
636639
return true if current mission item is a vtol takeoff
637640
*/

0 commit comments

Comments
 (0)