【问题标题】:Reading in multiple STEM signals into multiple datacubes将多个 STEM 信号读入多个数据立方体
【发布时间】:2020-09-09 14:55:19
【问题描述】:

我编写了一个通过焦点 STEM 采集脚本,它使用 DSAcquire 函数读取图像,其中我使用 DSAcquireData(img, signalindex, etc.) 指定要读取的信号。

上面的好处是我可以在不出现在屏幕上的情况下读取图像,将其复制到数据立方体中,然后获取系列中的下一个,等等。

如果我想使用两个信号而不是一个(例如 HAADF 和 BF),似乎唯一的方法是在设置 digiscan 参数后使用DSStartAcquisition

我应该如何将信号复制到两个预先分配的图像堆栈(stack1stack2)中?最好不要让数十张图片弄乱屏幕(但最好有一些进度衡量标准?)

【问题讨论】:

  • 大概你想要一个连续的采集,或者你要求一个循环的单独调用?
  • 我更喜欢持续获取,但我会在整个过程中改变重点。

标签: dm-script


【解决方案1】:

这样做的一种方法 - 通过迭代 x 个单独的收购是 F1 帮助示例的直接扩展:

// Acquire 2 signals simultaneously, e.g. HAADF and BF detector


number paramID
number width    = 512 // pixel
number height   = 512 // pixel
number rotation = 0   // degree
number pixelTime= 2   // microseconds
number lSynch   = 1   // activated
paramID = DSCreateParameters( width, height, rotation, pixelTime, lSynch )

number signalIndex, dataType, selected, imageID
signalIndex = 0
dataType    = 2 // 2 byte data
selected    = 1 // acquire this signal

image img1 := IntegerImage( "Signal 1", dataType, 0, width, height )
img1.ShowImage()
imageID     = img1.ImageGetID() // use displayed image
DSSetParametersSignal( paramID, signalIndex, dataType, selected, imageID )

signalIndex = 1
dataType    = 2 // 2 byte data
selected    = 1 // acquire this signal

image img2 := IntegerImage( "Signal 1", dataType, 0, width, height )
img2.Showimage()
imageID     = img2.ImageGetID() // use displayed image
DSSetParametersSignal( paramID, signalIndex, dataType, selected, imageID )

number continuous  = 0 // 0 = single frame, 1 = continuous
number synchronous = 1 // 0 = return immediately, 1 = return when finished

// Create stack to copy data to
number nplanes = 10
image stack1 := img1.ImageClone()
stack1.ImageResize(3,width,height,nplanes)
stack1.SetName("Signal 1 (stack)")
stack1.ShowImage()

image stack2 := img2.ImageClone()
stack2.ImageResize(3,width,height,nplanes)
stack2.SetName("Signal 2 (stack)")
stack2.ShowImage()

//Quickly arrange image
EGUPerformActionWithAllShownImages("arrange")

// Iterated acquisition
for( number i=0; i<nPlanes; i++ )
{
    DSStartAcquisition( paramID, continuous, synchronous )
    // Copy data
    stack1.slice2(0,0,i, 0,width,1, 1,height,1) = img1
    stack2.slice2(0,0,i, 0,width,1, 1,height,1) = img2
}
DSDeleteParameters( paramID ) // remove parameters from memory

但是,这将在每一帧重新开始新的 Digiscan 采集。您可能更喜欢通过连续采集和图像侦听器来执行此操作。

为此,您很可能会按照此处 F1 帮助中的说明连接图像侦听器:

Digiscan 采集 - 取决于速度 - 每帧会更新几次图像,因此您需要检查它是否为帧结束。

执行此操作的一种方法是使用 data_value_changed 事件,然后检查图像中的最后一个像素是否已更改值。另一种选择是使用 tags_changed 事件,因为显然采集图像的标签每帧更新一次。不过,这两种选择都有一些潜在的问题。

另请参阅有关此主题的这个非常相关的最新问题:Fastest way to see which pixel has changed when using a listener

【讨论】:

  • 谢谢!我还将阅读有关使用侦听器的内容。使用图像 ID 是我没有想到的!聪明!
  • @TomNorway 您可能还想查看plugins here,尤其是 DigiScan Stack AcquisitionStackBuilder(图像更新).
  • 我现在正试图以连续模式读取,改变焦点并执行图像操作(在图像上运行过滤器并找到它的 max 作为焦点的函数)。在连续模式下运行是否需要线程才能优雅地停止采集?如果没有,如果我想执行提到的焦点更改和图像操作,我还需要线程吗?逻辑说是,但我注意到你没有提到它。
  • @TomNorway 如果您在连续模式下运行,基本上就像您将运行“搜索”视图一样。改变显微镜焦点不会影响扫描(但你会得到中间帧图像对比度的变化,所以很可能是一两帧的垃圾,除非你等待一个新的进入。)运行图像过滤器需要运行在该图像的副本上(在帧完成时拍摄),而不是在用于持续读出的图像上。
  • 线程方面呢?连续模式是否在引擎盖下的自己的线程中运行,这让脚本进展到让我的更改焦点?还是我需要在自己的线程中运行 DSAcquisition?此外,您知道synchrononous=1 在连续读出期间是否同时更新整个帧?这样我就不用担心在最后一个像素上专门触发了。我现在无法检查,因为有人在使用我们的显微镜:p
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-06-28
  • 2021-09-10
  • 2017-06-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-07-18
相关资源
最近更新 更多