From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.
We appreciate your patience as we improve our online experience.
From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.
We appreciate your patience as we improve our online experience.
07-31-2013 06:31 AM
I'm currently designing a system to measure vibration on N different devices (test stations) at the same time. My plan is to use a master VI that will launch:
1) A GUI to display results of each station's test to the end user
2) A separate VI to control each station
Since each station is similar I would like to write the station control VIs using LVOOP. That way I can define a parent type as a generic station and then define different children for different station types. So far so good?
The main problem I'm having is that the number of stations can be different for each system that we build. I would like to be able to define this during setup by reading a value in a config file. After the program launches, I would like it to automatically launch the VIs used for station control by defining the number of stations (class instances) dynamically. The problem is that since each station will run until a user presses the stop button, I can't just loop through an array to start all of the stations in sequence. In that case I couldn't start the next station until the first station's control VI has closed.
I was thinking that I could use VI Server calls to do this, but I'm not sure exactly how this works with LVOOP. So, does anyone have a suggestion?
07-31-2013 07:58 AM
Since you have a common set of methods operating, Parent classes, you will need to make sure that each VI is reentrant. This will allow the VIs to run independent of each other.
Have a master loop to do a dynamic start of the VIs so they will run independent. Again, make sure all your Vis are reentrant.
07-31-2013 09:23 AM
Joseph,
Thanks for your response. I've attached a simple demonstration of what I would like to do. I set the VIs so that they are reentrant, but as you can see the for loop that indexes through each instance won't continue to start the next instance until the one before it has stopped. You can open any of the object VIs to see that they are not updating their indicators. The loop indicator on the main VI also shows that only the first loop iteration executes until I press the stop button. I've created a few different test cases within the diagram disable structure to show that the program doesn't behave as I want it to in any of the situations. The target behavior would be all instances of the class opening and operating at the same time.
Could you take a look at this and maybe explain what I could do to fix the problem? Thanks.
07-31-2013 09:49 AM
I have not used it, but I think this is one of the reasons the Actor Framework was developed. Here's a link the the Actor Framework Community site.
07-31-2013 11:08 AM
Take a look at Start Asynchronous or Call by Reference. These should invoke a new version of the vi for each call.
07-31-2013 11:54 PM
well i am not sure how to do it in lvoop but here is an idea
open vi ref with option 08 inside a for loop, make the subvi reentrant. number of iteration of for loop will give you the no of instances using with invoke node you can launch as much vis as you need.
08-02-2013 09:04 AM
Here's an updated version of code that seems to solve the problem.
Basically, what I want is to be able to launch N different stations independently when I start the program. If you open the Test Launch Multiple VIs.vi within the project attached and then run the VI as is, you will see exactly what I want to happen. You can toggle showing the sub panels to prove that the VI is working by selecting the "Show Sub Panels" button.
I got this to work with asynchronous VIs. I had to write a wrapper function to allow for dynamic dispatching, but this is fine. The wrapper function takes a static input of the parent class type. Within the wrapper function I choose the actual class instance that will be active. The asynchronous calls are made using a static reference to the wrapper function and with option x80 (call and forget) for obtaining the VI reference.
As an alternative, you can also choose the Case Structure method and run the VI. This method creates a case for each number of stations and then launches the number of VIs that are specified. It isn't elegant, but it will also work if you don't have a huge number of possibilities.
Anyway, thanks for the suggestions. Take a look at this code if you're interested and let me know if you see any potential problems. FYI, I did try building this as an executable and didn't have any problems.
08-02-2013 01:20 PM
I would use the first method and load your specific class as a plugin. That way you can deploy new devices without needing to rebuild your master controller. Simply add the new plug-in (using a packed library) and you now support a new device.
04-10-2018 05:00 PM - edited 04-10-2018 05:00 PM
To add to your answer, I have been doing work with Actor Framework where i have multiple tests running and obtaining data from the same source and a main system controlling all of them. I can create new instances of the test and destroy them as needed. If you want I could explain further. It seemed to me that it was something like this what you needed.
Best Regards