12-12-2018 03:12 AM
Hello--
I have an application where I'm sending a 100Hz pulse to a device and I'd like to measure 27 analog inputs for each cycle of the pulse. My DAQ is an NI-USB 6363 OEM.
I've configured the task to trigger off the counter output (PFI12 in this case), and have the system capturing a finite number of samples for each cycle (1M samples /27 channels @ 100Hz = 370 samples per cycle). Despite this, I seem to be only getting about 22-24 samples for every 100 cycles. I'm not getting any buffer overruns, so I'm not sure where the data is going. Below is my code:
Public Function StartPulse(ByVal CycleParams As CycleParameterType, ByVal SampleRate As Double, ByRef ErrMsg As String) As Boolean
With CycleParams
PressHiTime = .PressureOnTime / 1000
PressLoTime = (.Period - .PressureOnTime) / 1000
VentHiTime = .VentOnTime / 1000
VentLoTime = (.Period - .VentOnTime) / 1000
VentLagTime = (.LagTime) / 1000
SamplesPerSnap = Convert.ToInt32(SampleRate * .Period) / 1000
End With
If AIRunningTask Is Nothing Then
Try
AITask = New Task()
AITask.AIChannels.CreateVoltageChannel("/" & DAQName & AIPort, _
"AnalogInputs", AITerminalConfiguration.Rse, AIMinVoltage, AIMaxVoltage, AIVoltageUnits.Volts)
AITask.Timing.ConfigureSampleClock("", SampleRate, SampleClockActiveEdge.Rising, SampleQuantityMode.FiniteSamples, SamplesPerSnap)
AITask.Triggers.StartTrigger.ConfigureDigitalEdgeTrigger("/" & DAQName & PressurePulseOutputChannel, DigitalEdgeStartTriggerEdge.Rising)
AIReader = New AnalogMultiChannelReader(AITask.Stream)
AIRunningTask = AITask
AIReader.SynchronizeCallbacks = True
AITask.Control(TaskAction.Verify)
'Pressure Signal Generation
PressurePulseTask = New Task()
PressurePulseTask.COChannels.CreatePulseChannelTime("/" & DAQName & PressurePulseCounter, _
"PressureSignal", COPulseTimeUnits.Seconds, COPulseIdleState.Low, _
0, PressLoTime, PressHiTime)
PressurePulseTask.Timing.ConfigureImplicit(SampleQuantityMode.ContinuousSamples)
'Vent Signal Generation
VentPulseTask = New Task()
VentPulseTask.COChannels.CreatePulseChannelTime("/" & DAQName & VentPulseCounter, _
"VentSignal", COPulseTimeUnits.Seconds, COPulseIdleState.Low, _
VentLagTime, VentLoTime, VentHiTime)
VentPulseTask.Triggers.StartTrigger.Type = StartTriggerType.DigitalEdge
VentPulseTask.Triggers.StartTrigger.DigitalEdge.Edge = DigitalEdgeStartTriggerEdge.Rising
VentPulseTask.Triggers.StartTrigger.DigitalEdge.Source = "/" & DAQName & PressurePulseOutputChannel
VentPulseTask.Timing.ConfigureImplicit(SampleQuantityMode.ContinuousSamples)
'Count the Signals
CountPulseTask = New Task()
CountPulseTask.CIChannels.CreateCountEdgesChannel("/" & DAQName & CountPulseCounter, _
"CountPulses", CICountEdgesActiveEdge.Rising, 0, _
CICountEdgesCountDirection.Up)
CountPulseTask.CIChannels.All.CountEdgesTerminal = "/" & DAQName & PressurePulseOutputChannel
CountPulseReader = New CounterSingleChannelReader(CountPulseTask.Stream)
'Start 'em up!
CountPulseTask.Start()
VentPulseTask.Start()
AIReader.BeginReadWaveform(SamplesPerSnap, AIAsyncCallback, AITask)
PressurePulseTask.Start()
Debug.Print(AITask.Timing.SampleClockSource)
Catch ex As Exception
AIRunningTask = Nothing
AITask.Dispose()
StatusCheckTimer.Enabled = False
ErrMsg = ErrMsg & " " & ex.Message
StartPulse = False
Exit Function
End Try
End If
StartPulse = True
End Function
Private Sub AICallback(ByVal ar As IAsyncResult)
Dim ErrMsg As String = ""
Try
If (Not (AIRunningTask Is Nothing)) AndAlso AIRunningTask Is ar.AsyncState Then
' Retrieve data
AIData = AIReader.EndReadWaveform(ar)
'Plot your data here
DataToQueue(AIData)
AIReader.BeginMemoryOptimizedReadWaveform(SamplesPerSnap, AIAsyncCallback, AITask, AIData)
End If
Catch ex As DaqException
DAQError = ex.Message
StopPulse(ErrMsg)
End Try
End Sub
Private Sub DataToQueue(ByVal sourceArray As AnalogWaveform(Of Double)())
Dim i As Byte = 0
Dim tmpstr As String = ""
Dim tmpAIdata(NumChannels - 1, SamplesPerSnap - 1) As Double
Dim dataCount As Integer = sourceArray(i).Samples.Count
For i = 0 To NumChannels - 1
For j As Integer = 0 To (dataCount - 1)
tmpAIdata(i, j) = sourceArray(i).Samples(j).Value
Next
If i = SystemPressureChannel Then
AIPressure = tmpAIdata(i, dataCount - 1)
End If
Next i
AISnap.Add(tmpAIdata)
End Sub
Any thoughts on what the problem is? Do I need to configure the sample clock source?Thanks!!!Sandheep
12-13-2018 10:29 AM
If you execute the code with only one channel are you seeing the same behavior?
12-13-2018 04:08 PM
Dane--
Thanks for the response. I did not try that, but remedied the situation by switching to a solution based on the ContAcqVoltSmpls_EveryNSamplesEvent example.
That seemed to be the only option that did not use Endreadwaveform. Perhaps I don't understand how things work, but it seems to be that if you have an async callback that has an endreadwaveform, data handling code, and beginreadwaveform, then there is a possibility to lose data in between the endread and beginread, right? Or is the data streaming constantly, and endread finishes a "sip" of data, while beginread begins a "sip"?
Please let me know what you think.
Thanks!
Sandheep