Example #1
0
    async def acquisition_async(
        self,
        num=np.inf,
        timeout=None,
        raw=False,
        initialising_cams=None,
        raise_on_timeout=True,
    ):
        """Concrete implementation of :meth:`pymanip.video.Camera.acquisition_async` for the Andor camera.

        .. todo::
            add support for initialising_cams
        """

        loop = asyncio.get_event_loop()

        # Make sure no acquisition is running & flush
        if self.CameraAcquiring.getValue():
            self.AcquisitionStop()
        SDK3.Flush(self.handle)
        self.buffer_queued = False

        # Set acquisition mode
        self.CycleMode.setString("Continuous")
        # self.FrameRate.setValue(float(framerate))
        self.MetadataEnable.setValue(True)
        pc_clock = time.time()
        timestamp_clock = self.TimestampClock.getValue()
        timestamp_frequency = self.TimestampClockFrequency.getValue()
        print("ts clock =", timestamp_clock)
        print("ts freq =", timestamp_frequency)

        # Init buffers
        bufSize = self.ImageSizeBytes.getValue()
        buf = np.empty(bufSize, "uint8")
        rbuf, cbuf = self.AOIWidth.getValue(), self.AOIHeight.getValue()
        img = np.empty((rbuf, cbuf), np.uint16)
        xs, ys = img.shape[:2]
        a_s = self.AOIStride.getValue()
        dt = self.PixelEncoding.getString()
        print("Original pixel encoding:", dt)

        # Start acquisition
        self.AcquisitionStart()
        print("Started acquisition at framerate:", self.FrameRate.getValue())
        print("Exposure time is {:.1f} ms".format(self.ExposureTime.getValue() * 1000))
        if timeout is None:
            exposure_ms = self.ExposureTime.getValue() * 1000
            framerate_ms = 1000 / self.FrameRate.getValue()
            timeout_ms = int(max((2 * exposure_ms, 2 * framerate_ms, 1000)))
            timeout = timeout_ms

        try:
            count = 0
            while count < num:
                if not self.buffer_queued:
                    SDK3.QueueBuffer(
                        self.handle,
                        buf.ctypes.data_as(SDK3.POINTER(SDK3.AT_U8)),
                        buf.nbytes,
                    )
                    self.buffer_queued = True
                try:
                    pData, lData = await loop.run_in_executor(
                        None, SDK3.WaitBuffer, self.handle, timeout
                    )
                except Exception:
                    if raise_on_timeout:
                        raise CameraTimeout()
                    else:
                        stop_signal = yield None
                        if stop_signal:
                            break
                        else:
                            continue
                # Convert buffer and yield image
                SDK3.ConvertBuffer(
                    buf.ctypes.data_as(ctypes.POINTER(ctypes.c_uint8)),
                    img.ctypes.data_as(ctypes.POINTER(ctypes.c_uint8)),
                    xs,
                    ys,
                    a_s,
                    dt,
                    "Mono16",
                )
                ticks = parse_metadata(buf)
                ts = (ticks - timestamp_clock) / timestamp_frequency + pc_clock
                # if count == 5:
                #    print('image min max:', np.min(img), np.max(img))
                # if count < 10:
                #    print('FPGA ticks =', ticks)
                #    print('Timestamp =', ts)
                self.buffer_queued = False
                stop_signal = yield MetadataArray(
                    img.reshape((cbuf, rbuf), order="C"),
                    metadata={"counter": count, "timestamp": ts},
                )
                count = count + 1
                if stop_signal:
                    break

        finally:
            self.AcquisitionStop()
        if stop_signal:
            yield True
Example #2
0
    async def acquisition_async(
        self,
        num=np.inf,
        timeout=1000,
        raw=False,
        framerate=None,
        external_trigger=False,
        initialising_cams=None,
        raise_on_timeout=True,
    ):
        """Concrete implementation of :meth:`pymanip.video.Camera.acquisition_async` for the AVT camera.
        """
        self.camera.AcquisitionMode = "Continuous"
        if framerate is not None:
            # Not usable if HighSNRIImages>0, external triggering or
            # IIDCPacketSizeAuto are active
            self.camera.AcquisitionFrameRate = framerate
        if external_trigger:
            self.camera.TriggerMode = "On"
            self.camera.TriggerSource = "InputLines"
        self.frame = self.camera.getFrame()
        self.frame.announceFrame()
        self.camera.startCapture()
        self.camera.runFeatureCommand("AcquisitionStart")
        self.buffer_queued = False
        try:
            count = 0
            while count < num:
                if not self.buffer_queued:
                    self.frame.queueFrameCapture()
                    self.buffer_queued = True
                if (count == 0 and initialising_cams is not None
                        and self in initialising_cams):
                    initialising_cams.remove(self)
                errorCode = await self.frame.waitFrameCapture_async(
                    int(timeout))
                if errorCode == -12:
                    if raise_on_timeout:
                        raise CameraTimeout("cam" + str(self.num) + " timeout")
                    else:
                        stop_signal = yield None
                        if stop_signal:
                            break
                        else:
                            continue
                elif errorCode != 0:
                    raise VimbaException(errorCode)
                if self.frame.pixel_bytes == 1:
                    dt = np.uint8
                elif self.frame.pixel_bytes == 2:
                    dt = np.uint16
                else:
                    raise NotImplementedError
                self.buffer_queued = False
                stop_signal = yield MetadataArray(
                    np.ndarray(
                        buffer=self.frame.getBufferByteData(),
                        dtype=dt,
                        shape=(self.frame.height, self.frame.width),
                    ),
                    metadata={
                        "counter": count,
                        "timestamp": self.frame.timestamp * 1e-7,
                    },
                )
                count += 1
                if stop_signal:
                    break

        finally:
            self.camera.runFeatureCommand("AcquisitionStop")
            self.camera.endCapture()
            self.camera.revokeAllFrames()
        if stop_signal:
            yield True
