private void StartDaq() { //Insert the range value into the table if (CanSelectRange) { Database.InsertInfoCommand.Parameters.Add(new SQLiteParameter("Resolution", (int)Resolution)); Database.ExecuteCommand(Database.InsertInfoCommand); CanSelectRange = false; } //Begin Daquisition int packetSize = 16; _dataPtr = MccService.ScaledWinBufAllocEx(32); ScanOptions options = ScanOptions.SingleIo | ScanOptions.Continuous | ScanOptions.Background | ScanOptions.ScaleData; if (SamplePeriod > 1000) { options |= ScanOptions.HighResRate; } if (DaqBoard.BoardName == "USB-1608G") { packetSize = 8; } if (DaqBoard.BoardName == "USB-1408FS") { MccService.WinBufFreeEx(_dataPtr); _dataPtr = MccService.WinBufAllocEx(4); packetSize = 2; options = ScanOptions.SingleIo | ScanOptions.Continuous | ScanOptions.Background; } _daqBoard.AInScan(0, numChannels, 2 * packetSize, ref _sampleRate, Resolution, _dataPtr, options); _isReading = true; BeginChartUpdateAsync(); //Set buttons and status label to Running state CanStart = false; CanStop = true; CanBrowse = false; Status = "Running"; StatusBrush = Brushes.LimeGreen; }
public override IObservable <Mat> Generate() { const int PacketSize = 256; return(Observable.Create <Mat>((observer, cancellationToken) => { return Task.Factory.StartNew(() => { var range = Range; var sampleRate = SampleRate; var sampleCount = SampleCount; var lowChannel = LowChannel; var highChannel = HighChannel; var board = new MccBoard(BoardNumber); var channels = highChannel - lowChannel + 1; var dataPoints = sampleCount * channels; var bufferSize = PacketSize * (sampleCount * 2 / PacketSize + 1); var bufferPoints = bufferSize * channels; var buffer = new Mat(bufferSize, channels, Depth.S16, 1); var options = ScanOptions.Continuous | ScanOptions.Background; var dataAvailable = default(EventCallback); using (var waitEvent = new AutoResetEvent(false)) using (var cancellation = cancellationToken.Register(() => waitEvent.Set())) { try { dataAvailable = delegate { waitEvent.Set(); }; var error = board.EnableEvent(EventType.OnDataAvailable, dataPoints, dataAvailable, IntPtr.Zero); ThrowExceptionForErrorInfo(error); var actualRate = sampleRate; error = board.AInScan(lowChannel, highChannel, bufferPoints, ref actualRate, range, buffer.Data, options); ThrowExceptionForErrorInfo(error); if (actualRate != sampleRate) { throw new InvalidOperationException($"The specified sampling rate is not available. Suggested rate: {actualRate}"); } var readIndex = 0; while (!cancellationToken.IsCancellationRequested) { waitEvent.WaitOne(); error = board.GetStatus(out short status, out int count, out int index, FunctionType.AiFunction); ThrowExceptionForErrorInfo(error); if (index < 0) { continue; } index /= channels; var overflowCount = 0; var readCount = index - readIndex; if (readCount < 0) // overflow { overflowCount = bufferSize - readIndex; readCount = index + overflowCount; } while (readCount >= sampleCount) { readCount -= sampleCount; var output = new Mat(channels, sampleCount, buffer.Depth, buffer.Channels); if (overflowCount > 0) { overflowCount -= sampleCount; if (overflowCount < 0) // wrap-around buffer, copy remainder { var overflowSamples = bufferSize - readIndex; using (var outputOverflow = output.GetSubRect(new Rect(0, 0, overflowSamples, channels))) using (var dataOverflow = buffer.GetSubRect(new Rect(0, readIndex, channels, overflowSamples))) { CV.Transpose(dataOverflow, outputOverflow); } readIndex = 0; overflowSamples = sampleCount - overflowSamples; using (var outputOverflow = output.GetSubRect(new Rect(sampleCount - overflowSamples, 0, overflowSamples, channels))) using (var dataOverflow = buffer.GetSubRect(new Rect(0, readIndex, channels, overflowSamples))) { CV.Transpose(dataOverflow, outputOverflow); } observer.OnNext(output); continue; } } using (var data = buffer.GetSubRect(new Rect(0, readIndex, channels, sampleCount))) { CV.Transpose(data, output); } readIndex = (readIndex + sampleCount) % bufferSize; observer.OnNext(output); } } } finally { board.StopBackground(FunctionType.AiFunction); board.DisableEvent(EventType.OnDataAvailable); GC.KeepAlive(dataAvailable); } } }, cancellationToken, TaskCreationOptions.LongRunning, TaskScheduler.Default); })); }