LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Stopping SubVI with While Loop

Hi -
 
Sorry if this post is repetitive.  I've read all of the solutions that people have detailed regarding global variables, releasing queues, examples such as generate numbers, etc., but can't seem to solve my problem.
 
I've written a main VI (Photoreflectance Final 10) to control a stepper motor and read voltages from a Labjack U12.  It calls a sub VI (LJStreamMerOld) that is adapted from Labjack's simple LJStream1 VI for reading and plotting voltages.  The modifications are mostly so that the sub VIs front panel controls can be controlled by the main VI.
 
I have included the while loop in the main VI so that I can sequentially "initialize," "scan," "reset," and "enable labjack."  I want the STOP button the front panel of the main VI to terminate both the main VI and the sub VI when I am done performing these operations.  From what I understand, the STOP boolean is only read once by the sub VI unless you pass it through as a reference or use a global variable.
 
As it stands right now, if I manually change the global variable (in its front panel) from off to on while both programs are running, I am able to terminate.  I've tried changing the style of the button from the latch options to the switch options, as I understand that these can introduce complications.  In my last attempt to solve the problem, I introduced additional while loops into the sub VI and was able to get the STOP button to function properly...at the cost of being unable to obtain data from the labjack.
 
I'm attaching the library file.  I was unable to save as an earlier version (kept crashing LabVIEW), so hopefully this is OK.  I've tried to include as many of the lower level VIs as possible, but I think it should be clear what I'm trying to do without probing anything other than the main and sub VIs.
 
Thanks in advance for your help!
 
Meredith
0 Kudos
Message 1 of 5
(3,148 Views)
Your fundamental problem is that your subVI has its own loops and once the subVI is called by the main VI, control is passed to it. At that point nothing you do on the main VI's front panel affects the subVI since the main VI is waiting for the subVI to finish, and it never does since the global variable is set by you pressing the "Stop" button on the main VI. But you can't because the main VI isn't listening to you anymore. I did not investigate your code with a fine-tooth comb, but why does the subVI have its own loop? If the subVI is required to have its own loop then you will need to run it in parallel to the main VI. This means launching it dynamically. This will require an architectural change.

A few other comments:
  • Is the main VI supposed to perform all those actions all the time? If so one thing you should change is that you don't want to initialize the serial port during each iteration of the loop. In fact, you're doing it twice during each iteration of the main loop: once with the "Basic Serial Write and Read" and the second time in the last frame.
  • You are completely disregarding any error I/O with the serial port communication.
  • You should consider bundling the inputs to the subVI and creating typedefs of them for better software management.
0 Kudos
Message 2 of 5
(3,131 Views)

Thanks for the response.

The sub VI is required to have its own loop.  So by "running in parallel" and "launching dynamically," I presume you mean transplanting the entire contents of the sub VI into the main VI?  I was worried about doing this as I thought it would complicate things.  But I guess it's the only way to concurrently control the main and sub VIs.  Also, I suppose that would prevent me from having to create typedefs?  Or would that still streamline the passing of values within the main VI?

To address your other comments:

1) I see what you're saying about the serial port initialization.  I think I can put the VISA Configure Serial Port.vi outside of the while loop in the main VI, as it should be initialized everytime the program is run (regardless of what action/s is/are being performed).

2) I can add error I/Os with the serial communcation.  I believe I had started doing it in the third flat sequence box of the main VI (then true, then stacked sequence)...but got sidetracked by functionality issues related to the serial port write.

3) It seemed to be that the way I currently send values to the sub VI was probably clumsy.  I'll look into the typedefs that you mentioned. 

Thanks,

Meredith

0 Kudos
Message 3 of 5
(3,121 Views)
By running in parallel and launching dynamically I did not mean to put the subVI's code into the main VI. I meant that you use the VI Server to launch the subVI from the main VI and control is returned to the main VI. At that point both the main VI and the subVI are running in parallel. Check the VI documentation on the VI Server as well as examples that ship with LabVIEW that show how to do this. Unfortunately, there's no good example that ships with LabVIEW that shows this, but you can take a look at this example.

Note that this is a *possibility*, and not necessarily the best choice for you. Again, I did not look at your code in detail, and so I'm providing a general solution to the general problem that you are encountering. Clearly, you would need to launch the subVI once, and you would need a mechanism to pass the control values into the subVI. You can do this via globals, the VI Server, or queues.

You can accomplish the same thing by placing the subVI on the mainVI's block diagram outside the while loop instead of calling it from inside the while loop. Since the subVI has its own loop it will run in parallel to the main loop's execution.

Message Edited by smercurio_fc on 07-05-2007 02:46 PM

0 Kudos
Message 4 of 5
(3,114 Views)
Another possibility is the Producer/Consumer design pattern which ships with LV. This has the data acquisition in one loop and the user interface in another. The state machine concept may also be helpful for your application.

Lynn
0 Kudos
Message 5 of 5
(3,105 Views)