11-13-2015 02:15 PM
I have a non-modal dialog (non-reentrant VI as well so only one instance can run) that just reads a functional global and is displaying some general info to an operator. I use the start async call node to launch this dialog when a button is pressed. The problem is, if the user presses the button again while the dialog is open, it can't launch another instance, which is fine and is what I want. But, it queues the launching of the VI up in the background so as soon as I do close the dialog, another launches.
With the Run VI method, it would throw an error saying the VI is already running, which I can then capture and discard the event. But, then I lose the strict typing of a connector pane because I have to use the set control method. Is there any good way to marry these two functionalities -- or said another way, can I determine if a VI is running already while still using the start async call node and getting the benefit of a strictly typed conn pane?
11-13-2015 02:54 PM
Did you try making a Property Node >> Metrics >> Front Panel Loaded ?
11-13-2015 10:53 PM
Use a FG to remember vi refnum of opened VI(s).
11-14-2015 09:26 AM
11-14-2015 10:22 AM
A useful technique (which may or may not help you) is to have the Async-called VI create a reference an pass it back to the caller. This reference will be destroyed when the VI stops, so one can use it to test if the VI is still running.
11-14-2015 10:29 AM
Another method, somewhat kludgy, is to disable the control after the VI is opened, then reenable after it is closed.
Cheers,
mcduff
11-24-2015 09:42 AM
Did any of these methods do the trick for you, Greg?
11-24-2015 10:04 AM
When I start an asynchronous call like that for a dialogue, I usually create a queue or user event so I can communicate with the dialogue (e.g. if my application shuts down, I want to tell the dialogue to close as well) and pass it into the ACBR node - you can check if the queue / event reference is valid and if it is, then you know the dialogue is open and shouldn't open it again.
11-24-2015 11:57 AM
For what it's worth (I'm late to this thread)
Yet another way to do this...
Right before you try to call the dialog, try to acquire the semaphore with a short timeout (say, 100 ms). If it times out, the dialog is already open.
It may sound like an overly complex solution, but when you encapsulate the semaphore functionality in a class (especially one that is reused) it makes the implementation really straightforward.
Plus, this way you're not reliant on VI server to know whether your dialog is open. In the past I've used this method over and over in applications and never run into a problem.
I hope this helps someone.
11-24-2015 04:10 PM
Seeing Mr_Jim's reply, I'm reminded of some test code I wrote today to play around with Clones, and in doing so, found a way to tell if a Clone is still running (which is, I think, the question here). For this to work, you need to have access to the Clone Reference, and need to call it with Call and Collect (Option 100). Note that you can (and should) use a Strictly-Type Static VI Reference to build the Clone Reference.
The method relies on using the Wait on Async Call function, with a Timeout of 0 (so it doesn't wait) -- if the Clone is still running, it will immediately return Error 123 ("Timed Out"), but if it has finished, it will just return. This works even if you do not need to use Call and Collect, but only want to know "Did that Asynchronous VI finish?" -- this acts as a Test for that.
Thanks for asking this question -- I hadn't realized the utility of this particular function and mode of calling Asyncs before.
Bob Schor