Skip to content

Commit 16e39ab

Browse files
Rover: CONDITION_YAW command handling for skid-steering rover
Implements condition_yaw command handling for skid-steering rover only. Direction specification not yet implemented. Adds an autotest to rover.py that tests this behaviour. Co-authored-by: Tiago Santos <tiago.castro.santos@tecnico.ulisboa.pt>
1 parent fb4e5ce commit 16e39ab

File tree

5 files changed

+121
-0
lines changed

5 files changed

+121
-0
lines changed

Rover/GCS_MAVLink_Rover.cpp

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -500,6 +500,13 @@ MAV_RESULT GCS_MAVLINK_Rover::handle_command_int_packet(const mavlink_command_in
500500
{
501501
switch (packet.command) {
502502

503+
case MAV_CMD_CONDITION_YAW:
504+
if (rover.g2.motors.have_skid_steering()) {
505+
return handle_command_condition_yaw(packet);
506+
}
507+
// not yet implemented for other vehicle types
508+
return MAV_RESULT_UNSUPPORTED;
509+
503510
case MAV_CMD_DO_CHANGE_SPEED:
504511
// param1 : unused
505512
// param2 : new speed in m/s
@@ -578,6 +585,33 @@ MAV_RESULT GCS_MAVLINK_Rover::handle_command_nav_set_yaw_speed(const mavlink_com
578585
}
579586
#endif
580587

588+
MAV_RESULT GCS_MAVLINK_Rover::handle_command_condition_yaw(const mavlink_command_int_t &packet)
589+
{
590+
// param1 : target angle [0-360]
591+
// param2 : speed during change [deg per second]
592+
// param3 : direction (-1:ccw, +1:cw)
593+
// param4 : relative offset (1) or absolute angle (0)
594+
595+
// exit if vehicle is not in Guided mode
596+
if (!rover.control_mode->in_guided_mode()) {
597+
return MAV_RESULT_FAILED;
598+
}
599+
600+
// get final angle, 1 = Relative, 0 = Absolute
601+
switch ((int) packet.param4) {
602+
case 0: // absolute angle
603+
// absolute angle
604+
rover.mode_guided.set_desired_turn_rate_and_heading(packet.param1 * 100.0f, packet.param2 * 100.0f, packet.param3);
605+
break;
606+
case 1: // relative angle
607+
rover.mode_guided.set_desired_turn_rate_and_heading_delta(packet.param1 * 100.0f, packet.param2 * 100.0f, packet.param3);
608+
break;
609+
default:
610+
return MAV_RESULT_DENIED;
611+
}
612+
return MAV_RESULT_ACCEPTED;
613+
}
614+
581615
MAV_RESULT GCS_MAVLINK_Rover::handle_command_int_do_reposition(const mavlink_command_int_t &packet)
582616
{
583617
const bool change_modes = ((int32_t)packet.param2 & MAV_DO_REPOSITION_FLAGS_CHANGE_MODE) == MAV_DO_REPOSITION_FLAGS_CHANGE_MODE;

Rover/GCS_MAVLink_Rover.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ class GCS_MAVLINK_Rover : public GCS_MAVLINK
1919

2020
MAV_RESULT _handle_command_preflight_calibration(const mavlink_command_int_t &packet, const mavlink_message_t &msg) override;
2121
MAV_RESULT handle_command_int_packet(const mavlink_command_int_t &packet, const mavlink_message_t &msg) override;
22+
MAV_RESULT handle_command_condition_yaw(const mavlink_command_int_t &packet);
2223
MAV_RESULT handle_command_int_do_reposition(const mavlink_command_int_t &packet);
2324
MAV_RESULT handle_command_nav_set_yaw_speed(const mavlink_command_int_t &packet, const mavlink_message_t &msg);
2425

Rover/mode.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -551,6 +551,10 @@ class ModeGuided : public Mode
551551
void set_desired_heading_delta_and_speed(float yaw_delta_cd, float target_speed);
552552
void set_desired_turn_rate_and_speed(float turn_rate_cds, float target_speed);
553553

554+
// set desired turn rate and heading
555+
void set_desired_turn_rate_and_heading(float yaw_angle_cd, float turn_rate_cds, int8_t direction);
556+
void set_desired_turn_rate_and_heading_delta(float yaw_delta_cd, float turn_rate_cds, int8_t direction);
557+
554558
// set steering and throttle (-1 to +1). Only called from scripts
555559
void set_steering_and_throttle(float steering, float throttle);
556560

@@ -574,6 +578,7 @@ class ModeGuided : public Mode
574578
TurnRateAndSpeed,
575579
Loiter,
576580
SteeringAndThrottle,
581+
TurnRateAndHeading,
577582
Stop
578583
};
579584

Rover/mode_guided.cpp

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,30 @@ void ModeGuided::update()
101101
break;
102102
}
103103

104+
case SubMode::TurnRateAndHeading:
105+
{
106+
// stop vehicle if target not updated within 3 seconds
107+
if (have_attitude_target && (millis() - _des_att_time_ms) > 3000) {
108+
gcs().send_text(MAV_SEVERITY_WARNING, "target not received last 3secs, stopping");
109+
have_attitude_target = false;
110+
break;
111+
}
112+
if (have_attitude_target) {
113+
// run steering and throttle controllers
114+
calc_steering_to_heading(_desired_yaw_cd, _desired_yaw_rate_cds * 0.01f);
115+
break;
116+
}
117+
// we have reached the destination so stay here
118+
if (rover.is_boat()) {
119+
if (!start_loiter()) {
120+
stop_vehicle();
121+
}
122+
break;
123+
}
124+
stop_vehicle();
125+
break;
126+
}
127+
104128
case SubMode::Loiter:
105129
{
106130
rover.mode_loiter.update();
@@ -149,6 +173,7 @@ float ModeGuided::wp_bearing() const
149173
return g2.wp_nav.wp_bearing_cd() * 0.01f;
150174
case SubMode::HeadingAndSpeed:
151175
case SubMode::TurnRateAndSpeed:
176+
case SubMode::TurnRateAndHeading:
152177
return 0.0f;
153178
case SubMode::Loiter:
154179
return rover.mode_loiter.wp_bearing();
@@ -169,6 +194,8 @@ float ModeGuided::nav_bearing() const
169194
case SubMode::HeadingAndSpeed:
170195
case SubMode::TurnRateAndSpeed:
171196
return 0.0f;
197+
case SubMode::TurnRateAndHeading:
198+
return _desired_yaw_cd * 0.01f;
172199
case SubMode::Loiter:
173200
return rover.mode_loiter.nav_bearing();
174201
case SubMode::SteeringAndThrottle:
@@ -187,6 +214,7 @@ float ModeGuided::crosstrack_error() const
187214
return g2.wp_nav.crosstrack_error();
188215
case SubMode::HeadingAndSpeed:
189216
case SubMode::TurnRateAndSpeed:
217+
case SubMode::TurnRateAndHeading:
190218
return 0.0f;
191219
case SubMode::Loiter:
192220
return rover.mode_loiter.crosstrack_error();
@@ -206,6 +234,7 @@ float ModeGuided::get_desired_lat_accel() const
206234
return g2.wp_nav.get_lat_accel();
207235
case SubMode::HeadingAndSpeed:
208236
case SubMode::TurnRateAndSpeed:
237+
case SubMode::TurnRateAndHeading:
209238
return 0.0f;
210239
case SubMode::Loiter:
211240
return rover.mode_loiter.get_desired_lat_accel();
@@ -226,6 +255,7 @@ float ModeGuided::get_distance_to_destination() const
226255
return _distance_to_destination;
227256
case SubMode::HeadingAndSpeed:
228257
case SubMode::TurnRateAndSpeed:
258+
case SubMode::TurnRateAndHeading:
229259
return 0.0f;
230260
case SubMode::Loiter:
231261
return rover.mode_loiter.get_distance_to_destination();
@@ -246,6 +276,7 @@ bool ModeGuided::reached_destination() const
246276
return g2.wp_nav.reached_destination();
247277
case SubMode::HeadingAndSpeed:
248278
case SubMode::TurnRateAndSpeed:
279+
case SubMode::TurnRateAndHeading:
249280
case SubMode::Loiter:
250281
case SubMode::SteeringAndThrottle:
251282
case SubMode::Stop:
@@ -269,6 +300,7 @@ bool ModeGuided::set_desired_speed(float speed)
269300
case SubMode::Loiter:
270301
return rover.mode_loiter.set_desired_speed(speed);
271302
case SubMode::SteeringAndThrottle:
303+
case SubMode::TurnRateAndHeading:
272304
case SubMode::Stop:
273305
// no speed control
274306
return false;
@@ -288,6 +320,7 @@ bool ModeGuided::get_desired_location(Location& destination) const
288320
return false;
289321
case SubMode::HeadingAndSpeed:
290322
case SubMode::TurnRateAndSpeed:
323+
case SubMode::TurnRateAndHeading:
291324
// not supported in these submodes
292325
return false;
293326
case SubMode::Loiter:
@@ -374,6 +407,32 @@ void ModeGuided::set_desired_turn_rate_and_speed(float turn_rate_cds, float targ
374407
#endif
375408
}
376409

410+
// set desired attitude
411+
void ModeGuided::set_desired_turn_rate_and_heading(float yaw_angle_cd, float turn_rate_cds, int8_t direction)
412+
{
413+
// initialisation and logging
414+
_guided_mode = SubMode::TurnRateAndHeading;
415+
_des_att_time_ms = AP_HAL::millis();
416+
417+
// record targets
418+
_desired_yaw_cd = yaw_angle_cd;
419+
_desired_yaw_rate_cds = turn_rate_cds;
420+
have_attitude_target = true;
421+
}
422+
423+
// set desired attitude
424+
void ModeGuided::set_desired_turn_rate_and_heading_delta(float yaw_delta_cd, float turn_rate_cds, int8_t direction)
425+
{
426+
/// handle initialisation
427+
float desired_yaw_cd = _desired_yaw_cd;
428+
if (_guided_mode != SubMode::TurnRateAndHeading) {
429+
_guided_mode = SubMode::TurnRateAndHeading;
430+
desired_yaw_cd = ahrs.yaw_sensor;
431+
}
432+
433+
set_desired_turn_rate_and_heading(wrap_180_cd(desired_yaw_cd + yaw_delta_cd), turn_rate_cds, direction);
434+
}
435+
377436
// set steering and throttle (both in the range -1 to +1)
378437
void ModeGuided::set_steering_and_throttle(float steering, float throttle)
379438
{

Tools/autotest/rover.py

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6315,6 +6315,27 @@ def MAV_CMD_DO_CHANGE_SPEED(self):
63156315
self.wait_distance_to_home(0, 5, timeout=30)
63166316
self.disarm_vehicle()
63176317

6318+
def MAV_CMD_CONDITION_YAW(self):
6319+
'''simple test for CONDITION_YAW command'''
6320+
model = "rover-skid"
6321+
self.customise_SITL_commandline([],
6322+
model=model,
6323+
defaults_filepath=self.model_defaults_filepath(model))
6324+
self.wait_ready_to_arm()
6325+
self.arm_vehicle()
6326+
self.change_mode('GUIDED')
6327+
6328+
def send_cmd(x, y):
6329+
self.run_cmd(
6330+
mavutil.mavlink.MAV_CMD_CONDITION_YAW,
6331+
p1=60, # target angle
6332+
p2=10, # degrees/second
6333+
p3=1, # -1 is counter-clockwise, 1 clockwise
6334+
p4=0, # 1 for relative, 0 for absolute
6335+
)
6336+
self.wait_heading(60, called_function=send_cmd)
6337+
self.disarm_vehicle()
6338+
63186339
def MAV_CMD_MISSION_START(self):
63196340
'''simple test for starting missing using this command'''
63206341
# home and 1 waypoint a long way away:
@@ -6946,6 +6967,7 @@ def tests(self):
69466967
self.SET_POSITION_TARGET_LOCAL_NED,
69476968
self.MAV_CMD_DO_SET_MISSION_CURRENT,
69486969
self.MAV_CMD_DO_CHANGE_SPEED,
6970+
self.MAV_CMD_CONDITION_YAW,
69496971
self.MAV_CMD_MISSION_START,
69506972
self.MAV_CMD_NAV_SET_YAW_SPEED,
69516973
self.Button,

0 commit comments

Comments
 (0)