Skip to content

Commit 7001850

Browse files
committed
Copter: simple mode fix
Replaces update_simple_mode with apply_simple_mode function that takes roll and pitch input arguments. The rotation is now done within the various get-pilot-desired-xxx methods removing the need for each flight mode to call update_simple_mode and also removing the slightly ugly call to overwrite RC_Channels' control inputs from the flight code (e.g. no more calls to set_control_in)
1 parent e57b8a4 commit 7001850

17 files changed

Lines changed: 46 additions & 86 deletions

ArduCopter/Copter.cpp

Lines changed: 0 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -850,39 +850,6 @@ void Copter::init_simple_bearing()
850850
#endif
851851
}
852852

853-
// update_simple_mode - rotates pilot input if we are in simple mode
854-
void Copter::update_simple_mode(void)
855-
{
856-
float rollx, pitchx;
857-
858-
// exit immediately if no new radio frame or not in simple mode
859-
if (simple_mode == SimpleMode::NONE || !ap.new_radio_frame) {
860-
return;
861-
}
862-
863-
// mark radio frame as consumed
864-
ap.new_radio_frame = false;
865-
866-
// avoid processing bind-time RC values:
867-
if (!rc().has_valid_input()) {
868-
return;
869-
}
870-
871-
if (simple_mode == SimpleMode::SIMPLE) {
872-
// rotate roll, pitch input by -initial simple heading (i.e. north facing)
873-
rollx = channel_roll->get_control_in()*simple_cos_yaw - channel_pitch->get_control_in()*simple_sin_yaw;
874-
pitchx = channel_roll->get_control_in()*simple_sin_yaw + channel_pitch->get_control_in()*simple_cos_yaw;
875-
}else{
876-
// rotate roll, pitch input by -super simple heading (reverse of heading to home)
877-
rollx = channel_roll->get_control_in()*super_simple_cos_yaw - channel_pitch->get_control_in()*super_simple_sin_yaw;
878-
pitchx = channel_roll->get_control_in()*super_simple_sin_yaw + channel_pitch->get_control_in()*super_simple_cos_yaw;
879-
}
880-
881-
// rotate roll, pitch input from north facing to vehicle's perspective
882-
channel_roll->set_control_in(rollx*ahrs.cos_yaw() + pitchx*ahrs.sin_yaw());
883-
channel_pitch->set_control_in(-rollx*ahrs.sin_yaw() + pitchx*ahrs.cos_yaw());
884-
}
885-
886853
// update_super_simple_bearing - adjusts simple bearing based on location
887854
// should be called after home_bearing_rad has been updated
888855
void Copter::update_super_simple_bearing(bool force_update)

ArduCopter/Copter.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -722,7 +722,6 @@ class Copter : public AP_Vehicle {
722722
void three_hz_loop();
723723
void one_hz_loop();
724724
void init_simple_bearing();
725-
void update_simple_mode(void);
726725
void update_super_simple_bearing(bool force_update);
727726
void read_AHRS(void);
728727
void update_altitude();

ArduCopter/mode.cpp

Lines changed: 36 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -563,8 +563,15 @@ void Mode::get_pilot_desired_lean_angles_rad(float &roll_out_rad, float &pitch_o
563563
return;
564564
}
565565

566-
//transform pilot's normalised roll or pitch stick input into a roll and pitch euler angle command
567-
rc_input_to_roll_pitch_rad(channel_roll->norm_input_dz(), channel_pitch->norm_input_dz(), angle_max_rad, angle_limit_rad, roll_out_rad, pitch_out_rad);
566+
// fetch roll and pitch inputs
567+
float roll_in_norm = channel_roll->norm_input_dz();
568+
float pitch_in_norm = channel_pitch->norm_input_dz();
569+
570+
// apply SIMPLE mode transform to pilot inputs
571+
apply_simple_mode(roll_in_norm, pitch_in_norm);
572+
573+
// transform pilot's normalised roll or pitch stick input into a roll and pitch euler angle command
574+
rc_input_to_roll_pitch_rad(roll_in_norm, pitch_in_norm, angle_max_rad, angle_limit_rad, roll_out_rad, pitch_out_rad);
568575
}
569576

