Skip to content

Commit ab2fc60

Browse files
authored
Add async property callback to DemoCamera (#160)
* Add async property callback to DemoCamera Allows for more comprehensive testing of downstream libraries. It seems that it was necessary to make a follower and leader property as with only a single property there is a callback fired as soon the action returns, so added a second "Follower" property that is set to the leaders value after a (configurable) delay. * Use data member for async properties Also make follower readonly. * conform to name styling convention * add locks to async leader/follower props * better scoping of thread gaurds * naming convention * use temp variablefor better scoping * better protection against races * remove unneeded lock
1 parent 6a48a3a commit ab2fc60

File tree

2 files changed

+56
-1
lines changed

2 files changed

+56
-1
lines changed

DeviceAdapters/DemoCamera/DemoCamera.cpp

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
#include <algorithm>
3232
#include "WriteCompactTiffRGB.h"
3333
#include <iostream>
34+
#include <future>
3435

3536

3637

@@ -396,6 +397,17 @@ int CDemoCamera::Initialize()
396397
}
397398
}
398399

400+
// Test Property with an async callback
401+
// When the leader is set the follower will be set to the same value
402+
// with some delay (default 2 seconds).
403+
// This is to allow downstream testing of callbacks originating from
404+
// device threads.
405+
pAct = new CPropertyAction (this, &CDemoCamera::OnAsyncLeader);
406+
CreateStringProperty("AsyncPropertyLeader", "init", false, pAct);
407+
pAct = new CPropertyAction (this, &CDemoCamera::OnAsyncFollower);
408+
CreateStringProperty("AsyncPropertyFollower", "init", true, pAct);
409+
CreateIntegerProperty("AsyncPropertyDelayMS", 2000, false);
410+
399411
//pAct = new CPropertyAction(this, &CDemoCamera::OnSwitch);
400412
//nRet = CreateIntegerProperty("Switch", 0, false, pAct);
401413
//SetPropertyLimits("Switch", 8, 1004);
@@ -1289,6 +1301,41 @@ int CDemoCamera::OnTestProperty(MM::PropertyBase* pProp, MM::ActionType eAct, lo
12891301

12901302
}
12911303

1304+
void CDemoCamera::SlowPropUpdate(std::string leaderValue)
1305+
{
1306+
// wait in order to simulate a device doing something slowly
1307+
// in a thread
1308+
long delay; GetProperty("AsyncPropertyDelayMS", delay);
1309+
CDeviceUtils::SleepMs(delay);
1310+
{
1311+
MMThreadGuard g(asyncFollowerLock_);
1312+
asyncFollower_ = leaderValue;
1313+
}
1314+
OnPropertyChanged("AsyncPropertyFollower", leaderValue.c_str());
1315+
}
1316+
1317+
int CDemoCamera::OnAsyncFollower(MM::PropertyBase* pProp, MM::ActionType eAct)
1318+
{
1319+
if (eAct == MM::BeforeGet){
1320+
MMThreadGuard g(asyncFollowerLock_);
1321+
pProp->Set(asyncFollower_.c_str());
1322+
}
1323+
// no AfterSet as this is a readonly property
1324+
return DEVICE_OK;
1325+
}
1326+
1327+
int CDemoCamera::OnAsyncLeader(MM::PropertyBase* pProp, MM::ActionType eAct)
1328+
{
1329+
if (eAct == MM::BeforeGet){
1330+
pProp->Set(asyncLeader_.c_str());
1331+
}
1332+
if (eAct == MM::AfterSet)
1333+
{
1334+
pProp->Get(asyncLeader_);
1335+
fut_ = std::async(std::launch::async, &CDemoCamera::SlowPropUpdate, this, asyncLeader_);
1336+
}
1337+
return DEVICE_OK;
1338+
}
12921339

12931340
/**
12941341
* Handles "Binning" property.

DeviceAdapters/DemoCamera/DemoCamera.h

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737
#include <map>
3838
#include <algorithm>
3939
#include <stdint.h>
40+
#include <future>
4041

4142
//////////////////////////////////////////////////////////////////////////////
4243
// Error codes
@@ -174,7 +175,10 @@ class CDemoCamera : public CCameraBase<CDemoCamera>
174175
// action interface
175176
// ----------------
176177
int OnMaxExposure(MM::PropertyBase* pProp, MM::ActionType eAct);
177-
int OnTestProperty(MM::PropertyBase* pProp, MM::ActionType eAct, long);
178+
int OnTestProperty(MM::PropertyBase* pProp, MM::ActionType eAct, long);
179+
int OnAsyncFollower(MM::PropertyBase* pProp, MM::ActionType eAct);
180+
int OnAsyncLeader(MM::PropertyBase* pProp, MM::ActionType eAct);
181+
void SlowPropUpdate(std::string leaderValue);
178182
int OnBinning(MM::PropertyBase* pProp, MM::ActionType eAct);
179183
int OnPixelType(MM::PropertyBase* pProp, MM::ActionType eAct);
180184
int OnBitDepth(MM::PropertyBase* pProp, MM::ActionType eAct);
@@ -265,10 +269,14 @@ class CDemoCamera : public CCameraBase<CDemoCamera>
265269
std::vector<unsigned> multiROIHeights_;
266270

267271
double testProperty_[10];
272+
std::string asyncLeader_;
273+
std::string asyncFollower_;
268274
MMThreadLock imgPixelsLock_;
275+
MMThreadLock asyncFollowerLock_;
269276
friend class MySequenceThread;
270277
int nComponents_;
271278
MySequenceThread * thd_;
279+
std::future<void> fut_;
272280
int mode_;
273281
ImgManipulator* imgManpl_;
274282
double pcf_;

0 commit comments

Comments
 (0)