Measurement Studio for VB6

cancel
Showing results for 
Search instead for 
Did you mean: 

DAQmxReadAnalogF64 possible to be non-blocking?

I see that DAQmxReadAnalogF64 is a blocking call. This freezes up my app untill all the samples have been read. Is there any way I can read the daq board and acquire a bunch of samples without freezing up the machine? Right now, a button click doesnt even register until the daq board has been read.....
thanks,
sb
0 Kudos
Message 1 of 17
(13,747 Views)

Hi bonos-

One way to avoid blocking on a DAQmxRead call is to only execute the read operation when necessary.  The best way to do this is to make use of NI-DAQmx Events to monitor the transition of samples to the PC buffer (i.e. the area that is available to DAQmxRead).  The example "C:\Program Files\National Instruments\NI-DAQ\Examples\DAQmx ANSI C\Analog In\Measure Voltage\Cont Acq-Int Clk" shows how to call the DAQmxRead from a seperate callback using NI-DAQmx Events.

Hopefully this helps-

Tom W
National Instruments
0 Kudos
Message 2 of 17
(13,735 Views)
I didn't have too much trouble getting the ANSI C callback example going. That is, after wasting a lot of time trying to get it working on a simulated card, Googling for a clue as to why it didn't work, and then finding out from this forum that the much vaunted impementation of simulated devices doesn't actually support callbacks/events, making it pretty much useless for my purposes. Oh well.
But then I wanted to use the callbacks in my VB6 projects. There don't appear to be any examples provided of doing this with NIDAQmx, I wonder why? It may be possible, but they are certainly making it hard to find out how. I've tried converting from the C examples, I think I have a callback working, but the  thing takes an exception and "I'm sorry, your application failed, would you like to tell Microsoft all about it?". Ok,  I figure that I must need the callback to be synchronous for VB6, that the NIDAQmx  async thread  may be accessing my VB data out of context. But the  type library doesn't contain the Option value for DAQmx_Val_SynchronousEventCallbacks, so I have to get it from the C header, NIDAQmx.h, where it is 1. I try that, but get an error message that "Requested value is not a supported value for this property". Ok, where do I go from here? Has anyone got a working example of a VB6 application using NIDAQmx and callbacks?
I know I shouldn't have naively believed all the promo guff about NIDAQmx being so much better and easier to use that "Traditional NIDAQ". And then figured that I should be able to upgrade several years worth of traditional code, written in VC and VB and including several OCX projects, to the new system in a week. I should have realized that the new stuff is still quite immature and will take time for people to become familiar with it and build up a code base, and that NI really doesn't have an interest in supporting legacy software, or they would have just updated the DAQ ActiveX controls.

Which brings up another question. One of the main ideas behind using ActiveX controls is that they can insulate large and complex applications from changes in underlying hardware. I make extensive use of this. Once an interface is defined, the ActiveX can be changed independently, the user application doesn't even have to be recompiled, so if NI had added the ability to talk to the NIDAQmx drivers to CWAI.ocx and family I would just have to register the new OCX and nothing else would need to be changed. I do this with OCX code I write all the time, adding in new functionality and never having to bother the guys who write the user apps. Why doesn't NI do this? If NIDAQmx is as good as the hype says, surely it should be a trivial matter to upgrade the ActiveX controls to support it?

Thanks for any helpful suggestions or examples,

David

0 Kudos
Message 3 of 17
(13,721 Views)
Hi Tom,
 
I wrote the code with the event , and took it over to the lab where the PCIMIOXE10 is(after stumbling around trying to get it to work with my simulated device and of course finding out  thats futile). In the lab, the event did not fire AT ALL!!!!! The execution never entered that event. Any ideas?
Thanks,
saroj
0 Kudos
Message 4 of 17
(13,715 Views)
I've now got the callback procedure written and working in VB, written an ActiveX control to encapsulate it, and a VB test program to demonstrate the control.
The ActiveX control is similar to the CWAI control (returns data through an AcquiredData event, etc) but much simpler as it is written to replace only the CWAI functionality used in my specific application.

I had a LOT of problems getting multiple channels to work correctly, kept getting buffer overflow when I knew it couldn't be timing, and I've seen others have had the same problem. It turns out that the NIDAQmx API documentation is incorrect in a couple of areas, as follows:



DAQmxCfgSampClkTiming
rate  - The sampling rate in samples per second.

