We closed this forum 18 June 2010. It has served us well since 2005 as the ALPHA forum did before it from 2002 to 2005. New discussions are ongoing at the new URL http://forum.processing.org. You'll need to sign up and get a new user account. We're sorry about that inconvenience, but we think it's better in the long run. The content on this forum will remain online.
IndexProgramming Questions & HelpElectronics,  Serial Library › Arduino + Processing serial problems
Page Index Toggle Pages: 1
Arduino + Processing serial problems (Read 3996 times)
Arduino + Processing serial problems
Jan 24th, 2010, 4:14am
 
I'm having troubles getting Arduino and Processing to talk to eachother. Summary: after a few parameters are met Arduino sends a "happy" message to Processing, Processing then takes a snapshot with a webcam.

Arduino code
Code:
int dirpin = 2;		// pin 3 is direction pin
int steppin = 12; // pin 12 "starts" motor
int val1 = 0; // val1 will store sensor1 value
int val2 = 0; // val2 will store sensor2 value
int val3 = 0; // val3 will store okbutton value
int val4 = 0; // stores STARTBUTTON count
int SENSOR1 = 4; // input pin for sensor1
int SENSOR2 = 5; // input pin for sensor2
int OKBUTTON = 6; // input pin for ok button
int STARTBUTTON = 3; // on switch
int LED1 = 9; // output pin for led1
int LED2 = 8; // output pin for led2
int LED3 = 7; // output pin for "both" led3
int firstSwitch; // variable for first switch case
int i;
void setup() {

Serial.begin(9600);

pinMode(dirpin, OUTPUT);
pinMode(steppin, OUTPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(SENSOR1, INPUT);
pinMode(SENSOR2, INPUT);
pinMode(OKBUTTON, INPUT);
pinMode(STARTBUTTON, INPUT);
}

void loop() {
Serial.println("absolute\n");
delay(100);
while (val4 == 0) {
val4 = digitalRead(STARTBUTTON); // check start button
int firstSwitch = 1; // set "starting" switch case
Serial.println("Starting Here\n");
delay(100);
}

switch (firstSwitch) {
case 1: // start up procedure
Serial.println("starting - case 1\n");
delay(100);
do {
val1 = digitalRead(SENSOR1);
val2 = digitalRead(SENSOR2);
if (val1 == HIGH) {
digitalWrite(LED1, HIGH);
} else {
digitalWrite(LED1, LOW);
}
if (val2 == HIGH) {
digitalWrite(LED2, HIGH);
} else {
digitalWrite(LED2, LOW);
}
if ((val1 == HIGH) && (val2 == HIGH)) {
digitalWrite(LED3, HIGH);
do {
val3 = digitalRead(OKBUTTON);
} while (val3 == LOW);
}
} while ((val1 == LOW) || (val2 == LOW));
digitalWrite(LED1, LOW);
digitalWrite(LED2, LOW);
digitalWrite(LED3, LOW);
break;
case 2: // bad procedure, add in buzzer
Serial.println("bad - case 2\n");
delay(100);
do {
val1 = digitalRead(SENSOR1);
val2 = digitalRead(SENSOR2);
if (val1 == HIGH) {
digitalWrite(LED1, HIGH);
} else {
digitalWrite(LED1, LOW);
}
if (val2 == HIGH) {
digitalWrite(LED2, HIGH);
} else {
digitalWrite(LED2, LOW);
}
if ((val1 == HIGH) && (val2 == HIGH)) {
digitalWrite(LED3, HIGH);
do {
val3 = digitalRead(OKBUTTON);
} while (val3 == LOW);
}
} while ((val1 == LOW) || (val2 == LOW));
digitalWrite(LED1, LOW);
digitalWrite(LED2, LOW);
digitalWrite(LED3, LOW);
break;
case 3: // good procedure
Serial.println("good - case 3\n");
delay(100);
break;
}

digitalWrite(dirpin, LOW); // Set the direction.
delay(100);

for (i = 0; i<10000; i++) { // 10000 microsteps
digitalWrite(steppin, LOW); // low to high for rising edge
digitalWrite(steppin, HIGH);
delayMicroseconds(200); // close to top speed
}
Serial.println("motor has moved\n");
delay(100);
val1 = digitalRead(SENSOR1);
val2 = digitalRead(SENSOR2);
if ((val1 == HIGH) && (val2 == HIGH)) { // if val1 & val2 are HIGH
Serial.println("sensors good\n");
delay(100);
Serial.print("Take shot\n"); // send "ok" to serial port
delay(100);
firstSwitch = 0; // set firstSwitch to zero
do {
if (Serial.available() > 0) { // if serial is availabe
firstSwitch = Serial.read(); // read serial into firstSwitch
}
} while (firstSwitch == 0); // keep checking if processing has finished
Serial.println(firstSwitch, DEC);
delay(100);
} else {
firstSwitch = 2; // if val1 or val2 are low set firstSwitch to bad
Serial.println("sensors did not line up\n");
delay(100);
}
}


Processing code
Code:
import processing.serial.*;
import processing.video.*;

Serial arduinoPort;
Capture webcam;
int which = 0;

void setup() {
size(640,480);
webcam = new Capture(this,640,480);
String[] devices = Capture.list();
println(devices);
webcam.settings();
arduinoPort = new Serial(this, Serial.list()[0], 9600);
}

void draw() {
while (arduinoPort.available() > 0) {
String inBuffer = arduinoPort.readStringUntil('\n');
if (inBuffer != null) {
String myString = new String(inBuffer);
if (myString.equals("Happy")) {
which = 1;
} else {
which = 2;
}
println(myString);
switch (which) {
case 1:
println("Good");
if (webcam.available() == true) {
webcam.read();
image(webcam ,0,0);
}
saveFrame("line-####.bmp");
arduinoPort.clear();
arduinoPort.write(3);
case 2:
println(myString);
arduinoPort.clear();
arduinoPort.write(2);
}
}
}
}


I pretty much have two problems
1. When I serial.println strings it always shows up multiple times in the Processing serial window, like so...

absolute
Starting Here
Starting Here
starting - case 1
starting - case 1
motor has moved
motor has moved
sensors good
sensors good
Happy
Happy
2
2

I think this happens because Processing checks the serial port multiple times before its updated, I'm not really sure how to fix this though.

2. As you can see in the above serial window post, "Happy" is received by Processing, however it doesn't trigger the webcam to take a snapshot like it should. It just returns a "2" back to the Arduino, which should happen if myString != Happy.

I've tried doing handshake methods and serialEvents() however any tutorials I've found seem to be a bit confusing. Any suggestions would be great!

Thanks

Re: Arduino + Processing serial problems
Reply #1 - Jan 25th, 2010, 2:20am
 
I can try to help with the little coding errors I can see, or at least, what I think might be wrong:

First thing is why it says 'Happy' twice. Simply because you call it twice. First you call println(myString) // outputs "Happy"
Then later you say: case 2: println(myString);

So, you should remove the first call, and then you need to insert a break (actually two breaks) in your switch statement. If you do this, you will only get "Good", which is what you want I suppose. Maybe the rest of the debugging gets easier now? Btw, it does take snapshots as the code works right now ...
Re: Arduino + Processing serial problems
Reply #2 - Jan 25th, 2010, 2:50am
 
Thanks for the reply knutEinar. I suppose you're right about printing twice, I guess I assumed it was never even getting that far into the code and though printing twice was a serial issue.But I guess that was the problem as I removed one of the println and it works fine now.

As for you making it take snapshots. You actually had a camera take snapshots with the Arduino code I submitted? If this is the case, that's quite bizarre because I  haven't been able to with the arduino code. I've been able to accomplish snapshots with a dumbed down Arduino code that simply serial.println("Happy") when a switch is flipped, but never have I with the code I posted. Do you mind sharing your secret? Ha.

Every time I run it the if (myString.equals("Happy")) sends the switch statement to case 2. Even though I'm getting "Happy" through the serial port. Was there anything you did differently at all?

Thanks

Re: Arduino + Processing serial problems
Reply #3 - Jan 25th, 2010, 5:19am
 
Sorry for the confusion, but the snapshots I talked about was from the Processing code. I didn't 'activate' the arduiono code per se, but assuming you will manage to send your byte from arduino to processing (and that should be quite possible), the snapshot function is working as it should. As for the switch statement I am a bit confused of what you try to achieve. But, as I said, did you put in 'break' statements in your switch? If you don't do that, you will always get a return of '2' from your code to arduino (since that is the last thing you ask it to do, and unless you put in 'break' statements, that is what it will continue to do, no matter what else you do). If you actually do get a '2' over to arduino as it is now, you should be quite happy, because that means your serial communication is working, you are just sending it the wrong info Smiley
Re: Arduino + Processing serial problems
Reply #4 - Jan 25th, 2010, 8:39pm
 
Hey knutEinar, this is my new Processing with the break; statements added. However it still isn't quite working correctly. I'm still using the Arduino code I previously posted.

Code:
import processing.serial.*;
import processing.video.*;

Serial arduinoPort;
Capture webcam;
int which = 0;

void setup() {
size(640,480);
webcam = new Capture(this,640,480);
String[] devices = Capture.list();
println(devices);
webcam.settings();
arduinoPort = new Serial(this, Serial.list()[0], 9600);
}

void draw() {
while (arduinoPort.available() > 0) {
String inBuffer = arduinoPort.readStringUntil('\n');
if (inBuffer != null) {
String myString = new String(inBuffer);
if (myString.equals("Happy")) {
which = 1;
} else {
which = 2;
}
switch (which) {
case 1:
println("Good");
if (webcam.available() == true) {
webcam.read();
image(webcam ,0,0);
}
saveFrame("line-####.bmp");
arduinoPort.clear();
arduinoPort.write(3);
break;
case 2:
println(myString);
arduinoPort.clear();
arduinoPort.write(2);
break;
}
}
}
}


Quote:
If you actually do get a '2' over to arduino as it is now, you should be quite happy, because that means your serial communication is working, you are just sending it the wrong info


As a matter of fact I am a bit happy because when it goes to the 'case 2' it does send a '2' back to the Arduino and the Arduino responds to it correctly. Sending a '2' to the Arduino represents anything I'm receiving from the Arduino EXCEPT "Happy." I want a snapshot when Processing receives "Happy."

As you can see from the serial window text below, I am getting "Happy" sent across the serial port. It's just not going to case 1, it always goes to case 2. So for the most part it does work correctly, its just not taking a snapshot whenever "Happy" is sent.

Starting Here
starting - case 1
motor has moved
sensors good
Happy
2

Thanks again for your responses.
Re: Arduino + Processing serial problems
Reply #5 - Jan 26th, 2010, 12:10am
 
Ok, so now you need to break it down to smaller pieces, to make the debugging easier. I'm sure you will get this to work Smiley

Still in the processing code, assuming you have something coming over the serial port. Now, let's try to find out what that something is. Since you keep getting a '2' back in response, and no snapshot is being taken, it is probably not "Happy" you receive.

First you should check what sort of string you actually do receive from Arduino:
Code:
String myString = new String(inBuffer);   
println("myString is: "+myString);
if (myString.equals("Happy")) {

That should tell you whether you get what you expect or not ...
You could also add a couple println inside your cases, like this:
Code:
case 1:
println("case 1");
// more code ...
case 2:
println("case 2");

I see that what I'm saying here is what already know is happening, and you could be right. This is just trying to be really precise about what is going on. I wonder if there could be something with your "Happy" string that needs to be done, like strip out white space or something? If this does not work, have you tried the "readStringUntil()"? Maybe that will work better for you?
Re: Arduino + Processing serial problems
Reply #6 - Jan 26th, 2010, 2:28am
 
Its working!

As soon as I read your suggestion of trim() it hit me that was probably the problem. I was using readStringUntil('\n') and putting line feeds at the end of everything I was sending from the Arduino. Now I can honestly say: I believe everything is working perfectly now. At least working correctly as far as the code goes. Now comes physical integration with the actual motor and sensors.

Thank you again knutEinar, I sincerely appreciate the help. Here's the final Processing code I got it going with. Just had to add in the trim() and modified case 2 a little.

Code:
import processing.serial.*;
import processing.video.*;

Serial arduinoPort;
Capture webcam;
int which = 0;

void setup() {
size(640,480);
webcam = new Capture(this,640,480);
String[] devices = Capture.list();
println(devices);
webcam.settings();
arduinoPort = new Serial(this, Serial.list()[0], 9600);
}

void draw() {
while (arduinoPort.available() > 0) {
String inBuffer = arduinoPort.readStringUntil('\n');
if (inBuffer != null) {
String myString = new String(inBuffer);
String myString2 = trim(myString);
if (myString2.equals("Happy")) {

which = 1;
} else {
which = 2;
}
switch (which) {
case 1:
println("Good");
if (webcam.available() == true) {
webcam.read();
image(webcam ,0,0);
}
saveFrame("line-####.bmp");
arduinoPort.clear();
arduinoPort.write(3);

break;
case 2:
if (myString2.equals("nope")) {
arduinoPort.clear();
arduinoPort.write(2);
}
println(myString2);
break;
}
}
}
}
Re: Arduino + Processing serial problems
Reply #7 - Jan 26th, 2010, 6:37am
 
I'm glad it's working Smiley I believe you could actually get rid of your case statement all together, since you have an if/else above whose only job is to declare a case variable. Instead you could do all the work inside the if/else statement, _or_ you could change your case statement to test for String –or maybe that is not allowed, but in any case, both is not strictly necessary  Smiley Keep me posted Wink
Page Index Toggle Pages: 1