diff --git a/src/MissionManager/MissionManager.cc b/src/MissionManager/MissionManager.cc index 5b3372f8aaf0de6235ebb68bed3c207edd7e1765..f027f2d857f106f028b7d0d023b6ec1973806c9f 100644 --- a/src/MissionManager/MissionManager.cc +++ b/src/MissionManager/MissionManager.cc @@ -988,7 +988,23 @@ void MissionManager::generateResumeMission(int resumeIndex) } } - resumeIndex = qMin(resumeIndex, _missionItems.count() - 1); + // Be anal about crap input + resumeIndex = qMax(0, qMin(resumeIndex, _missionItems.count() - 1)); + + // Adjust resume index to be a location based command + const MissionCommandUIInfo* uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(_vehicle, _missionItems[resumeIndex]->command()); + if (!uiInfo || uiInfo->isStandaloneCoordinate() || !uiInfo->specifiesCoordinate()) { + // We have to back up to the last command which the vehicle flies through + while (--resumeIndex > 0) { + uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(_vehicle, _missionItems[resumeIndex]->command()); + if (uiInfo && (uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate())) { + // Found it + break; + } + + } + } + resumeIndex = qMax(0, resumeIndex); int seqNum = 0; QList resumeMission; @@ -1008,20 +1024,19 @@ void MissionManager::generateResumeMission(int resumeIndex) << MAV_CMD_IMAGE_STOP_CAPTURE << MAV_CMD_VIDEO_START_CAPTURE << MAV_CMD_VIDEO_STOP_CAPTURE - << MAV_CMD_DO_CHANGE_SPEED; - if (_vehicle->fixedWing() && _vehicle->px4Firmware()) { - includedResumeCommands << MAV_CMD_NAV_TAKEOFF; - } + << MAV_CMD_DO_CHANGE_SPEED + << MAV_CMD_SET_CAMERA_MODE + << MAV_CMD_NAV_TAKEOFF; bool addHomePosition = _vehicle->firmwarePlugin()->sendHomePositionToVehicle(); int setCurrentIndex = addHomePosition ? 1 : 0; - int resumeCommandCount = 0; + int prefixCommandCount = 0; for (int i=0; i<_missionItems.count(); i++) { MissionItem* oldItem = _missionItems[i]; if ((i == 0 && addHomePosition) || i >= resumeIndex || includedResumeCommands.contains(oldItem->command())) { if (i < resumeIndex) { - resumeCommandCount++; + prefixCommandCount++; } MissionItem* newItem = new MissionItem(*oldItem, this); newItem->setIsCurrentItem( i == setCurrentIndex); @@ -1029,91 +1044,56 @@ void MissionManager::generateResumeMission(int resumeIndex) resumeMission.append(newItem); } } + prefixCommandCount = qMax(0, qMin(prefixCommandCount, resumeMission.count())); // Anal prevention against crashes // De-dup and remove no-ops from the commands which were added to the front of the mission bool foundROI = false; - bool foundCamTrigDist = false; - QList imageStartCameraIds; - QList imageStopCameraIds; - QList videoStartCameraIds; - QList videoStopCameraIds; - while (resumeIndex >= 0) { - MissionItem* resumeItem = resumeMission[resumeIndex]; + bool foundCameraSetMode = false; + bool foundCameraStartStop = false; + prefixCommandCount--; // Change from count to array index + while (prefixCommandCount >= 0) { + MissionItem* resumeItem = resumeMission[prefixCommandCount]; switch (resumeItem->command()) { + case MAV_CMD_SET_CAMERA_MODE: + // Only keep the last one + if (foundCameraSetMode) { + resumeMission.removeAt(prefixCommandCount); + } + foundCameraSetMode = true; + break; case MAV_CMD_DO_SET_ROI: // Only keep the last one if (foundROI) { - resumeMission.removeAt(resumeIndex); + resumeMission.removeAt(prefixCommandCount); } foundROI = true; break; case MAV_CMD_DO_SET_CAM_TRIGG_DIST: - // Only keep the last one - if (foundCamTrigDist) { - resumeMission.removeAt(resumeIndex); - } - foundCamTrigDist = true; - break; - case MAV_CMD_IMAGE_START_CAPTURE: - { - // FIXME: Handle single image capture - int cameraId = resumeItem->param1(); - - if (resumeItem->param3() == 1) { - // This is an individual image capture command, remove it - resumeMission.removeAt(resumeIndex); - break; - } - // If we already found an image stop, then all image start/stop commands are useless - // De-dup repeated image start commands - // Otherwise keep only the last image start - if (imageStopCameraIds.contains(cameraId) || imageStartCameraIds.contains(cameraId)) { - resumeMission.removeAt(resumeIndex); - } - if (!imageStopCameraIds.contains(cameraId)) { - imageStopCameraIds.append(cameraId); - } - } - break; case MAV_CMD_IMAGE_STOP_CAPTURE: - { - int cameraId = resumeItem->param1(); - // Image stop only matters to kill all previous image starts - if (!imageStopCameraIds.contains(cameraId)) { - imageStopCameraIds.append(cameraId); - } - resumeMission.removeAt(resumeIndex); - } - break; case MAV_CMD_VIDEO_START_CAPTURE: - { - int cameraId = resumeItem->param1(); - // If we've already found a video stop, then all video start/stop commands are useless - // De-dup repeated video start commands - // Otherwise keep only the last video start - if (videoStopCameraIds.contains(cameraId) || videoStopCameraIds.contains(cameraId)) { - resumeMission.removeAt(resumeIndex); - } - if (!videoStopCameraIds.contains(cameraId)) { - videoStopCameraIds.append(cameraId); + case MAV_CMD_VIDEO_STOP_CAPTURE: + // Only keep the first of these commands that are found + if (foundCameraStartStop) { + resumeMission.removeAt(prefixCommandCount); } - } + foundCameraStartStop = true; break; - case MAV_CMD_VIDEO_STOP_CAPTURE: - { - int cameraId = resumeItem->param1(); - // Video stop only matters to kill all previous video starts - if (!videoStopCameraIds.contains(cameraId)) { - videoStopCameraIds.append(cameraId); + case MAV_CMD_IMAGE_START_CAPTURE: + // Only keep the first of these commands that are found + if (foundCameraStartStop) { + resumeMission.removeAt(prefixCommandCount); } - resumeMission.removeAt(resumeIndex); - } + if (resumeItem->param3() != 0) { + // Remove commands which do no trigger by time + resumeMission.removeAt(prefixCommandCount); + } + foundCameraStartStop = true; break; default: break; } - resumeIndex--; + prefixCommandCount--; } // Send to vehicle