From 1aed597f9c95aa930dedc0b5d3274f23654ead43 Mon Sep 17 00:00:00 2001 From: Julian Stirling Date: Thu, 2 Jul 2026 09:49:22 +0100 Subject: [PATCH] Smart scan return cancelled if cancelled before stitching starts. --- .../things/smart_scan.py | 15 ++++++++++++--- .../components/tabContentComponents/actionTab.vue | 1 + .../tabContentComponents/slideScanContent.vue | 2 +- 3 files changed, 14 insertions(+), 4 deletions(-) diff --git a/src/openflexure_microscope_server/things/smart_scan.py b/src/openflexure_microscope_server/things/smart_scan.py index d8ce6cf8..d4ee2d59 100644 --- a/src/openflexure_microscope_server/things/smart_scan.py +++ b/src/openflexure_microscope_server/things/smart_scan.py @@ -43,6 +43,7 @@ from .stage import BacklashCompensation, BaseStage T = TypeVar("T") P = ParamSpec("P") +MIN_IMAGES_TO_STITCH = 2 # This allows ActiveScanData to hold arbitrary workflow settings models during a scan. AnyModel = Annotated[ @@ -409,7 +410,10 @@ class SmartScanThing(OFMThing): # This scan can't stitch. return # Begin stitching once two images are captured - if self.scan_data.image_count >= 2 and not self._preview_stitcher.running: + if ( + self.scan_data.image_count >= MIN_IMAGES_TO_STITCH + and not self._preview_stitcher.running + ): self._preview_stitcher.start() @_scan_running @@ -449,9 +453,14 @@ class SmartScanThing(OFMThing): self._main_scan_loop(workflow) self._save_final_scan_data(scan_result="success") - except lt.exceptions.InvocationCancelledError: + except lt.exceptions.InvocationCancelledError as e: self.logger.info("Stopping scan because it was cancelled.") self._save_final_scan_data(scan_result="cancelled by user") + if self.scan_data.image_count < MIN_IMAGES_TO_STITCH: + # If too few images to stitch then, return to the centre and report + # cancelled + self._return_to_starting_position() + raise e except Exception as e: err_name = type(e).__name__ if self._scan_data is not None: @@ -760,6 +769,6 @@ class SmartScanThing(OFMThing): # Use the scan list (the data read by the gallery) to find any scans that # need stitching. for scan in self.get_data_for_gallery(): - if scan.dzi is None and scan.number_of_images >= 2: + if scan.dzi is None and scan.number_of_images >= MIN_IMAGES_TO_STITCH: self.logger.info(f"Stitching {scan.name}") self.stitch_scan(scan_name=scan.name) diff --git a/webapp/src/components/tabContentComponents/actionTab.vue b/webapp/src/components/tabContentComponents/actionTab.vue index 36570daf..dba0fd56 100644 --- a/webapp/src/components/tabContentComponents/actionTab.vue +++ b/webapp/src/components/tabContentComponents/actionTab.vue @@ -66,6 +66,7 @@ mode. submit-label="" :can-terminate="true" @completed="$emit('completed')" + @finished="$emit('finished')" @update:task-status="taskStatus = $event" @update:progress="progress = $event" @update:log="log = $event" diff --git a/webapp/src/components/tabContentComponents/slideScanContent.vue b/webapp/src/components/tabContentComponents/slideScanContent.vue index 6ab945f9..5ea250b8 100644 --- a/webapp/src/components/tabContentComponents/slideScanContent.vue +++ b/webapp/src/components/tabContentComponents/slideScanContent.vue @@ -6,7 +6,7 @@ :task-url="taskUrl" :task-info-title="infoPaneTitle" :task-info-stream="displayImageOnRight" - @completed="onScanCompleted" + @finished="onScanCompleted" @close-task="closeTask" @action-started-externally="startScanning" >