The attached image is not a finished product, but should give you a good idea of what I want the program to do.
The basic purpose of the program is to control a function generator to do a frequency sweep (yes, the driver/generator has a sweep function available even though I don't use it, I just use labview to do the sweeping instead, is this a bad way of achieving the sweep?)
The program needs to be able to 1) pause at any time so that the user can adjust the amplitude of the signal and 2) it needs to have an output killswitch as well, so that with a button click the amplitude immediately turns off, but will restart from where it was when I hit continue.
To achieve this I have made 2 case structures with buttons and I want your advice/feedback on how I have chosen to program this. Again, the program isn't nearly finished, just trying to figure out how I am going to set it up.
Also, the error handling is not completely set up yet, should I send it through both the pause loop and the killswitch loop as well as the driver up top that sends the device the data?
You expect to pause during a sweep? Your program will make one sweep, then stop. What exactly do you want to do?
You should look into the Producer/Consumer (events) Design Pattern. Using events to detect the button presses is much more efficient than polling loops.
In the consumer set up a state machine where the Pause state passes the amplitude and frequency unchanged and Kill Output state sets the amplitude to zero. If you want to restart fro the same amplitude later, you could keep the previous value in another shift register.
I want the program to pause or shut off the instrument in the middle of the sweep, at the push of a button, which it should be set up to do. The producer/consumer is a good idea to try though, as an event structure may make the code cleaner.
Thanks for the feedback!
So I started playing with an event structure and I am running into a problem (I also took out the actual instrument drivers and replaced them with indicators so that I can test run the program and see what is sent to the device).
In the image, the main "for loop" is excecuted when the run button is clicked at the bottom - this works fine.
The "pause loop" has not been formatted for the event structure yet (I have an issue with the "Kill Output" function that will also be a problem with the pause function, so I will get to that). The pause works pretty well as it is, it will pause the "for loop" until I tell it to continue and it will replace the old amplitude with the new one, but I would like to make it so that the pause is an event. More on that in a second.
The "kill output function" is an event handled by case 1 (case 1 not shown, there isn't much to it anyway, especially without the driver). The problem I am having with this is that it will not excecute until after the for loop has completed, and that is no good. I need it to work just like the pause function shown, to interrupt the for loop and execute the kill output event. Unlike the pause function, it does not have to resume the for loop after excecution. If I can't interrupt the for loop, then I cannot use the event structure and will have to go back to the way it was.
There is another issue with the "pause loop" that I will run into if I make it an event instead of a case structure, and that is the shift registers that go through it (I made the wires thicker to highlight it). If the "pause button" is false, the "amplitude" just gets passed right on through the structure and does not change, but if I press pause then the "new amplitude" is sent to the shift register instead, and I am not sure how to pass data through the event structure like that. Also, upon completion of the "pause" the program needs to resume where it left off in the "for loop" without losing its place... not sure how to do this with the event structure either.
Advice is appreciated, and pictures are wonderful 🙂
Is there even a way to make an event structure pause the excecution of the for loop with the push of a button?
As previosly stated this would be best done using the producer consumer events pattern to drive a queued state machine
Set Output on
Set Output Off
Thanks for the tip but I need a little more guidance on how to set it up.. The producer/consumer (events) has 2 loops, so you are suggesting that I put the main "for loop" that does the sweep in the consumer loop, and to put the pause loop in the producer loop as I did in the attached image?
I have set it up like this but I cannot seem to make it work. I took the "pause loop" and removed the case structure around it, placed it in the producer loop and made an event to handle the "pause value change". I also took the "amplitude" and "new amplitude" controls and pass them through the enqueue element, however the "pause" button does not pause the excecution of the for loop. How do I do this?
Oooooooh, I think I see what you mean. You want me to get rid of the for loop entirely, and handle the sweep itself with a state machine. Have a state that sets up the sweep, and then have a state that pushes the sweep forward. That way the pause button doesn't have to interrupt a for loop and can just interrupt the state machine?
take a look at the shipping example for ideas on how to set up a PC queued state machine.
And if you set up the consumer correctly you won't need a for loop in the consumer the "step" state will simply operate on the last values and go back to step.
I don't have time to whip up an example right now but if you are confussed by any point in the example I will be back to check.