Skip to content

Commit 01f5846

Browse files
committed
camtrack: request gimbal device attitude status
- onboard_controller: request gimbal device attitude status - onboard_controller: send image status at 20 Hz - onboard_controller: adjust default controller gains Signed-off-by: Rhys Mainwaring <[email protected]>
1 parent 3432d62 commit 01f5846

File tree

1 file changed

+45
-16
lines changed

1 file changed

+45
-16
lines changed

MAVProxy/modules/mavproxy_camtrack/onboard_controller.py

+45-16
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@
1818
--rtsp-server rtsp://192.168.1.204:8554/fpv_stream
1919
2020
3. Run controller on RPi4 companion computer using an RTSP stream from
21-
a SIYI A8 camea.
21+
a SIYI A8 camera.
2222
2323
python ./onboard_controller.py
2424
--master 192.168.144.171:15001
@@ -133,7 +133,7 @@ def __init__(self, device, sysid, cmpid, rtsp_url):
133133
# mavlink connection
134134
self._connection = None
135135

136-
# list of controllers to forward mavlink message to
136+
# list of controllers to forward mavlink messages
137137
self._controllers = []
138138
self._camera_controller = None
139139
self._gimbal_controller = None
@@ -180,7 +180,7 @@ def _mavlink_recv_task(self):
180180
"""
181181
Task to receive a mavlink message and forwward to controllers.
182182
"""
183-
update_rate = 1000.0
183+
update_rate = 1000.0 # Hz
184184
update_period = 1.0 / update_rate
185185

186186
while True:
@@ -248,10 +248,19 @@ def run(self):
248248
tracking_rect_changed = True
249249

250250
# TODO: how to ensure consistency of frame updates with GCS?
251-
fps = 50
252-
update_rate = fps
251+
update_rate = 50.0 # Hz
253252
update_period = 1.0 / update_rate
254253

254+
# TODO: consolidate common code - also used in GUI
255+
# request gimbal device attitude status
256+
gimbal_device_attitude_status_rate = 50.0 # Hz
257+
interval_us = int(1e6 / gimbal_device_attitude_status_rate)
258+
self.send_set_message_interval_message(
259+
mavutil.mavlink.MAVLINK_MSG_ID_GIMBAL_DEVICE_ATTITUDE_STATUS,
260+
interval_us, # requested interval in microseconds
261+
response_target=1, # flight-stack default
262+
)
263+
255264
frame_count = 0
256265
while True:
257266
start_time = time.time()
@@ -323,6 +332,23 @@ def __compare_rect(rect1, rect2):
323332
sleep_time = max(0.0, update_period - elapsed_time)
324333
time.sleep(sleep_time)
325334

335+
def send_set_message_interval_message(
336+
self, message_id, interval_us, response_target=1
337+
):
338+
self._connection.mav.command_long_send(
339+
self._connection.target_system, # target_system
340+
self._connection.target_component, # target_component
341+
mavutil.mavlink.MAV_CMD_SET_MESSAGE_INTERVAL, # command
342+
0, # confirmation
343+
message_id, # param1
344+
interval_us, # param2
345+
0, # param3
346+
0, # param4
347+
0, # param5
348+
0, # param6
349+
response_target, # param7
350+
)
351+
326352

327353
class VideoStream:
328354
"""
@@ -490,8 +516,8 @@ class CameraTrackController:
490516

491517
def __init__(self, connection):
492518
self._connection = connection
493-
self._sysid = self._connection.source_system
494-
self._cmpid = self._connection.source_component
519+
self._sysid = self._connection.source_system # system id matches vehicle
520+
self._cmpid = 1 # component id matches autopilot
495521

496522
print(
497523
f"Camera Track Controller: "
@@ -721,7 +747,7 @@ def _mavlink_task(self):
721747
sysid = self._sysid
722748
cmpid = self._cmpid
723749

724-
update_rate = 1000.0
750+
update_rate = 1000.0 # Hz
725751
update_period = 1.0 / update_rate
726752

727753
while True:
@@ -758,7 +784,7 @@ def _send_status_task(self):
758784
# TODO: stop sending image status when tracking stopped
759785
# TODO: set streaming rate using MAV_CMD_SET_MESSAGE_INTERVAL
760786

761-
update_rate = 2.0
787+
update_rate = 20.0 # Hz
762788
update_period = 1.0 / update_rate
763789

764790
while True:
@@ -780,8 +806,8 @@ class GimbalController:
780806

781807
def __init__(self, connection):
782808
self._connection = connection
783-
self._sysid = self._connection.source_system
784-
self._cmpid = self._connection.source_component
809+
self._sysid = self._connection.source_system # system id matches vehicle
810+
self._cmpid = 1 # component id matches autopilot
785811

786812
print(f"Gimbal Controller: src_sys: {self._sysid}, src_cmp: {self._cmpid})")
787813

@@ -805,9 +831,8 @@ def __init__(self, connection):
805831
self._gimbal_failure_flags = None
806832

807833
# TODO: add options for PI controller gains
808-
# PI controllers: SIYI A8: 0.1, Gazebo: 0.3
809-
self._pitch_controller = PI_controller(Pgain=0.5, Igain=0.01, IMAX=1.0)
810-
self._yaw_controller = PI_controller(Pgain=0.5, Igain=0.01, IMAX=1.0)
834+
self._pitch_controller = PI_controller(Pgain=0.1, Igain=0.01, IMAX=0.1)
835+
self._yaw_controller = PI_controller(Pgain=0.1, Igain=0.1, IMAX=1.0)
811836

812837
# Start the control thread
813838
self._control_in_queue = queue.Queue()
@@ -886,6 +911,9 @@ def _control_task(self):
886911
# the current mount orientation.
887912
_, ay, az = euler.quat2euler(gimbal_orientation)
888913

914+
self._pitch_controller.gain_mul = 4.0
915+
self._yaw_controller.gain_mul = 40.0
916+
889917
err_pitch = self._neutral_y - ay
890918
pitch_rate_rads = self._pitch_controller.run(err_pitch)
891919

@@ -909,6 +937,9 @@ def _control_task(self):
909937
err_x = act_x - tgt_x
910938
err_y = -(act_y - tgt_y)
911939

940+
self._pitch_controller.gain_mul = 1.0
941+
self._yaw_controller.gain_mul = 2.0
942+
912943
err_pitch = math.radians(err_y)
913944
pitch_rate_rads = self._pitch_controller.run(err_pitch)
914945

@@ -942,8 +973,6 @@ def __process_message():
942973
return
943974
msg = self._control_in_queue.get()
944975
mtype = msg.get_type()
945-
# NOTE: GIMBAL_DEVICE_ATTITUDE_STATUS is broadcast
946-
# (sysid=0, cmpid=0)
947976
if msg and mtype == "GIMBAL_DEVICE_ATTITUDE_STATUS":
948977
with self._mavlink_lock:
949978
self._gimbal_device_flags = msg.flags

0 commit comments

Comments
 (0)