570577
// transform pilot's roll or pitch input into a desired velocity
@@ -579,6 +586,9 @@ Vector2f Mode::get_pilot_desired_velocity(float vel_max) const
579586
float roll_out_norm = channel_roll->norm_input_dz();
580587
float pitch_out_norm = channel_pitch->norm_input_dz();
581588

589+
// apply SIMPLE mode transform to pilot inputs
590+
apply_simple_mode(roll_out_norm, pitch_out_norm);
591+
582592
// convert roll and pitch inputs into velocity in NE frame
583593
vel_ne_ms = Vector2f(-pitch_out_norm, roll_out_norm);
584594
if (vel_ne_ms.is_zero()) {
@@ -789,9 +799,6 @@ void Mode::land_run_horizontal_control()
789799
}
790800

791801
if (g.land_repositioning) {
792-
// apply SIMPLE mode transform to pilot inputs
793-
update_simple_mode();
794-
795802
// convert pilot input to reposition velocity
796803
// use half maximum acceleration as the maximum velocity to ensure aircraft will
797804
// stop from full reposition speed in less than 1 second.
@@ -1094,9 +1101,30 @@ float Mode::get_non_takeoff_throttle() const
10941101
return copter.get_non_takeoff_throttle();
10951102
}
10961103

1097-
// Updates simple/super-simple heading reference based on current yaw and mode.
1098-
void Mode::update_simple_mode(void) {
1099-
copter.update_simple_mode();
1104+
// Rotates roll/pitch pilot input if simple or super simple mode is active.
1105+
// roll and pitch may be in any units/scale; the rotation is scale-independent
1106+
void Mode::apply_simple_mode(float &roll, float &pitch) const
1107+
{
1108+
// exit immediately if not in simple mode
1109+
if (copter.simple_mode == Copter::SimpleMode::NONE) {
1110+
return;
1111+
}
1112+
1113+
float roll_out, pitch_out;
1114+
1115+
if (copter.simple_mode == Copter::SimpleMode::SIMPLE) {
1116+
// rotate roll, pitch input by -initial simple heading (i.e. north facing)
1117+
roll_out = roll*copter.simple_cos_yaw - pitch*copter.simple_sin_yaw;
1118+
pitch_out = roll*copter.simple_sin_yaw + pitch*copter.simple_cos_yaw;
1119+
} else {
1120+
// rotate roll, pitch input by -super simple heading (reverse of heading to home)
1121+
roll_out = roll*copter.super_simple_cos_yaw - pitch*copter.super_simple_sin_yaw;
1122+
pitch_out = roll*copter.super_simple_sin_yaw + pitch*copter.super_simple_cos_yaw;
1123+
}
1124+
1125+
// rotate roll, pitch input from north facing to vehicle's perspective
1126+
roll = roll_out*copter.ahrs.cos_yaw() + pitch_out*copter.ahrs.sin_yaw();
1127+
pitch = -roll_out*copter.ahrs.sin_yaw() + pitch_out*copter.ahrs.cos_yaw();
11001128
}
11011129

11021130
// Requests a mode change with the specified reason; returns true if accepted.

ArduCopter/mode.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -405,8 +405,8 @@ class Mode {
405405
// Returns the throttle level to maintain altitude (excluding takeoff boost).
406406
float get_non_takeoff_throttle() const;
407407

408-
// Updates simple/super-simple heading reference based on current yaw and mode.
409-
void update_simple_mode();
408+
// Rotates roll/pitch pilot input if simple or super simple mode is active.
409+
void apply_simple_mode(float &roll, float &pitch) const;
410410

411411
// Requests a mode change with the specified reason; returns true if accepted.
412412
bool set_mode(Mode::Number mode, ModeReason reason);

ArduCopter/mode_acro.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,9 @@ void ModeAcro::get_pilot_desired_rates_rads(float &roll_out_rads, float &pitch_o
108108
float pitch_in_norm = channel_pitch->norm_input_dz();
109109
const float yaw_in_norm = channel_yaw->norm_input_dz();
110110

111+
// apply SIMPLE mode transform to pilot inputs
112+
apply_simple_mode(roll_in_norm, pitch_in_norm);
113+
111114
// apply circular limit to pitch and roll inputs
112115
float norm_in_length = norm(pitch_in_norm, roll_in_norm);
113116

ArduCopter/mode_althold.cpp

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,6 @@ void ModeAltHold::run()
2929
// set vertical speed and acceleration limits
3030
pos_control->D_set_max_speed_accel_m(get_pilot_speed_dn_ms(), get_pilot_speed_up_ms(), get_pilot_accel_D_mss());
3131

32-
// apply SIMPLE mode transform to pilot inputs
33-
update_simple_mode();
34-
3532
// get pilot desired lean angles
3633
float target_roll_rad, target_pitch_rad;
3734
get_pilot_desired_lean_angles_rad(target_roll_rad, target_pitch_rad, attitude_control->lean_angle_max_rad(), attitude_control->get_althold_lean_angle_max_rad());

ArduCopter/mode_autotune.cpp

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -34,9 +34,6 @@ bool AutoTune::init()
3434

3535
void AutoTune::run()
3636
{
37-
// apply SIMPLE mode transform to pilot inputs
38-
copter.update_simple_mode();
39-
4037
// disarm when the landing detector says we've landed and spool state is ground idle
4138
if (copter.ap.land_complete && motors->get_spool_state() == AP_Motors::SpoolState::GROUND_IDLE) {
4239
copter.arming.disarm(AP_Arming::Method::LANDED);

ArduCopter/mode_flowhold.cpp

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -243,9 +243,6 @@ void ModeFlowHold::run()
243243
// set vertical speed and acceleration limits
244244
pos_control->D_set_max_speed_accel_m(get_pilot_speed_dn_ms(), get_pilot_speed_up_ms(), get_pilot_accel_D_mss());
245245

246-
// apply SIMPLE mode transform to pilot inputs
247-
update_simple_mode();
248-
249246
// check for filter change
250247
if (!is_equal(flow_filter.get_cutoff_freq(), flow_filter_hz.get())) {
251248
flow_filter.set_cutoff_frequency(copter.scheduler.get_loop_rate_hz(), flow_filter_hz.get());

ArduCopter/mode_land.cpp

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -163,9 +163,6 @@ void ModeLand::nogps_run()
163163
#endif
164164

165165
if (g.land_repositioning) {
166-
// apply SIMPLE mode transform to pilot inputs
167-
update_simple_mode();
168-
169166
// get pilot desired lean angles
170167
get_pilot_desired_lean_angles_rad(target_roll_rad, target_pitch_rad, attitude_control->lean_angle_max_rad(), attitude_control->get_althold_lean_angle_max_rad());
171168
}

ArduCopter/mode_loiter.cpp

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,6 @@
1010
bool ModeLoiter::init(bool ignore_checks)
1111
{
1212
float target_roll_rad, target_pitch_rad;
13-
// apply SIMPLE mode transform to pilot inputs
14-
update_simple_mode();
15-
1613
// convert pilot input to lean angles
1714
get_pilot_desired_lean_angles_rad(target_roll_rad, target_pitch_rad, loiter_nav->get_angle_max_rad(), attitude_control->get_althold_lean_angle_max_rad());
1815

@@ -86,9 +83,6 @@ void ModeLoiter::run()
8683
// set vertical speed and acceleration limits
8784
pos_control->D_set_max_speed_accel_m(get_pilot_speed_dn_ms(), get_pilot_speed_up_ms(), get_pilot_accel_D_mss());
8885

89-
// apply SIMPLE mode transform to pilot inputs
90-
update_simple_mode();
91-
9286
// convert pilot input to lean angles
9387
get_pilot_desired_lean_angles_rad(target_roll_rad, target_pitch_rad, loiter_nav->get_angle_max_rad(), attitude_control->get_althold_lean_angle_max_rad());
9488

0 commit comments

Comments
 (0)