From 24c22a27c94d928cc9908eb7ae0f618c67bbfb9b Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:36:17 -0800 Subject: [PATCH 01/14] MMDevice: adds functions to XYStage and Stage to let them signal whether they use callbacks to update the UI about their position. --- MMDevice/DeviceBase.h | 17 +++++++++++++++++ MMDevice/MMDevice.h | 20 +++++++++++++++++++- 2 files changed, 36 insertions(+), 1 deletion(-) diff --git a/MMDevice/DeviceBase.h b/MMDevice/DeviceBase.h index 8fb7aab1e..e4c9c79f3 100644 --- a/MMDevice/DeviceBase.h +++ b/MMDevice/DeviceBase.h @@ -1893,6 +1893,15 @@ class CStageBase : public CDeviceBase return DEVICE_OK; } + /** + * @brief Return true when your device adapter uses OnStagePositionChanged callbacks. + */ + virtual bool UsesOnStagePositionChanged() + { + return false; + } + + virtual int IsStageLinearSequenceable(bool& isSequenceable) const { isSequenceable = false; @@ -2103,6 +2112,14 @@ class CXYStageBase : public CDeviceBase return this->SetPositionSteps(xSteps+x, ySteps+y); } + /** + * @brief Return true when your device adapter uses OnXYStagePositionChanged callbacks. + */ + virtual bool UsesOnXYStagePositionChanged() + { + return false; + } + virtual int Move(double /*vx*/, double /*vy*/) { return DEVICE_UNSUPPORTED_COMMAND; diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index 0027736ea..dfc7d0f72 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -28,7 +28,7 @@ // Header version // If any of the class definitions changes, the interface version // must be incremented -#define DEVICE_INTERFACE_VERSION 74 +#define DEVICE_INTERFACE_VERSION 75 /////////////////////////////////////////////////////////////////////////////// // N.B. @@ -603,6 +603,15 @@ namespace MM { virtual int SetOrigin() = 0; virtual int GetLimits(double& lower, double& upper) = 0; + /** + * @brief Stages can use the OnStagePositionChanged callback to signal + * updates about their position. Some adapters do so, others do not, + * in which case the UI code should use polling. This function signals whether + * the device adapters uses callbacks, so that the UI knows it does not need + * to poll this device + */ + virtual bool UsesOnStagePositionChanged() = 0; + /** * @brief Return the focus direction. * @@ -709,6 +718,15 @@ namespace MM { virtual int Home() = 0; virtual int Stop() = 0; + /** + * @brief XY stages can use the OnXYStagePositionChanged callback to signal + * updates about their position. Some stage adapters do so, others do not, + * in which case the UI code can use polling. This function signals whether + * the device adapters uses callbacks, so that the UI knows it does not need + * to poll this device + */ + virtual bool UsesOnXYStagePositionChanged() = 0; + /** * @brief Define the current position as the (hardware) origin (0, 0). */ From ea7e26eedd3460fcd6a4112bdec0760e48fd827a Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:46:12 -0800 Subject: [PATCH 02/14] Update MMDevice/MMDevice.h Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- MMDevice/MMDevice.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index dfc7d0f72..bfb764cfc 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -608,7 +608,7 @@ namespace MM { * updates about their position. Some adapters do so, others do not, * in which case the UI code should use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need - * to poll this device + * to poll this device */ virtual bool UsesOnStagePositionChanged() = 0; From ef6f96aaff77e7ac77c0729b90653ce1c578cfc5 Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:46:25 -0800 Subject: [PATCH 03/14] Update MMDevice/MMDevice.h Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- MMDevice/MMDevice.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index bfb764cfc..ab9b8722b 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -604,7 +604,7 @@ namespace MM { virtual int GetLimits(double& lower, double& upper) = 0; /** - * @brief Stages can use the OnStagePositionChanged callback to signal + * @brief Stages can use the OnStagePositionChanged callback to signal * updates about their position. Some adapters do so, others do not, * in which case the UI code should use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need From b3e710f4617b8de2ea98e86941efdbbb88abf6e5 Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:46:36 -0800 Subject: [PATCH 04/14] Update MMDevice/MMDevice.h Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- MMDevice/MMDevice.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index ab9b8722b..76c95213e 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -723,7 +723,7 @@ namespace MM { * updates about their position. Some stage adapters do so, others do not, * in which case the UI code can use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need - * to poll this device + * to poll this device */ virtual bool UsesOnXYStagePositionChanged() = 0; From ec73c596ea9ea909b081201d3a3d912aa6bf5c79 Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:47:17 -0800 Subject: [PATCH 05/14] Update MMDevice/MMDevice.h Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- MMDevice/MMDevice.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index 76c95213e..761267ab4 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -719,7 +719,7 @@ namespace MM { virtual int Stop() = 0; /** - * @brief XY stages can use the OnXYStagePositionChanged callback to signal + * @brief XY stages can use the OnXYStagePositionChanged callback to signal * updates about their position. Some stage adapters do so, others do not, * in which case the UI code can use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need From b7926b57a7dedf7d2d1c74dfd7bbe20f0440e5f4 Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 24 Dec 2025 14:47:29 -0800 Subject: [PATCH 06/14] Update MMDevice/DeviceBase.h Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- MMDevice/DeviceBase.h | 1 - 1 file changed, 1 deletion(-) diff --git a/MMDevice/DeviceBase.h b/MMDevice/DeviceBase.h index e4c9c79f3..429a2437b 100644 --- a/MMDevice/DeviceBase.h +++ b/MMDevice/DeviceBase.h @@ -1901,7 +1901,6 @@ class CStageBase : public CDeviceBase return false; } - virtual int IsStageLinearSequenceable(bool& isSequenceable) const { isSequenceable = false; From ca8573d2f14325eb6bb8a1a2dc247d39a0bf326d Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Thu, 25 Dec 2025 09:59:02 -0800 Subject: [PATCH 07/14] Core and Device: add isStageUsingCallbacks and isXYStageUsingCallbacks functions. Bump MMCore version to 11.12.0. --- MMCore/Devices/StageInstance.cpp | 1 + MMCore/Devices/StageInstance.h | 1 + MMCore/Devices/XYStageInstance.cpp | 1 + MMCore/Devices/XYStageInstance.h | 1 + MMCore/MMCore.cpp | 40 +++++++++++++++++++++++++++++- MMCore/MMCore.h | 2 ++ MMDevice/DeviceBase.h | 12 +++++---- MMDevice/MMDevice.h | 4 +-- 8 files changed, 54 insertions(+), 8 deletions(-) diff --git a/MMCore/Devices/StageInstance.cpp b/MMCore/Devices/StageInstance.cpp index 666f8f9b0..d620f7116 100644 --- a/MMCore/Devices/StageInstance.cpp +++ b/MMCore/Devices/StageInstance.cpp @@ -60,6 +60,7 @@ StageInstance::SetFocusDirection(MM::FocusDirection direction) focusDirectionHasBeenSet_ = true; } +int StageInstance::UsesOnStagePositionChanged(bool& result) const { RequireInitialized(__func__); return GetImpl()->UsesOnStagePositionChanged(result); } int StageInstance::IsStageSequenceable(bool& isSequenceable) const { RequireInitialized(__func__); return GetImpl()->IsStageSequenceable(isSequenceable); } int StageInstance::IsStageLinearSequenceable(bool& isSequenceable) const { RequireInitialized(__func__); return GetImpl()->IsStageLinearSequenceable(isSequenceable); } bool StageInstance::IsContinuousFocusDrive() const { RequireInitialized(__func__); return GetImpl()->IsContinuousFocusDrive(); } diff --git a/MMCore/Devices/StageInstance.h b/MMCore/Devices/StageInstance.h index b94b1e6bf..b4e2cff93 100644 --- a/MMCore/Devices/StageInstance.h +++ b/MMCore/Devices/StageInstance.h @@ -57,6 +57,7 @@ class StageInstance : public DeviceInstanceBase int GetLimits(double& lower, double& upper); MM::FocusDirection GetFocusDirection(); void SetFocusDirection(MM::FocusDirection direction); + int UsesOnStagePositionChanged(bool& result) const; int IsStageSequenceable(bool& isSequenceable) const; int IsStageLinearSequenceable(bool& isSequenceable) const; bool IsContinuousFocusDrive() const; diff --git a/MMCore/Devices/XYStageInstance.cpp b/MMCore/Devices/XYStageInstance.cpp index 56f06844a..0b18bce63 100644 --- a/MMCore/Devices/XYStageInstance.cpp +++ b/MMCore/Devices/XYStageInstance.cpp @@ -42,6 +42,7 @@ int XYStageInstance::SetYOrigin() { RequireInitialized(__func__); return GetImpl int XYStageInstance::GetStepLimits(long& xMin, long& xMax, long& yMin, long& yMax) { RequireInitialized(__func__); return GetImpl()->GetStepLimits(xMin, xMax, yMin, yMax); } double XYStageInstance::GetStepSizeXUm() { RequireInitialized(__func__); return GetImpl()->GetStepSizeXUm(); } double XYStageInstance::GetStepSizeYUm() { RequireInitialized(__func__); return GetImpl()->GetStepSizeYUm(); } +int XYStageInstance::UsesOnXYStagePositionChanged(bool& result) const { RequireInitialized(__func__); return GetImpl()->UsesOnXYStagePositionChanged(result); } int XYStageInstance::IsXYStageSequenceable(bool& isSequenceable) const { RequireInitialized(__func__); return GetImpl()->IsXYStageSequenceable(isSequenceable); } int XYStageInstance::GetXYStageSequenceMaxLength(long& nrEvents) const { RequireInitialized(__func__); return GetImpl()->GetXYStageSequenceMaxLength(nrEvents); } int XYStageInstance::StartXYStageSequence() { RequireInitialized(__func__); return GetImpl()->StartXYStageSequence(); } diff --git a/MMCore/Devices/XYStageInstance.h b/MMCore/Devices/XYStageInstance.h index 9dd21a46e..b6819359f 100644 --- a/MMCore/Devices/XYStageInstance.h +++ b/MMCore/Devices/XYStageInstance.h @@ -56,6 +56,7 @@ class XYStageInstance : public DeviceInstanceBase int GetStepLimits(long& xMin, long& xMax, long& yMin, long& yMax); double GetStepSizeXUm(); double GetStepSizeYUm(); + int UsesOnXYStagePositionChanged(bool& result) const; int IsXYStageSequenceable(bool& isSequenceable) const; int GetXYStageSequenceMaxLength(long& nrEvents) const; int StartXYStageSequence(); diff --git a/MMCore/MMCore.cpp b/MMCore/MMCore.cpp index 0ac29080a..a73b32827 100644 --- a/MMCore/MMCore.cpp +++ b/MMCore/MMCore.cpp @@ -106,7 +106,7 @@ namespace mmi = mmcore::internal; * (Keep the 3 numbers on one line to make it easier to look at diffs when * merging/rebasing.) */ -const int MMCore_versionMajor = 11, MMCore_versionMinor = 11, MMCore_versionPatch = 0; +const int MMCore_versionMajor = 11, MMCore_versionMinor = 12, MMCore_versionPatch = 0; /////////////////////////////////////////////////////////////////////////////// @@ -2265,6 +2265,24 @@ void CMMCore::loadExposureSequence(const char* cameraLabel, std::vector throw CMMError(getDeviceErrorText(ret, pCamera)); } +/** +* Queries whether this stage uses callbacks to signal position changes +* When false, use polling to stay updated about the positionf of the stage +*/ +bool CMMCore::isStageUsingCallbacks(const char* label) MMCORE_LEGACY_THROW(CMMError) +{ + std::shared_ptr pStage = + deviceManager_->GetDeviceOfType(label); + + mmi::DeviceModuleLockGuard guard(pStage); + + bool result; + int ret = pStage->UsesOnStagePositionChanged(result); + if (ret != DEVICE_OK) + throw CMMError(getDeviceErrorText(ret, pStage)); + return result; +} + /** * Queries stage if it can be used in a sequence @@ -2417,6 +2435,26 @@ void CMMCore::setStageLinearSequence(const char* label, double dZ_um, int nSlice throw CMMError(getDeviceErrorText(ret, pStage)); } + +/** +* Queries whether this XYStage uses callbacks to signal position changes +* When false, use polling to stay updated about the positionf of the stage +*/ +bool CMMCore::isXYStageUsingCallbacks(const char* label) MMCORE_LEGACY_THROW(CMMError) +{ + std::shared_ptr pStage = + deviceManager_->GetDeviceOfType(label); + + mmi::DeviceModuleLockGuard guard(pStage); + + bool result; + int ret = pStage->UsesOnXYStagePositionChanged(result); + if (ret != DEVICE_OK) + throw CMMError(getDeviceErrorText(ret, pStage)); + + return result; +} + /** * Queries XY stage if it can be used in a sequence * @param label the XY stage device label diff --git a/MMCore/MMCore.h b/MMCore/MMCore.h index b8d68e056..302255505 100644 --- a/MMCore/MMCore.h +++ b/MMCore/MMCore.h @@ -499,6 +499,7 @@ class CMMCore void setFocusDirection(const char* stageLabel, int sign); int getFocusDirection(const char* stageLabel) MMCORE_LEGACY_THROW(CMMError); + bool isStageUsingCallbacks(const char* stageLabel) MMCORE_LEGACY_THROW(CMMError); bool isStageSequenceable(const char* stageLabel) MMCORE_LEGACY_THROW(CMMError); bool isStageLinearSequenceable(const char* stageLabel) MMCORE_LEGACY_THROW(CMMError); void startStageSequence(const char* stageLabel) MMCORE_LEGACY_THROW(CMMError); @@ -536,6 +537,7 @@ class CMMCore double newXUm, double newYUm) MMCORE_LEGACY_THROW(CMMError); void setAdapterOriginXY(double newXUm, double newYUm) MMCORE_LEGACY_THROW(CMMError); + bool isXYStageUsingCallbacks(const char* xyStageLabel) MMCORE_LEGACY_THROW(CMMError); bool isXYStageSequenceable(const char* xyStageLabel) MMCORE_LEGACY_THROW(CMMError); void startXYStageSequence(const char* xyStageLabel) MMCORE_LEGACY_THROW(CMMError); void stopXYStageSequence(const char* xyStageLabel) MMCORE_LEGACY_THROW(CMMError); diff --git a/MMDevice/DeviceBase.h b/MMDevice/DeviceBase.h index 429a2437b..055dbda33 100644 --- a/MMDevice/DeviceBase.h +++ b/MMDevice/DeviceBase.h @@ -1896,9 +1896,10 @@ class CStageBase : public CDeviceBase /** * @brief Return true when your device adapter uses OnStagePositionChanged callbacks. */ - virtual bool UsesOnStagePositionChanged() + virtual int UsesOnStagePositionChanged(bool& result) const { - return false; + result = false; + return DEVICE_OK; } virtual int IsStageLinearSequenceable(bool& isSequenceable) const @@ -2112,11 +2113,12 @@ class CXYStageBase : public CDeviceBase } /** - * @brief Return true when your device adapter uses OnXYStagePositionChanged callbacks. + * @brief Return true when your device adapter uses OnXYStagePositionChanged callbacks. */ - virtual bool UsesOnXYStagePositionChanged() + virtual int UsesOnXYStagePositionChanged(bool& result) const { - return false; + result = false; + return DEVICE_OK; } virtual int Move(double /*vx*/, double /*vy*/) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index 761267ab4..201dba3c6 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -610,7 +610,7 @@ namespace MM { * the device adapters uses callbacks, so that the UI knows it does not need * to poll this device */ - virtual bool UsesOnStagePositionChanged() = 0; + virtual int UsesOnStagePositionChanged(bool& result) const = 0; /** * @brief Return the focus direction. @@ -725,7 +725,7 @@ namespace MM { * the device adapters uses callbacks, so that the UI knows it does not need * to poll this device */ - virtual bool UsesOnXYStagePositionChanged() = 0; + virtual int UsesOnXYStagePositionChanged(bool &result) const = 0; /** * @brief Define the current position as the (hardware) origin (0, 0). From d16efd56a9c38a41e99f9bfc3f8bb1845a53b565 Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Fri, 16 Jan 2026 15:04:35 -0800 Subject: [PATCH 08/14] DeviceAdapters: implement overrides for UsesPositionChanged functions in DeviceAdapters that use the OnStage (and OnXYStage) PosityionChanged callbacks. I did not fully check all device adapters to make sure they use the callbacks all the time, nevertheless, this seems a good start. --- DeviceAdapters/ASIStage/ASIZStage.h | 2 ++ DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h | 1 + DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h | 2 ++ DeviceAdapters/Cephla/Squid.h | 3 +++ DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h | 2 ++ DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h | 1 + DeviceAdapters/DemoCamera/DemoCamera.h | 3 +++ DeviceAdapters/ESP32/esp32.h | 4 ++++ DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h | 2 ++ DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h | 2 ++ DeviceAdapters/MoticMicroscope/MoticMicroscope.h | 4 ++++ DeviceAdapters/NewportCONEX/Conex_Axis.h | 2 ++ .../NotificationTester/NotificationTester.cpp | 10 ++++++++++ DeviceAdapters/OpenFlexure/OpenFlexure.h | 5 +++++ DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h | 4 ++++ DeviceAdapters/PriorPureFocus/PureFocus.h | 3 +++ DeviceAdapters/PyDevice/PyStage.h | 9 +++++++++ DeviceAdapters/SouthPort/microz.h | 2 ++ DeviceAdapters/Standa/Standa.h | 2 ++ DeviceAdapters/Standa8SMC4/Standa8SMC4.h | 4 ++++ DeviceAdapters/StandaStage/StandaStage.h | 3 +++ DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h | 2 ++ DeviceAdapters/TriggerScope/TriggerScope.h | 2 ++ DeviceAdapters/WOSM/WOSM.h | 4 ++++ DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h | 3 ++- DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h | 3 ++- DeviceAdapters/ZeissCAN29/ZeissCAN29.h | 4 ++++ 27 files changed, 86 insertions(+), 2 deletions(-) diff --git a/DeviceAdapters/ASIStage/ASIZStage.h b/DeviceAdapters/ASIStage/ASIZStage.h index f9a5cfefe..c37b19a19 100644 --- a/DeviceAdapters/ASIStage/ASIZStage.h +++ b/DeviceAdapters/ASIStage/ASIZStage.h @@ -37,6 +37,8 @@ class ZStage : public CStageBase, public ASIBase bool IsContinuousFocusDrive() const { return false; } + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); int OnAxis(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h b/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h index c8d671de3..9c007484a 100644 --- a/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h +++ b/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h @@ -66,6 +66,7 @@ class RAMPSXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const; + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } // action interface // ---------------- diff --git a/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h b/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h index 61f225ed5..7ac6d0393 100644 --- a/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h +++ b/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h @@ -66,6 +66,8 @@ class RAMPSZStage : public CStageBase bool IsContinuousFocusDrive() const; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPosition(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/Cephla/Squid.h b/DeviceAdapters/Cephla/Squid.h index 9de90b272..b1bf35020 100644 --- a/DeviceAdapters/Cephla/Squid.h +++ b/DeviceAdapters/Cephla/Squid.h @@ -284,6 +284,7 @@ class SquidXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } // action interface // ---------------- @@ -354,6 +355,8 @@ class SquidZStage : public CStageBase } bool IsContinuousFocusDrive() const { return false; }; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + int OnAcceleration(MM::PropertyBase* pProp, MM::ActionType eAct); int OnMaxVelocity(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h b/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h index d8e5c3aba..d9ce7ff8a 100644 --- a/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h +++ b/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h @@ -119,6 +119,7 @@ class MD_SingleStage: // Checking device functions int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return DEVICE_OK;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } bool SupportsDeviceDetection(void); MM::DeviceDetectionStatus DetectDevice(void); @@ -227,6 +228,7 @@ public CXYStageBase double GetStepSizeYUm() { return stepSize_umY_; } int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } MM::DeviceDetectionStatus DetectDevice(void); protected: // check controller diff --git a/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h b/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h index 6df86506d..45d77a21e 100644 --- a/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h +++ b/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h @@ -251,6 +251,7 @@ class ChuoSeikiZStage : public CStageBase bool IsContinuousFocusDrive() const {return DEVICE_OK;} bool SupportsDeviceDetection(void){return DEVICE_OK;} MM::DeviceDetectionStatus DetectDevice(void); + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } private: diff --git a/DeviceAdapters/DemoCamera/DemoCamera.h b/DeviceAdapters/DemoCamera/DemoCamera.h index f6fc343ed..eb238f008 100644 --- a/DeviceAdapters/DemoCamera/DemoCamera.h +++ b/DeviceAdapters/DemoCamera/DemoCamera.h @@ -498,6 +498,8 @@ class CDemoStage : public CStageBase bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPosition(MM::PropertyBase* pProp, MM::ActionType eAct); @@ -578,6 +580,7 @@ class CDemoXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } // action interface // ---------------- diff --git a/DeviceAdapters/ESP32/esp32.h b/DeviceAdapters/ESP32/esp32.h index 60101a955..6f0f8a90b 100644 --- a/DeviceAdapters/ESP32/esp32.h +++ b/DeviceAdapters/ESP32/esp32.h @@ -325,6 +325,8 @@ class CESP32Stage : public CStageBase nrEvents = 0; return DEVICE_OK; } + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + private: double stepSizeUm_; double pos_um_; @@ -389,6 +391,8 @@ class CESP32XYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + int OnXStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnXStageMaxPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnYStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h index 540404b0e..594b278f0 100644 --- a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h +++ b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h @@ -46,6 +46,8 @@ class MCL_NanoDrive_XYStage : public CXYStageBase virtual double GetStepSizeYUm(); virtual int IsXYStageSequenceable(bool& isSequenceable) const; + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // Action interface int OnLowerLimitX(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimitX(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h index a54ab54e7..8a4a7dc53 100644 --- a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h +++ b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h @@ -51,6 +51,8 @@ class MCL_NanoDrive_ZStage : public CStageBase virtual int SendStageSequence(); virtual bool IsContinuousFocusDrive() const; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // Action interface int OnLowerLimit(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/MoticMicroscope/MoticMicroscope.h b/DeviceAdapters/MoticMicroscope/MoticMicroscope.h index 5875b773c..2e149c107 100644 --- a/DeviceAdapters/MoticMicroscope/MoticMicroscope.h +++ b/DeviceAdapters/MoticMicroscope/MoticMicroscope.h @@ -128,6 +128,8 @@ class XYStage : public CXYStageBase, public EventReceiver virtual int IsXYStageSequenceable(bool& isSequenceable) const; + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + void EventHandler(int eventId, int data); private: int _init; @@ -166,6 +168,8 @@ class ZStage : public CStageBase, public EventReceiver virtual bool IsContinuousFocusDrive() const; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + void EventHandler(int eventId, int data); private: int _init; diff --git a/DeviceAdapters/NewportCONEX/Conex_Axis.h b/DeviceAdapters/NewportCONEX/Conex_Axis.h index 94b9d8810..e45fc0afc 100644 --- a/DeviceAdapters/NewportCONEX/Conex_Axis.h +++ b/DeviceAdapters/NewportCONEX/Conex_Axis.h @@ -118,6 +118,8 @@ class Axis : public CStageBase, public Conex_AxisBase bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPort (MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/NotificationTester/NotificationTester.cpp b/DeviceAdapters/NotificationTester/NotificationTester.cpp index 9683ac9c1..0d3a0b5dd 100644 --- a/DeviceAdapters/NotificationTester/NotificationTester.cpp +++ b/DeviceAdapters/NotificationTester/NotificationTester.cpp @@ -395,6 +395,11 @@ class NTestStage : public CStageBase> bool IsContinuousFocusDrive() const final { return false; } + + int UsesOnStagePositionChanged(bool& result) const final { + result = true; + return DEVICE_OK; + } }; template @@ -610,6 +615,11 @@ class NTestXYStage : public CXYStageBase> flag = false; return DEVICE_OK; } + + int UsesOnXYStagePositionChanged(bool& result) const final { + result = true; + return DEVICE_OK; + } }; MODULE_API void InitializeModuleData() diff --git a/DeviceAdapters/OpenFlexure/OpenFlexure.h b/DeviceAdapters/OpenFlexure/OpenFlexure.h index c72e8bd81..dd8437394 100644 --- a/DeviceAdapters/OpenFlexure/OpenFlexure.h +++ b/DeviceAdapters/OpenFlexure/OpenFlexure.h @@ -123,6 +123,8 @@ class XYStage : public CXYStageBase int GetLimitsUm(double& xMin, double& xMax, double& yMin, double& yMax); int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + bool Busy() { return false; } void GetName(char*) const; @@ -165,6 +167,9 @@ class ZStage : public CStageBase int GetLimits(double& lower, double& upper) { return DEVICE_UNSUPPORTED_COMMAND;} // nah int IsStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const { return false; } + + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + bool Busy() { return false; } // Helper functions diff --git a/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h b/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h index 4952fccfa..0af3f27cc 100644 --- a/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h +++ b/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h @@ -119,6 +119,8 @@ class CPiezoConceptStage : public CStageBase int GetStageSequenceMaxLength(long& nrEvents) const { nrEvents = 0; return DEVICE_OK; } + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + private: double stepSizeUm_; double pos_um_; @@ -182,6 +184,8 @@ class CPiezoConceptXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + int OnXStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnXStageMaxPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnYStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/PriorPureFocus/PureFocus.h b/DeviceAdapters/PriorPureFocus/PureFocus.h index 5e94fd27a..4bebb5744 100644 --- a/DeviceAdapters/PriorPureFocus/PureFocus.h +++ b/DeviceAdapters/PriorPureFocus/PureFocus.h @@ -170,6 +170,9 @@ class PureFocusOffset : public CStageBase { bool IsContinuousFocusDrive() const { return false; }; + + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + void CallbackPositionSteps(long steps); void RemoveHub() { pHub_ = 0; }; diff --git a/DeviceAdapters/PyDevice/PyStage.h b/DeviceAdapters/PyDevice/PyStage.h index dc0fa9430..3ec6665aa 100644 --- a/DeviceAdapters/PyDevice/PyStage.h +++ b/DeviceAdapters/PyDevice/PyStage.h @@ -32,6 +32,10 @@ class CPyStage : public PyStageClass { bool IsContinuousFocusDrive() const override { return true; } + int UsesOnStagePositionChanged(bool& result) const override { + result = true; + return DEVICE_OK; + } protected: double StepSizeUm() const; double origin_ = 0.0; @@ -118,6 +122,11 @@ class CPyXYStage : public PyXYStageClass { return DEVICE_UNSUPPORTED_COMMAND; } + int UsesOnXYStagePositionChanged(bool& result) const override { + result = true; + return DEVICE_OK; + } + protected: double origin_x_ = 0.0; double origin_y_ = 0.0; diff --git a/DeviceAdapters/SouthPort/microz.h b/DeviceAdapters/SouthPort/microz.h index 785a0ead1..601e37d8c 100644 --- a/DeviceAdapters/SouthPort/microz.h +++ b/DeviceAdapters/SouthPort/microz.h @@ -53,6 +53,8 @@ class MicroZStage : public CStageBase bool IsContinuousFocusDrive() const; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // Sequence functions int IsStageSequenceable(bool& isSequenceable) const; int GetStageSequenceMaxLength(long& nrEvents) const; diff --git a/DeviceAdapters/Standa/Standa.h b/DeviceAdapters/Standa/Standa.h index fd67a6a4a..3fdc7693e 100644 --- a/DeviceAdapters/Standa/Standa.h +++ b/DeviceAdapters/Standa/Standa.h @@ -62,6 +62,8 @@ class StandaZStage : public CStageBase int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnAxisLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/Standa8SMC4/Standa8SMC4.h b/DeviceAdapters/Standa8SMC4/Standa8SMC4.h index de070083e..be436bfa1 100644 --- a/DeviceAdapters/Standa8SMC4/Standa8SMC4.h +++ b/DeviceAdapters/Standa8SMC4/Standa8SMC4.h @@ -58,6 +58,8 @@ class Standa8SMC4Z : public CStageBase virtual bool IsContinuousFocusDrive() const; + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); @@ -110,6 +112,8 @@ class Standa8SMC4XY : public CXYStageBase virtual bool IsContinuousFocusDrive() const; + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPortX(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/StandaStage/StandaStage.h b/DeviceAdapters/StandaStage/StandaStage.h index ae20308cc..128142436 100644 --- a/DeviceAdapters/StandaStage/StandaStage.h +++ b/DeviceAdapters/StandaStage/StandaStage.h @@ -116,6 +116,8 @@ class CStandaStage : public CStageBase bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- @@ -266,6 +268,7 @@ class CStandaXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } // action interface // ---------------- diff --git a/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h b/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h index 46cd807d2..ea2b8a811 100644 --- a/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h +++ b/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h @@ -80,6 +80,8 @@ class ThorlabsAPTStage : public CStageBase int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/TriggerScope/TriggerScope.h b/DeviceAdapters/TriggerScope/TriggerScope.h index fe2cdbe8d..366aa366e 100644 --- a/DeviceAdapters/TriggerScope/TriggerScope.h +++ b/DeviceAdapters/TriggerScope/TriggerScope.h @@ -348,6 +348,8 @@ class CTriggerScopeFocus : public CStageBase bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + int OnSequence(MM::PropertyBase* pProp, MM::ActionType eAct); int OnDACNumber(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WOSM/WOSM.h b/DeviceAdapters/WOSM/WOSM.h index 542475bf3..34206d72e 100644 --- a/DeviceAdapters/WOSM/WOSM.h +++ b/DeviceAdapters/WOSM/WOSM.h @@ -330,6 +330,8 @@ class CWOSMStage : public CStageBase nrEvents = 0; return DEVICE_OK; } + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + private: double stepSizeUm_; double pos_um_; @@ -394,6 +396,8 @@ class CWOSMXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + int OnXStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnXStageMaxPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnYStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h b/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h index 889e6c613..91941e580 100644 --- a/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h +++ b/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h @@ -77,7 +77,8 @@ class ZPiezoCANDevice : public CStageBase int SetOrigin(); int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} - + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h b/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h index e99c444a7..dbd0c7300 100644 --- a/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h +++ b/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h @@ -77,7 +77,8 @@ class ZPiezoWSDevice : public CStageBase int SetOrigin(); int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} - + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/ZeissCAN29/ZeissCAN29.h b/DeviceAdapters/ZeissCAN29/ZeissCAN29.h index 79ef67051..f251d11d3 100644 --- a/DeviceAdapters/ZeissCAN29/ZeissCAN29.h +++ b/DeviceAdapters/ZeissCAN29/ZeissCAN29.h @@ -836,6 +836,8 @@ class Axis : public CStageBase, public ZeissAxis int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return false;} + int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnPosition(MM::PropertyBase* pProp, MM::ActionType eAct); @@ -890,6 +892,8 @@ class XYStage : public CXYStageBase, public ZeissAxis double GetStepSizeYUm() {return stepSize_um_;} int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} + int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } + // action interface // ---------------- int OnMoveMode(MM::PropertyBase* pProp, MM::ActionType eAct); From ec8d201b15ba55b3ec52b39b9d8bc4d906158c4e Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Wed, 21 Jan 2026 09:36:40 -0800 Subject: [PATCH 09/14] MMDevice: explained that UsesOnStagePositionChanged functions should always return the same value as the UI will not query these functions continuously. --- MMDevice/MMDevice.h | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index 201dba3c6..23eb2c4bd 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -608,7 +608,9 @@ namespace MM { * updates about their position. Some adapters do so, others do not, * in which case the UI code should use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need - * to poll this device + * to poll this device. It is best practice to not change the result of this + * function (i.e. use a const value) as the UI will query the function + * only once. */ virtual int UsesOnStagePositionChanged(bool& result) const = 0; @@ -723,7 +725,9 @@ namespace MM { * updates about their position. Some stage adapters do so, others do not, * in which case the UI code can use polling. This function signals whether * the device adapters uses callbacks, so that the UI knows it does not need - * to poll this device + * to poll this device. It is best practice to not change the result of this + * function (i.e. use a const value) as the UI will query the function + * only once. */ virtual int UsesOnXYStagePositionChanged(bool &result) const = 0; From 386743a3ef6a3037f743142532f20da27b2d8f8a Mon Sep 17 00:00:00 2001 From: Nico Stuurman Date: Thu, 29 Jan 2026 18:00:07 -0800 Subject: [PATCH 10/14] Devices: revert adding UsesOnStagePositionChanged defaults unless completely confident they actually do (ZeissCAN29, DemoCamera, Cephla) --- DeviceAdapters/ASIStage/ASIZStage.h | 2 -- DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h | 2 -- DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h | 2 -- DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h | 1 - DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h | 1 - DeviceAdapters/ESP32/esp32.h | 2 -- DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h | 2 -- DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h | 2 -- DeviceAdapters/MoticMicroscope/MoticMicroscope.h | 4 ---- DeviceAdapters/NewportCONEX/Conex_Axis.h | 2 -- .../NotificationTester/NotificationTester.cpp | 10 ---------- DeviceAdapters/OpenFlexure/OpenFlexure.h | 4 ---- DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h | 4 ---- DeviceAdapters/PriorPureFocus/PureFocus.h | 2 -- DeviceAdapters/PyDevice/PyStage.h | 6 +----- DeviceAdapters/SouthPort/microz.h | 2 -- DeviceAdapters/Standa/Standa.h | 2 -- DeviceAdapters/Standa8SMC4/Standa8SMC4.h | 4 ---- DeviceAdapters/StandaStage/StandaStage.h | 4 ---- DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h | 2 -- DeviceAdapters/TriggerScope/TriggerScope.h | 2 -- DeviceAdapters/WOSM/WOSM.h | 4 ---- DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h | 2 -- DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h | 2 -- 24 files changed, 1 insertion(+), 69 deletions(-) diff --git a/DeviceAdapters/ASIStage/ASIZStage.h b/DeviceAdapters/ASIStage/ASIZStage.h index c37b19a19..f9a5cfefe 100644 --- a/DeviceAdapters/ASIStage/ASIZStage.h +++ b/DeviceAdapters/ASIStage/ASIZStage.h @@ -37,8 +37,6 @@ class ZStage : public CStageBase, public ASIBase bool IsContinuousFocusDrive() const { return false; } - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); int OnAxis(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h b/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h index 9c007484a..a340f38c8 100644 --- a/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h +++ b/DeviceAdapters/CNCMicroscope/RAMPSStage/XYStage.h @@ -66,8 +66,6 @@ class RAMPSXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const; - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPosition(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h b/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h index 7ac6d0393..61f225ed5 100644 --- a/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h +++ b/DeviceAdapters/CNCMicroscope/RAMPSStage/ZStage.h @@ -66,8 +66,6 @@ class RAMPSZStage : public CStageBase bool IsContinuousFocusDrive() const; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPosition(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h b/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h index d9ce7ff8a..83ad90796 100644 --- a/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h +++ b/DeviceAdapters/ChuoSeiki_MD5000/ChuoSeiki_MD_XYZ.h @@ -228,7 +228,6 @@ public CXYStageBase double GetStepSizeYUm() { return stepSize_umY_; } int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK; } - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } MM::DeviceDetectionStatus DetectDevice(void); protected: // check controller diff --git a/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h b/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h index 45d77a21e..6df86506d 100644 --- a/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h +++ b/DeviceAdapters/ChuoSeiki_QT/ChuoSeiki_QT_XYZ.h @@ -251,7 +251,6 @@ class ChuoSeikiZStage : public CStageBase bool IsContinuousFocusDrive() const {return DEVICE_OK;} bool SupportsDeviceDetection(void){return DEVICE_OK;} MM::DeviceDetectionStatus DetectDevice(void); - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } private: diff --git a/DeviceAdapters/ESP32/esp32.h b/DeviceAdapters/ESP32/esp32.h index 6f0f8a90b..892f58995 100644 --- a/DeviceAdapters/ESP32/esp32.h +++ b/DeviceAdapters/ESP32/esp32.h @@ -325,8 +325,6 @@ class CESP32Stage : public CStageBase nrEvents = 0; return DEVICE_OK; } - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - private: double stepSizeUm_; double pos_um_; diff --git a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h index 594b278f0..540404b0e 100644 --- a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h +++ b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_XYStage.h @@ -46,8 +46,6 @@ class MCL_NanoDrive_XYStage : public CXYStageBase virtual double GetStepSizeYUm(); virtual int IsXYStageSequenceable(bool& isSequenceable) const; - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // Action interface int OnLowerLimitX(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimitX(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h index 8a4a7dc53..a54ab54e7 100644 --- a/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h +++ b/DeviceAdapters/MCL_NanoDrive/MCL_NanoDrive_ZStage.h @@ -51,8 +51,6 @@ class MCL_NanoDrive_ZStage : public CStageBase virtual int SendStageSequence(); virtual bool IsContinuousFocusDrive() const; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // Action interface int OnLowerLimit(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/MoticMicroscope/MoticMicroscope.h b/DeviceAdapters/MoticMicroscope/MoticMicroscope.h index 2e149c107..5875b773c 100644 --- a/DeviceAdapters/MoticMicroscope/MoticMicroscope.h +++ b/DeviceAdapters/MoticMicroscope/MoticMicroscope.h @@ -128,8 +128,6 @@ class XYStage : public CXYStageBase, public EventReceiver virtual int IsXYStageSequenceable(bool& isSequenceable) const; - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - void EventHandler(int eventId, int data); private: int _init; @@ -168,8 +166,6 @@ class ZStage : public CStageBase, public EventReceiver virtual bool IsContinuousFocusDrive() const; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - void EventHandler(int eventId, int data); private: int _init; diff --git a/DeviceAdapters/NewportCONEX/Conex_Axis.h b/DeviceAdapters/NewportCONEX/Conex_Axis.h index e45fc0afc..94b9d8810 100644 --- a/DeviceAdapters/NewportCONEX/Conex_Axis.h +++ b/DeviceAdapters/NewportCONEX/Conex_Axis.h @@ -118,8 +118,6 @@ class Axis : public CStageBase, public Conex_AxisBase bool IsContinuousFocusDrive() const {return false;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPort (MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/NotificationTester/NotificationTester.cpp b/DeviceAdapters/NotificationTester/NotificationTester.cpp index 0d3a0b5dd..9683ac9c1 100644 --- a/DeviceAdapters/NotificationTester/NotificationTester.cpp +++ b/DeviceAdapters/NotificationTester/NotificationTester.cpp @@ -395,11 +395,6 @@ class NTestStage : public CStageBase> bool IsContinuousFocusDrive() const final { return false; } - - int UsesOnStagePositionChanged(bool& result) const final { - result = true; - return DEVICE_OK; - } }; template @@ -615,11 +610,6 @@ class NTestXYStage : public CXYStageBase> flag = false; return DEVICE_OK; } - - int UsesOnXYStagePositionChanged(bool& result) const final { - result = true; - return DEVICE_OK; - } }; MODULE_API void InitializeModuleData() diff --git a/DeviceAdapters/OpenFlexure/OpenFlexure.h b/DeviceAdapters/OpenFlexure/OpenFlexure.h index dd8437394..103139cb8 100644 --- a/DeviceAdapters/OpenFlexure/OpenFlexure.h +++ b/DeviceAdapters/OpenFlexure/OpenFlexure.h @@ -123,8 +123,6 @@ class XYStage : public CXYStageBase int GetLimitsUm(double& xMin, double& xMax, double& yMin, double& yMax); int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - bool Busy() { return false; } void GetName(char*) const; @@ -168,8 +166,6 @@ class ZStage : public CStageBase int IsStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const { return false; } - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - bool Busy() { return false; } // Helper functions diff --git a/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h b/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h index 0af3f27cc..4952fccfa 100644 --- a/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h +++ b/DeviceAdapters/PIEZOCONCEPT/PIEZOCONCEPT.h @@ -119,8 +119,6 @@ class CPiezoConceptStage : public CStageBase int GetStageSequenceMaxLength(long& nrEvents) const { nrEvents = 0; return DEVICE_OK; } - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - private: double stepSizeUm_; double pos_um_; @@ -184,8 +182,6 @@ class CPiezoConceptXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - int OnXStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnXStageMaxPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnYStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/PriorPureFocus/PureFocus.h b/DeviceAdapters/PriorPureFocus/PureFocus.h index 4bebb5744..bdb901d55 100644 --- a/DeviceAdapters/PriorPureFocus/PureFocus.h +++ b/DeviceAdapters/PriorPureFocus/PureFocus.h @@ -171,8 +171,6 @@ class PureFocusOffset : public CStageBase { return false; }; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - void CallbackPositionSteps(long steps); void RemoveHub() { pHub_ = 0; }; diff --git a/DeviceAdapters/PyDevice/PyStage.h b/DeviceAdapters/PyDevice/PyStage.h index 3ec6665aa..4ac22f728 100644 --- a/DeviceAdapters/PyDevice/PyStage.h +++ b/DeviceAdapters/PyDevice/PyStage.h @@ -32,10 +32,6 @@ class CPyStage : public PyStageClass { bool IsContinuousFocusDrive() const override { return true; } - int UsesOnStagePositionChanged(bool& result) const override { - result = true; - return DEVICE_OK; - } protected: double StepSizeUm() const; double origin_ = 0.0; @@ -123,7 +119,7 @@ class CPyXYStage : public PyXYStageClass { } int UsesOnXYStagePositionChanged(bool& result) const override { - result = true; + result = false; return DEVICE_OK; } diff --git a/DeviceAdapters/SouthPort/microz.h b/DeviceAdapters/SouthPort/microz.h index 601e37d8c..785a0ead1 100644 --- a/DeviceAdapters/SouthPort/microz.h +++ b/DeviceAdapters/SouthPort/microz.h @@ -53,8 +53,6 @@ class MicroZStage : public CStageBase bool IsContinuousFocusDrive() const; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // Sequence functions int IsStageSequenceable(bool& isSequenceable) const; int GetStageSequenceMaxLength(long& nrEvents) const; diff --git a/DeviceAdapters/Standa/Standa.h b/DeviceAdapters/Standa/Standa.h index 3fdc7693e..fd67a6a4a 100644 --- a/DeviceAdapters/Standa/Standa.h +++ b/DeviceAdapters/Standa/Standa.h @@ -62,8 +62,6 @@ class StandaZStage : public CStageBase int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return false;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnAxisLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/Standa8SMC4/Standa8SMC4.h b/DeviceAdapters/Standa8SMC4/Standa8SMC4.h index be436bfa1..de070083e 100644 --- a/DeviceAdapters/Standa8SMC4/Standa8SMC4.h +++ b/DeviceAdapters/Standa8SMC4/Standa8SMC4.h @@ -58,8 +58,6 @@ class Standa8SMC4Z : public CStageBase virtual bool IsContinuousFocusDrive() const; - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); @@ -112,8 +110,6 @@ class Standa8SMC4XY : public CXYStageBase virtual bool IsContinuousFocusDrive() const; - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPortX(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/StandaStage/StandaStage.h b/DeviceAdapters/StandaStage/StandaStage.h index 128142436..d5feac1da 100644 --- a/DeviceAdapters/StandaStage/StandaStage.h +++ b/DeviceAdapters/StandaStage/StandaStage.h @@ -116,8 +116,6 @@ class CStandaStage : public CStageBase bool IsContinuousFocusDrive() const {return false;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- @@ -268,8 +266,6 @@ class CStandaXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- diff --git a/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h b/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h index ea2b8a811..46cd807d2 100644 --- a/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h +++ b/DeviceAdapters/ThorlabsAPTStage/ThorlabsAPTStage.h @@ -80,8 +80,6 @@ class ThorlabsAPTStage : public CStageBase int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} bool IsContinuousFocusDrive() const {return false;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/TriggerScope/TriggerScope.h b/DeviceAdapters/TriggerScope/TriggerScope.h index 366aa366e..fe2cdbe8d 100644 --- a/DeviceAdapters/TriggerScope/TriggerScope.h +++ b/DeviceAdapters/TriggerScope/TriggerScope.h @@ -348,8 +348,6 @@ class CTriggerScopeFocus : public CStageBase bool IsContinuousFocusDrive() const {return false;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - int OnSequence(MM::PropertyBase* pProp, MM::ActionType eAct); int OnDACNumber(MM::PropertyBase* pProp, MM::ActionType eAct); int OnUpperLimit(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WOSM/WOSM.h b/DeviceAdapters/WOSM/WOSM.h index 34206d72e..542475bf3 100644 --- a/DeviceAdapters/WOSM/WOSM.h +++ b/DeviceAdapters/WOSM/WOSM.h @@ -330,8 +330,6 @@ class CWOSMStage : public CStageBase nrEvents = 0; return DEVICE_OK; } - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - private: double stepSizeUm_; double pos_um_; @@ -396,8 +394,6 @@ class CWOSMXYStage : public CXYStageBase int IsXYStageSequenceable(bool& isSequenceable) const { isSequenceable = false; return DEVICE_OK; } - int UsesOnXYStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - int OnXStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnXStageMaxPos(MM::PropertyBase* pProp, MM::ActionType eAct); int OnYStageMinPos(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h b/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h index 91941e580..c22daaf05 100644 --- a/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h +++ b/DeviceAdapters/WieneckeSinske/ZPiezoCanDevice.h @@ -77,8 +77,6 @@ class ZPiezoCANDevice : public CStageBase int SetOrigin(); int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); diff --git a/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h b/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h index dbd0c7300..1a47c3b1d 100644 --- a/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h +++ b/DeviceAdapters/WieneckeSinske/ZPiezoWSDevice.h @@ -77,8 +77,6 @@ class ZPiezoWSDevice : public CStageBase int SetOrigin(); int IsStageSequenceable(bool& isSequenceable) const {isSequenceable = false; return DEVICE_OK;} - int UsesOnStagePositionChanged(bool& result) const { result = true; return DEVICE_OK; } - // action interface // ---------------- int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); From 242e6b5d93c4c1a59eb0616da09a6f02ec711877 Mon Sep 17 00:00:00 2001 From: "Mark A. Tsuchida" Date: Fri, 20 Feb 2026 15:59:39 -0600 Subject: [PATCH 11/14] Remove the doProcess flag from InsertImage() --- MMCore/CircularBuffer.cpp | 12 +++-------- MMCore/CircularBuffer.h | 5 +++-- MMCore/CoreCallback.cpp | 43 ++++++++------------------------------- MMCore/CoreCallback.h | 8 ++++++-- MMDevice/MMDevice.h | 21 +++++++++++-------- 5 files changed, 34 insertions(+), 55 deletions(-) diff --git a/MMCore/CircularBuffer.cpp b/MMCore/CircularBuffer.cpp index 448e6f9a0..9db6b396e 100644 --- a/MMCore/CircularBuffer.cpp +++ b/MMCore/CircularBuffer.cpp @@ -192,18 +192,12 @@ static std::string FormatLocalTime(std::chrono::time_pointProcess(const_cast(buf), width, height, byteDepth); - } - } - if (core_->cbuf_->InsertImage(buf, width, height, byteDepth, &md)) - return DEVICE_OK; - else - return DEVICE_BUFFER_OVERFLOW; - } - catch (CMMError& /*e*/) - { - return DEVICE_INCOMPATIBLE_IMAGE; - } + return InsertImage(caller, buf, width, height, bytesPerPixel, 1, serializedMetadata); } -int CoreCallback::InsertImage(const MM::Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned byteDepth, unsigned nComponents, const char* serializedMetadata, const bool doProcess) +int CoreCallback::InsertImage(const MM::Device* caller, const unsigned char* buf, + unsigned width, unsigned height, unsigned bytesPerPixel, unsigned nComponents, + const char* serializedMetadata) { Metadata origMd; if (serializedMetadata) @@ -261,15 +239,12 @@ int CoreCallback::InsertImage(const MM::Device* caller, const unsigned char* buf { Metadata md = AddCameraMetadata(caller, &origMd); - if(doProcess) - { MM::ImageProcessor* ip = GetImageProcessor(caller); if( NULL != ip) { - ip->Process(const_cast(buf), width, height, byteDepth); + ip->Process(const_cast(buf), width, height, bytesPerPixel); } - } - if (core_->cbuf_->InsertImage(buf, width, height, byteDepth, nComponents, &md)) + if (core_->cbuf_->InsertImage(buf, width, height, bytesPerPixel, nComponents, &md)) return DEVICE_OK; else return DEVICE_BUFFER_OVERFLOW; diff --git a/MMCore/CoreCallback.h b/MMCore/CoreCallback.h index e31e8966d..74bb1f10b 100644 --- a/MMCore/CoreCallback.h +++ b/MMCore/CoreCallback.h @@ -84,8 +84,12 @@ class CoreCallback : public MM::Core void Sleep(const MM::Device* caller, double intervalMs); // continuous acquisition support - int InsertImage(const MM::Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned byteDepth, const char* serializedMetadata, const bool doProcess = true); - int InsertImage(const MM::Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned byteDepth, unsigned nComponents, const char* serializedMetadata, const bool doProcess = true); + int InsertImage(const MM::Device* caller, const unsigned char* buf, + unsigned width, unsigned height, unsigned bytesPerPixel, + const char* serializedMetadata); + int InsertImage(const MM::Device* caller, const unsigned char* buf, + unsigned width, unsigned height, unsigned bytesPerPixel, unsigned nComponents, + const char* serializedMetadata); bool InitializeImageBuffer(unsigned channels, unsigned slices, unsigned int w, unsigned int h, unsigned int pixDepth); int AcqFinished(const MM::Device* caller, int statusCode); diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index f7ab56a18..cb76c2c36 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -28,7 +28,7 @@ // Header version // If any of the class definitions changes, the interface version // must be incremented -#define DEVICE_INTERFACE_VERSION 74 +#define DEVICE_INTERFACE_VERSION 75 /////////////////////////////////////////////////////////////////////////////// // N.B. @@ -1682,14 +1682,15 @@ namespace MM { * Cameras must call this function during sequence acquisition to send * each frame to the Core. * - * byteDepth: 1 or 2 for grayscale images; 4 for BGR_ + * bytesPerPixel: 1 or 2 for grayscale images; 4 or 8 for BGRx * - * nComponents: 1 for grayscale; 4 for BGR_ (_: unused component) + * nComponents: 1 for grayscale; 4 for BGRx (x: an unused component) * - * serializedMetadata: must be the result of md.serialize().c_str() (md - * being an instance of Metadata) + * (8-byte BGRx may not be supported by the Micro-Manager GUI) * - * doProcess: must be true, except for the case mentioned below + * serializedMetadata: must be the result of md.Serialize() (md + * being an instance of MM::CameraImageMetadata) + * or nullptr (= no tags) * * Legacy note: Previously, cameras were required to perform special * handling when InsertImage() returns DEVICE_BUFFER_OVERFLOW and @@ -1698,7 +1699,9 @@ namespace MM { * cameras should always just stop the acquisition if InsertImage() * returns any error. */ - virtual int InsertImage(const Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned byteDepth, unsigned nComponents, const char* serializedMetadata, const bool doProcess = true) = 0; + virtual int InsertImage(const Device* caller, const unsigned char* buf, + unsigned width, unsigned height, unsigned bytePerPixel, unsigned nComponents, + const char* serializedMetadata) = 0; /** * @brief Send a grayscale frame to the Core during sequence acquisition. @@ -1706,7 +1709,9 @@ namespace MM { * Same as the overload with the added nComponents parameter. * Assumes nComponents == 1 (grayscale). */ - virtual int InsertImage(const Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned byteDepth, const char* serializedMetadata = nullptr, const bool doProcess = true) = 0; + virtual int InsertImage(const Device* caller, const unsigned char* buf, + unsigned width, unsigned height, unsigned bytePerPixel, + const char* serializedMetadata = nullptr) = 0; /** * @brief Prepare the sequence buffer for the given image size and pixel format. From e93660371050dd57ff50bed22a04d6afb557500d Mon Sep 17 00:00:00 2001 From: "Mark A. Tsuchida" Date: Fri, 20 Feb 2026 16:56:02 -0600 Subject: [PATCH 12/14] Add default arg for InsertImage serializedMetadata This change is safe, in the sense that it won't cause any silent change in overload resolution. In the unlikely event that a camera adapter (that we don't control) calls InsertImage(c, b, w, h, bpp, 0), which previously resolved to the single-component overload (0 being null serializedMetadata), it would now get a compiler error ("call is ambiguous"). Such calls would need to remove the 0 or replace it with `nullptr`. --- MMDevice/MMDevice.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index cb76c2c36..84a4a661c 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -1701,7 +1701,7 @@ namespace MM { */ virtual int InsertImage(const Device* caller, const unsigned char* buf, unsigned width, unsigned height, unsigned bytePerPixel, unsigned nComponents, - const char* serializedMetadata) = 0; + const char* serializedMetadata = nullptr) = 0; /** * @brief Send a grayscale frame to the Core during sequence acquisition. From 310dd9507a7f9bac5074d15b5f8937b678b0eb8f Mon Sep 17 00:00:00 2001 From: "Mark A. Tsuchida" Date: Fri, 20 Feb 2026 17:14:02 -0600 Subject: [PATCH 13/14] MMDevice: remove 3 Camera functions These have already been made `final` recently to prevent override. GetPixelSizeUm() - never called from Core, intent unclear GetComponentName() - never called from Core, inconsistent impls PrepareSequenceAcqusition() - inconsistent impls, seldom of value, typo in name --- MMDevice/DeviceBase.h | 15 --------------- MMDevice/MMDevice.h | 13 +------------ 2 files changed, 1 insertion(+), 27 deletions(-) diff --git a/MMDevice/DeviceBase.h b/MMDevice/DeviceBase.h index be7c80203..1eb48cbb0 100644 --- a/MMDevice/DeviceBase.h +++ b/MMDevice/DeviceBase.h @@ -1422,23 +1422,11 @@ class CCameraBase : public CDeviceBase */ virtual int StopSequenceAcquisition() = 0; - // It appears that this function was never used by MMCore and is slated for - // removal. Concrete cameras should not override. - double GetPixelSizeUm() const final { return 0.0; } - virtual unsigned GetNumberOfComponents() const { return 1; // Default to monochrome (ie not RGB) } - // To be removed (never used by MMCore); devices should not override. - virtual int GetComponentName(unsigned channel, char* name) final - { - (void)channel; - CDeviceUtils::CopyLimitedString(name, ""); - return DEVICE_OK; - } - /** * @brief Return the number of channels. * @@ -1494,9 +1482,6 @@ class CCameraBase : public CDeviceBase CDeviceUtils::CopyLimitedString(serializedMetadata, md.Serialize()); } - // To be removed; devices should no longer override. - virtual int PrepareSequenceAcqusition() final {return DEVICE_OK;} - /** * @brief Start sequence acquisition. */ diff --git a/MMDevice/MMDevice.h b/MMDevice/MMDevice.h index f7ab56a18..4804a813c 100644 --- a/MMDevice/MMDevice.h +++ b/MMDevice/MMDevice.h @@ -28,7 +28,7 @@ // Header version // If any of the class definitions changes, the interface version // must be incremented -#define DEVICE_INTERFACE_VERSION 74 +#define DEVICE_INTERFACE_VERSION 75 /////////////////////////////////////////////////////////////////////////////// // N.B. @@ -373,9 +373,6 @@ namespace MM { */ virtual unsigned GetNumberOfComponents() const = 0; - /** Unused; to be removed. */ - virtual int GetComponentName(unsigned component, char* name) = 0; - /** * @brief Return the number of simultaneous channels that camera is capable of. * @@ -422,10 +419,6 @@ namespace MM { * Required by the MM::Camera API. */ virtual unsigned GetBitDepth() const = 0; - /** - * @brief Unused and slated for removal. Implemented in DeviceBase.h. - */ - virtual double GetPixelSizeUm() const = 0; /** * @brief Return the current binning factor. */ @@ -488,10 +481,6 @@ namespace MM { * @brief Stop an ongoing sequence acquisition. */ virtual int StopSequenceAcquisition() = 0; - /** - * @brief Set up the camera so that Sequence acquisition can start without delay. - */ - virtual int PrepareSequenceAcqusition() = 0; /** * @brief Indicate whether sequence acquisition is currently running. * From 8b0a36c87e4562cc097abec7bdc495b448a7ce10 Mon Sep 17 00:00:00 2001 From: "Mark A. Tsuchida" Date: Fri, 20 Feb 2026 17:29:23 -0600 Subject: [PATCH 14/14] Match MMCoreJ POM version to MMCore version --- MMCoreJ_wrap/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MMCoreJ_wrap/pom.xml b/MMCoreJ_wrap/pom.xml index f9f8836f3..3cdddd539 100644 --- a/MMCoreJ_wrap/pom.xml +++ b/MMCoreJ_wrap/pom.xml @@ -6,7 +6,7 @@ org.micro-manager.mmcorej MMCoreJ - 11.13.0 + 11.14.0 MMCore Java API Java bindings for MMCore, the device abstraction layer of Micro-Manager, the microscope control and acquisition platform.