diff --git a/src/openflexure_microscope_server/things/scan_workflows.py b/src/openflexure_microscope_server/things/scan_workflows.py index 4085b5b2..0e2c52e3 100644 --- a/src/openflexure_microscope_server/things/scan_workflows.py +++ b/src/openflexure_microscope_server/things/scan_workflows.py @@ -173,13 +173,13 @@ class RectGridWorkflow(ScanWorkflow[SettingModelType], Generic[SettingModelType] # Redefine _csm Thing Slot, as CSM is required for any RectGridWorkflow _csm: CameraStageMapper = lt.thing_slot() - overlap: float = lt.setting(default=0.45, ge=0.1, le=0.7, multiple_of=0.05) + overlap: float = lt.setting(default=0.45, ge=0.1, le=0.7) """The fraction that adjacent images should overlap in x and y. This must be between 0.1 and 0.7. """ - autofocus_dz: int = lt.setting(default=1000, ge=400, le=3000, multiple_of=200) + autofocus_dz: int = lt.setting(default=1000, ge=400, le=3000) """The z distance to perform an autofocus in steps. Must be greater than or equal to 400, and less than or equal to 3000. @@ -290,7 +290,7 @@ class HistoScanWorkflow(RectGridWorkflow[HistoScanSettingsModel]): This uses the settings from the ``BackgroundDetectThing``. """ - max_range: int = lt.setting(default=45000, multiple_of=1000) + max_range: int = lt.setting(default=45000) """The maximum distance in steps from the centre of the scan.""" # Stacking settings @@ -311,7 +311,7 @@ class HistoScanWorkflow(RectGridWorkflow[HistoScanSettingsModel]): Defaults to 9 which balances reliability and speed. """ - stack_dz: int = lt.setting(default=50, ge=20, le=400, multiple_of=10) + stack_dz: int = lt.setting(default=50, ge=20, le=400) """Distance in steps between images in a z-stack. Suggested values: @@ -538,7 +538,9 @@ class HistoScanWorkflow(RectGridWorkflow[HistoScanSettingsModel]): def settings_ui(self) -> list[PropertyControl]: """A list of PropertyControl objects to create the settings in the scan tab.""" return [ - property_control_for(self, "overlap", label="Image Overlap (0.1-0.7)"), + property_control_for( + self, "overlap", label="Image Overlap (0.1-0.7)", step=0.05 + ), property_control_for( self, "stack_images_to_save", label="Images in Stack to Save" ), @@ -547,9 +549,13 @@ class HistoScanWorkflow(RectGridWorkflow[HistoScanSettingsModel]): "stack_min_images_to_test", label="Minimum number of images to test for focus", ), - property_control_for(self, "stack_dz", label="Stack dz (steps)"), - property_control_for(self, "autofocus_dz", label="Autofocus Range (steps)"), - property_control_for(self, "max_range", label="Maximum Distance (steps)"), + property_control_for(self, "stack_dz", label="Stack dz (steps)", step=5), + property_control_for( + self, "autofocus_dz", label="Autofocus Range (steps)", step=200 + ), + property_control_for( + self, "max_range", label="Maximum Distance (steps)", step=1000 + ), property_control_for( self, "skip_background", label="Detect and Skip Empty Fields " ), @@ -662,7 +668,9 @@ class RegularGridWorkflow(RectGridWorkflow[RegularGridSettingsModel]): def settings_ui(self) -> list[PropertyControl]: """A list of PropertyControl objects to create the settings in the scan tab.""" return [ - property_control_for(self, "overlap", label="Image Overlap (0.1-0.7)"), + property_control_for( + self, "overlap", label="Image Overlap (0.1-0.7)", step=0.05 + ), property_control_for(self, "x_count", label="Number of columns"), property_control_for(self, "y_count", label="Number of rows"), property_control_for(self, "autofocus_dz", label="Autofocus Range (steps)"), diff --git a/src/openflexure_microscope_server/ui.py b/src/openflexure_microscope_server/ui.py index 4347fbbd..3cb4375e 100644 --- a/src/openflexure_microscope_server/ui.py +++ b/src/openflexure_microscope_server/ui.py @@ -97,6 +97,16 @@ class PropertyControl(BaseModel): when selected. """ + step: Optional[int | float] = None + """The step size for a numerical input. + + If the property is not numeric this will be ignored. + + If this is left as None, then the UI will try to use the ``multipleOf`` field in + the property dataSchema. If ``multipleOf`` is not set then the browser default is + used. + """ + def property_control_for( thing: lt.Thing, property_name: str, **kwargs: Any diff --git a/webapp/src/components/labThingsComponents/inputFromSchema.vue b/webapp/src/components/labThingsComponents/inputFromSchema.vue index 519d2bd4..108788f6 100644 --- a/webapp/src/components/labThingsComponents/inputFromSchema.vue +++ b/webapp/src/components/labThingsComponents/inputFromSchema.vue @@ -27,7 +27,7 @@ type="number" :min="minimum" :max="maximum" - :step="step" + :step="spinner_step" @input="grabFocus" @focusout="focusOut" @keydown="keyDown" @@ -152,6 +152,11 @@ export default { default: null, required: false, }, + step: { + type: Number, + default: null, + required: false, + }, }, emits: ["requestUpdate", "sendValue", "animationShown"], @@ -253,8 +258,17 @@ export default { if (this.dataType !== "number") return undefined; return this.dataSchema.minimum; }, - step() { + /** + * The step size for numerical spinners. + * + * If not a number this is `undefined`. If `step` is set as a prop then it is used + * otherwise `multipleOf` from the property `dataSchema` is used. If `multipleOf` + * is not set in the `dataSchema` JS will return `undefined` and the browser will + * use its default value. + */ + spinner_step() { if (this.dataType !== "number") return undefined; + if (this.step !== null) return this.step; return this.dataSchema.multipleOf; }, }, diff --git a/webapp/src/components/labThingsComponents/propertyControl.vue b/webapp/src/components/labThingsComponents/propertyControl.vue index cbf4dd28..8c1ae576 100644 --- a/webapp/src/components/labThingsComponents/propertyControl.vue +++ b/webapp/src/components/labThingsComponents/propertyControl.vue @@ -5,6 +5,7 @@ :label="label" :animate="animate" :options="options" + :step="step" @request-update="readProperty" @send-value="writeProperty" @animation-shown="resetAnimate" @@ -50,6 +51,11 @@ export default { default: null, required: false, }, + step: { + type: Number, + default: null, + required: false, + }, }, data() { diff --git a/webapp/src/components/labThingsComponents/serverSpecifiedPropertyControl.vue b/webapp/src/components/labThingsComponents/serverSpecifiedPropertyControl.vue index 807ec039..9b3e240a 100644 --- a/webapp/src/components/labThingsComponents/serverSpecifiedPropertyControl.vue +++ b/webapp/src/components/labThingsComponents/serverSpecifiedPropertyControl.vue @@ -7,6 +7,7 @@ :read-back="propertyData.read_back" :read-back-delay="propertyData.read_back_delay" :options="propertyData.options" + :step="propertyData.step" />