55
66import serial
77from app .customTypes import Response
8- from app .utils import commandAccepted , wpToMissionItemInt
8+ from app .utils import commandAccepted
99from pymavlink import mavutil , mavwp
1010
1111if TYPE_CHECKING :
@@ -238,7 +238,7 @@ def getItemDetails(
238238 if not mission_type_check .get ("success" ):
239239 return mission_type_check
240240
241- failure_message = f"Failed to get mission item { item_number } /{ mission_count } for mission type { mission_type } "
241+ failure_message = f"Failed to get mission item { item_number } /{ mission_count - 1 } for mission type { mission_type } "
242242
243243 self .drone .is_listening = False
244244
@@ -260,7 +260,7 @@ def getItemDetails(
260260
261261 if response :
262262 self .drone .logger .debug (
263- f"Got response for mission item { item_number } /{ mission_count } for mission type { mission_type } "
263+ f"Got response for mission item { item_number } /{ mission_count - 1 } for mission type { mission_type } "
264264 )
265265 return {
266266 "success" : True ,
@@ -269,7 +269,7 @@ def getItemDetails(
269269
270270 else :
271271 self .drone .logger .error (
272- f"Got no response for mission item { item_number } /{ mission_count } for mission type { mission_type } "
272+ f"Got no response for mission item { item_number } /{ mission_count - 1 } for mission type { mission_type } "
273273 )
274274 return {
275275 "success" : False ,
@@ -279,7 +279,7 @@ def getItemDetails(
279279 except serial .serialutil .SerialException :
280280 self .drone .is_listening = True
281281 self .drone .logger .error (
282- f"Got no response for mission item { item_number } /{ mission_count } , serial exception"
282+ f"Got no response for mission item { item_number } /{ mission_count - 1 } , serial exception"
283283 )
284284 return {
285285 "success" : False ,
@@ -454,9 +454,63 @@ def loadWaypointFile(self, file_path: str, mission_type: int) -> Response:
454454 "message" : f"Waypoint file loaded { loader .count ()} points successfully" ,
455455 }
456456
457- def uploadMission (self , mission_type : int ) -> Response :
457+ def _parseWaypointsListIntoLoader (
458+ self , waypoints : List [dict ], mission_type : int
459+ ) -> mavwp .MAVWPLoader :
458460 """
459- Uploads the current mission to the drone.
461+ Parses a list of waypoints into a MAVWPLoader object.
462+ """
463+
464+ if mission_type == TYPE_MISSION :
465+ loader = mavwp .MAVWPLoader (
466+ target_system = self .drone .target_system ,
467+ target_component = self .drone .target_component ,
468+ )
469+ elif mission_type == TYPE_FENCE :
470+ loader = mavwp .MissionItemProtocol_Fence (
471+ target_system = self .drone .target_system ,
472+ target_component = self .drone .target_component ,
473+ )
474+ elif mission_type == TYPE_RALLY :
475+ loader = mavwp .MissionItemProtocol_Rally (
476+ target_system = self .drone .target_system ,
477+ target_component = self .drone .target_component ,
478+ )
479+
480+ for wp in waypoints :
481+ if isinstance (wp , mavutil .mavlink .MAVLink_mission_item_int_message ):
482+ loader .add (wp )
483+ elif isinstance (wp , dict ):
484+ # Convert dict to MAVLink mission item int message
485+ p = mavutil .mavlink .MAVLink_mission_item_int_message (
486+ self .drone .target_system ,
487+ self .drone .target_component ,
488+ wp ["seq" ],
489+ wp ["frame" ],
490+ wp ["command" ],
491+ wp ["current" ],
492+ wp ["autocontinue" ],
493+ wp ["param1" ],
494+ wp ["param2" ],
495+ wp ["param3" ],
496+ wp ["param4" ],
497+ int (wp ["x" ]),
498+ int (wp ["y" ]),
499+ wp ["z" ],
500+ wp ["mission_type" ],
501+ )
502+ loader .add (p )
503+ else :
504+ self .drone .logger .error (
505+ f"Invalid waypoint type { type (wp )} in waypoints list"
506+ )
507+ raise ValueError (f"Invalid waypoint type { type (wp )} in waypoints list" )
508+
509+ return loader
510+
511+ def uploadMission (self , mission_type : int , waypoints : List [dict ]) -> Response :
512+ """
513+ Uploads the current mission to the drone. This method overwrites the current loader if the upload is successful.
460514
461515 Args:
462516 mission_type (int): The type of mission to upload. 0=Mission,1=Fence,2=Rally.
@@ -465,14 +519,9 @@ def uploadMission(self, mission_type: int) -> Response:
465519 if not mission_type_check .get ("success" ):
466520 return mission_type_check
467521
468- if mission_type == TYPE_MISSION :
469- loader = self .missionLoader
470- elif mission_type == TYPE_FENCE :
471- loader = self .fenceLoader
472- else :
473- loader = self .rallyLoader
522+ new_loader = self ._parseWaypointsListIntoLoader (waypoints , mission_type )
474523
475- if loader .count () == 0 :
524+ if new_loader .count () == 0 :
476525 return {
477526 "success" : False ,
478527 "message" : f"No waypoints loaded for the mission type of { mission_type } " ,
@@ -487,7 +536,7 @@ def uploadMission(self, mission_type: int) -> Response:
487536 self .drone .master .mav .mission_count_send (
488537 self .drone .target_system ,
489538 self .drone .target_component ,
490- loader .count (),
539+ new_loader .count (),
491540 mission_type = mission_type ,
492541 )
493542
@@ -515,13 +564,11 @@ def uploadMission(self, mission_type: int) -> Response:
515564 }
516565 elif response .mission_type == mission_type :
517566 self .drone .logger .debug (
518- f"Sending mission item { response .seq } out of { loader .count ()} "
519- )
520- self .drone .master .mav .send (
521- wpToMissionItemInt (loader .item (response .seq ))
567+ f"Sending mission item { response .seq } out of { new_loader .count ()- 1 } "
522568 )
569+ self .drone .master .mav .send (new_loader .item (response .seq ))
523570
524- if response .seq == loader .count () - 1 :
571+ if response .seq == new_loader .count () - 1 :
525572 mission_ack_response = self .drone .master .recv_match (
526573 type = [
527574 "MISSION_ACK" ,
@@ -537,6 +584,12 @@ def uploadMission(self, mission_type: int) -> Response:
537584 and mission_ack_response .mission_type == mission_type
538585 ):
539586 self .drone .logger .info ("Uploaded mission successfully" )
587+ if mission_type == TYPE_MISSION :
588+ self .missionLoader = new_loader
589+ elif mission_type == TYPE_FENCE :
590+ self .fenceLoader = new_loader
591+ else :
592+ self .rallyLoader = new_loader
540593 return {
541594 "success" : True ,
542595 "message" : "Mission uploaded successfully" ,
0 commit comments