Example #3
0
    async def acquisition_async(
        self,
        num=np.inf,
        timeout=None,
        raw=False,
        initialising_cams=None,
        raise_on_timeout=True,
    ):
        """
        Multiple image acquisition
        yields a shared memory numpy array valid only
        before generator object cleanup.

        timeout in milliseconds
        """

        loop = asyncio.get_event_loop()

        if timeout is None:
            delay, exposure = self.current_delay_exposure_time()
            timeout = int(max((2000 * exposure, 1000)))

        # Arm camera
        if pf.PCO_GetRecordingState(self.handle):
            pf.PCO_SetRecordingState(self.handle, False)
        pf.PCO_ArmCamera(self.handle)
        warn, err, status = self.health_status()
        if err != 0:
            raise RuntimeError("Camera has error status!")
        XResAct, YResAct, XResMax, YResMax = pf.PCO_GetSizes(self.handle)

        with PCO_Buffer(self.handle, XResAct, YResAct) as buf1, PCO_Buffer(
                self.handle, XResAct, YResAct) as buf2, PCO_Buffer(
                    self.handle, XResAct,
                    YResAct) as buf3, PCO_Buffer(self.handle, XResAct,
                                                 YResAct) as buf4:

            buffers = (buf1, buf2, buf3, buf4)
            try:
                pf.PCO_SetImageParameters(
                    self.handle,
                    XResAct,
                    YResAct,
                    pf.IMAGEPARAMETERS_READ_WHILE_RECORDING,
                )
                pf.PCO_SetRecordingState(self.handle, True)
                for buffer in buffers:
                    pf.PCO_AddBufferEx(self.handle, 0, 0, buffer.bufNr,
                                       XResAct, YResAct, 16)
                count = 0
                buffer_ring = itertools.cycle(buffers)
                while count < num:
                    if (count == 0 and initialising_cams is not None
                            and self in initialising_cams):
                        initialising_cams.remove(self)

                    waitstat = await loop.run_in_executor(
                        None,
                        win32event.WaitForMultipleObjects,
                        [buffer.event_handle for buffer in buffers],
                        0,
                        timeout,
                    )
                    if waitstat == win32event.WAIT_TIMEOUT:
                        if raise_on_timeout:
                            raise CameraTimeout(f"Timeout ({timeout:})")
                        else:
                            stop_signal = yield None
                            if not stop_signal:
                                continue
                            else:
                                break
                    for ii, buffer in zip(range(4), buffer_ring):
                        waitstat = await loop.run_in_executor(
                            None, win32event.WaitForSingleObject,
                            buffer.event_handle, 0)
                        if waitstat == win32event.WAIT_OBJECT_0:
                            win32event.ResetEvent(buffer.event_handle)
                            statusDLL, statusDrv = pf.PCO_GetBufferStatus(
                                self.handle, buffer.bufNr)
                            if statusDrv != 0:
                                raise RuntimeError(
                                    "buffer {:} error status {:}".format(
                                        buffer.bufNr, statusDrv))
                            if raw:
                                data = {"buffer": buffer.bytes()}
                                if self.timestamp_mode:
                                    counter, dt = PCO_get_binary_timestamp(
                                        buffer.bufPtr[:14])
                                    data["counter"] = counter
                                    data["timestamp"] = dt
                                stop_signal = yield data
                            else:
                                if self.metadata_mode:
                                    metadata = pf.PCO_GetMetaData(
                                        self.handle, buffer.bufNr)
                                    stop_signal = yield MetadataArray(
                                        buffer.as_array(), metadata=metadata)
                                elif self.timestamp_mode:
                                    counter, dt = PCO_get_binary_timestamp(
                                        buffer.bufPtr[:14])
                                    stop_signal = yield MetadataArray(
                                        buffer.as_array(),
                                        metadata={
                                            "counter": counter,
                                            "timestamp": dt
                                        },
                                    )
                                else:
                                    stop_signal = yield buffer.as_array()
                            count += 1
                            pf.PCO_AddBufferEx(self.handle, 0, 0, buffer.bufNr,
                                               XResAct, YResAct, 16)
                        else:
                            break
                        if stop_signal:
                            break
                    if stop_signal:
                        break
            finally:
                pf.PCO_SetRecordingState(self.handle, False)
                pf.PCO_CancelImages(self.handle)
        if stop_signal:
            yield True