DAQmxRegisterEveryNSamplesEvent
nSamples  - The number of samples after which each event should occur.

Wrong - both these parameters should be in Samples/Channel, NOT in Samples!!
It works fine when you are using only one channel, but once you add extras things don't work right anymore.

David
 
Message 5 of 17
(13,703 Views)
Hi David-
 
Those parameter definitions can be a bit confusing because the wording is sort of ambiguous.  It's implied that since the channels are multiplexed on most DAQ cards that all timing configuration parameters will be in Samples/Second/Channel, but it could be clearer in the function manual.  I'll file a request for that to be reworded- thanks for the feedback.
 
Would you mind posting your event setup and callback code?  There aren't any VB6 examples for DAQmx events out there, so if you have it working I think a lot of users could benefit from taking a look at yours.Smiley Happy
 
Thanks a lot-
Tom W
National Instruments
0 Kudos
Message 6 of 17
(13,702 Views)
Hi Tom,

I've attached my ActiveX control and test-harness program here as an example. The ActiveX detects whether it is on real or simulated hardware, and uses a timer on the simulation so i can run it on systems without real hardware. Note that that this is only an example, not production code, there is lots to be fixed. For example you will note how a static address (from a code module) needs to be passed as the CallBack address. The ActiveX then registers its actual address once it is instantiated. Of course if you create more than one instance of the ActiveX control in an application this simple-minded approach won't work.

To run the demo you will need to create the global  analog input voltage channels Speedmx, ExitGaugeAmx and EntryGaugeAmx, or modify the channel names in the test harness text boxes to something you have.
To open the group in VB, open the .VBG file in the "Tester" directory.
If you want to run without building you need to "regsvr32 CBMXInput.ocx"

I'm now on to struggling with the changes Digital IO with NIDAQmx. Clients still need to see ins, outs and line-direction masks, and the new API doesn't make that a simple translation!

Cheers,

David
0 Kudos
Message 7 of 17
(13,693 Views)
Is it possible to get an event in VB6 from the digital IO driver? I'm not experienced with developing Active X controls. I've used the NI controls in the past, but they don't work with the DAQmx.
 
We are using a USB DIO and when I do a port read, the whole process takes about 80ms! I'm using this to indicate pallet presence using omron optical sensors and I need the time to sample for values under 20 ms at max.  If I could use the events, I could handle them when the sensor is triggered maybe rather than continuously going out and checking the status of each sensor.
 
We've built 3 of these test systems and will be building another 20, each with 16 DIO channels total. I'm considering looking for an easier to use DIO solution. Does anyone have any suggestions regarding VB6 interoperability and a DIO device?
 
Thanks
0 Kudos
Message 8 of 17
(13,629 Views)
Hi tbihn-
 
I assume you are using the USB-6501.  Unfortunately this device will not be compatible with NI-DAQmx events because it features neither hardware-timing nor change detection capabilities.
 
If you would like to execute code based on the change on a digital line, I would suggest that you use a board with change detection capability.  For example, the PCI-6221 features change detection timing as does the PCI-6509 DIO device.  Any device which supports change detection under NI-DAQmx will allow you to execute code in response to a change on a digital line.  With devices that do not support change detection, your best option will be the polling approach you are using currently.
 
How are you polling the DIO?  If you create and destroy a task every time you execute a read then it will definitely be slower.  If you're not already, I would suggest creating one task at the beginning of operation and simply calling the appropriate DAQmxRead function when you need to check the line states.  This should significantly increase your application's performance.
 
Hopefully this helps-
Tom W
National Instruments
0 Kudos
Message 9 of 17
(13,621 Views)
Hi tbihn,

My approach to this would be to build an ActiveX control that creates the DIO task when it is initialized, and then polls the IO using a timer (say 20mS) and raises an even when the inputs change. You can have the current DIO state as a property of the control, so the application can then read the current state at any time. The task can then be cleared when the control is terminated. I have now incorporated the same sort of approach in my control.
The advantage of using an ActiveX control is that you can enhance it, say to automatically make use of NIDAQmx events if it finds hardware that supports it, without needing to rebuild or redistribute your application.
Of course you can do the same thing directly in your application, using a timer to poll the DIO and then running the "event" code, if you are more comfortable doing it that way!

David
0 Kudos
Message 10 of 17
(13,619 Views)