LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Synchronizing DAQ assistant and serial communication

I am trying to synchronize the DAQ assistant to start recording strain values when my serial communication begins and then stop reading values once the serial communication is terminated. I currently have a while loop that includes the DAQ assistant outputting my strain values into a graph. For the serial communication I followed the Basic serial read and write example. I wired the T/F terminal (the one that determines if the program will read the ASCII commands) to my conditional terminal in the while loop using the condition 'Continue if True'. For this condition the DAQ assistant starts reading strain values as soon as my ASCII commands are read but unfortunately I am now in an infinite loop. I then changed the condition of the while loop conditional terminal to 'Stop if True' but with this condition, my DAQ assistant does not read the strain values at all.
 
Is there a way that I can program my while loop to begin recording values when the serial communication is started and then stop reading values when this connection is terminated?
0 Kudos
Message 1 of 14
(5,385 Views)
What determines when serial communication begins or ends?  Is it a button press on the front panel, the turning on of the instrument?  How is the Daq assistant related to your serial communication?  Please post your latest code so we can understand better and suggest ideas.
0 Kudos
Message 2 of 14
(5,379 Views)
To give some background, I am programming a DAQ system that would read strain from a specimen as it is being loaded. I have an actuator that is being controlled by the serial communication and when the actuator starts to move, I would like the DAQ assistant to start reading values. Through the ASCII commands that I write into the program (using the basic serial read and write program), the actuator starts to move.
0 Kudos
Message 3 of 14
(5,374 Views)
You need to put your Serial Write and Read functions in a loop.  That way you can issue a command to start the actuator, and issue a command to stop.  You can use a shift register on that loop to keep track of a boolean to detect whether the actuator is running.
 
Create a run button on your front panel, set its default operation to switch when released.
If the buttons is true, and the boolean is currently false, a true get written to the boolean and the start command gets written to the serial port.
If the button is false, and the boolean is currently true, a false gets written to the boolean and the stop command gets written to the serial port.
All other other cases, button is true and boolean true, or button is false and boolean false, you don't need to do anything.
 
In the upper loop, read a local variable of that run button.  Put your write to measurement file in the True case structure tied to the local variable of that button.
 
Now you have two loops running.  But you need to stop your program.  But a Stop button on your front panel.  Wire it to the stop if true conditional terminal of one loop, and a local variable of it to the conditional terminal of the other loop.  You will have to make this button switch when released also.  You may want to check this button before exiting the loop and make sure the "Stop actuator" serial commands get written before the loop and then the program exits.
0 Kudos
Message 4 of 14
(5,372 Views)
I have added the suggestions that you made but I am not sure if my shift registers and local variables are wired correctly. Also when I start the program it automatically starts to move the actuator, is there a way that the program can wait until I push a button when I want it to move. I thought that having the RUN button wired to the loop that this is what it would do but for some reason it jumps into the program whether I push the run button or not. Is there a way to fix this? I have added my code so that you can see what I am talking about. 
0 Kudos
Message 5 of 14
(5,343 Views)

I don't understand how your code compares to what you want to do?  You have 3 different sets of read and write controls on your front panel, all set to *IDN.  Which of these is supposed to send the start actuator command?  What is your start actuator command?  One set only can execute once, right in the first frame, and that depends on if your have the read and write booleans set before you start the program.  The other two sets occur in the loop associated with your Run button.  But why the boolean Read 4 that toggles the results going between read string 4 and read string 5?

I don't think it is a good idea to take the Read/Write example and extend it in this way.  It looks like all of these sets are associated with the same Com port.  If you send a command in one frame but don't read it because the read switch is not set, then write another command, the buffer is still going to have what was returned after the first write command.

You need to get this down to one communication mechanism per com port.  And get rid of the read/write switches, especially the read since you almost certainly need to read results after every write.  If you need to send different commands, put an enum control on the screen that is attached to a case structure to put out the appropriate string associated with each command.

 

Message Edited by Ravens Fan on 08-29-2007 02:02 PM

0 Kudos
Message 6 of 14
(5,338 Views)
I have my code simplized to using only one com port. I am having a few problems with the serial read and write. For some reason I am only able to communicate with my actuator by using the write command where I have to write in my commands, that is why when you open up my code you only see write controls. When my program opens all write controls only have the *IDN command and I have to manually write in my ASCII commands. I tried to wire a string constant to my serial write but my commands are not being acknowledged by the actuator. The commands are being read but nothing is happening. Is there another way to send individual commands directly to the serial port without me having to write them on the front panel?
 
Also I am unsure of a way that I can tell my program to go into my case structure. Right now I have a select command (under the initialize/default case) but this does not provide me with all the options that I need. I would like to be able to load the properties from the actuator, save the properties, restart the actuator, enable it for movement, then start running it, stop the movement and then disable it all in one go. Is there a way that I can tell my program to do this?
 
I am also not sure if I wired my right shift register correctly? Before, I got an error from Labview telling me I need to index the array to select different elements and with using the index array vi then I never got an error.
 
Do you have any suggestions that might make my code simpler?
0 Kudos
Message 7 of 14
(5,316 Views)
One reason that your commands are not being recognized is that you are not sending the termination character. For the \r to send a carriage return the string constant must be set to '\'Codes Display. Your Enable state sends 4 characters: "E", "N", "\", "r".

Another is that most of the states are never entered. The state machine starts at the LOAD state because the shift register is initialized that way. Typically teh shift register would be initialized to the "Initialize" state. The Load state feeds the default value to the array of state enums, which is probably an empty array. Since the control does not seem to be there, I cannot tell what the default value of coming out of the index array will be.

Every state should feed a value of the next state to the shift register. Do not set the tunnel to Use Default if Unwired for this. You do not need the array.

Except for Initialize, RUN, and QUIT, all the states conatin identical code; only the string to be written differs. These can probably be combined into one with a selector to chose the string.

The while loop in the RUN state will run forever. How do you stop the program?

Lynn
0 Kudos
Message 8 of 14
(5,311 Views)
Is there a better way to synchronize my DAQ assistant and serial read and write? When I run my program it appears that my actuator starts to move before the DAQ assistant start to read the values. Also, if I let my while loop continue too long, I get an error saying "the value that were previously available have since been overwritten". They suggest to increase buffer size, sample for a specific number of values, etc. I am wanting to keep reading samples continuously as I am using that output as a measure to end my serial connection.
0 Kudos
Message 9 of 14
(5,274 Views)
I think you should move your DAQ assistant and write to measurement file to a separate loop that is parallel to your state machine.  Put in in a case that executes whenever your state is a particular value such as Run.  Set the Daq assistant to N samples rather than continuous.  If the loop runs too long, it has collected more samples that it has buffer space for.  So if you collect N samples, then write it out, then go back and collect another N, you'll be fine.
 
It is difficult to tell which state does what.  I would recommend turning your enum of the different states into a TypeDef.  And instead of using numbered cases, use the particular name as defined in the typedef.  This will get rid of the red coercion dots on that shift register and tunnels, and also make it clearer as to which case does what.  I am guessing that the actuator starts moving in an earlier case. (#3 or #4?), and the acquisition doesn't start until state 5.
 
So if you move the data acquisition to a separate loop and have it run only under certain conditions (such as state = run OR state=enable OR ......) (make your state go to an indicator so you can read it as an local variable in the other loop) then the acquisition will run when you want it to.
0 Kudos
Message 10 of 14
(5,268 Views)