Recitation 8: Serial Communication by Karen Zhang

Exercise 1: Make a Processing Etch A Sketch

In this recitation, we finally started to combine what we learned about Arduino and Processing together to make two small projects! Overall, there were two challenges I faced. First, sometimes I forgot how to connect the circuit since we did not practice for a really long time. Second, how to combine the code from Arduino and Processing together. Thanks to the sample code, it saved a lot of work for me to make it run.

I built a circuit with two potentiometers, which were separated connected to pin A0 and A1. With the help of Katie, I corrected some of my mistakes in code. Nevertheless, the track of the ellipse was not so stable that I expected. I tried to switch the direction, it became a little better. 

Sketch: 

Video: 

Code: 

void setup() {

 Serial.begin(9600);

}

void loop() {

 int sensor1 = analogRead(A0);

 int sensor2 = analogRead(A1);

 // keep this format

 Serial.print(sensor1);

 Serial.print(“,”);  // put comma between sensor values

 Serial.print(sensor2);

 Serial.println();

 delay(100);

}

import processing.serial.*;

String myString = null;

Serial myPort;

int NUM_OF_VALUES = 2;   /** YOU MUST CHANGE THIS ACCORDING TO YOUR PROJECT **/

int[] sensorValues;      /** this array stores values from Arduino **/

float x;

float y;

void setup() {

 size(500, 500);

 background(0);

 setupSerial();

}

void draw() {

 updateSerial();

 printArray(sensorValues);

 x = map(sensorValues[0], 0, 1023, 0, width);

 y = map(sensorValues[1], 0, 1023, 0, height);

 noStroke();

 ellipse(x, y, 10, 10);

 // use the values like this!

 // sensorValues[0]

 // add your code

 //

}

void setupSerial() {

 printArray(Serial.list());

 myPort = new Serial(this, Serial.list()[4], 9600);

 myPort.clear();

 // Throw out the first reading,

 // in case we started reading in the middle of a string from the sender.

 myString = myPort.readStringUntil( 10 );  // 10 = ‘\n’ Linefeed in ASCII

 myString = null;

 sensorValues = new int[NUM_OF_VALUES];

}

void updateSerial() {

 while (myPort.available() > 0) {

   myString = myPort.readStringUntil( 10 ); // 10 = ‘\n’  Linefeed in ASCII

   if (myString != null) {

     String[] serialInArray = split(trim(myString), “,”);

     if (serialInArray.length == NUM_OF_VALUES) {

       for (int i=0; i<serialInArray.length; i++) {

         sensorValues[i] = int(serialInArray[i]);

       }

     }

   }

 }

}

Exercise 2: Make a musical instrument with Arduino

In this exercise, first I built a circuit with a buzzer connecting to pin 9 and the ground. I also designed to use the mouse to control the sound of the buzzer.  Thus, the frequency and duration should reflect the position of mouseX and mouseY. So when I moved the “paw” on my screen, the sound of the buzzer also changed. 

Moreover, Eric also reminded me that it is not possible to generate tones lower than 31Hz. So I had to map the frequency to make sure that it sounds right. 

Sketch: 

Video: 

Code: 

#define NUM_OF_VALUES 2    /** YOU MUST CHANGE THIS ACCORDING TO YOUR PROJECT **/

/** DO NOT REMOVE THESE **/

int tempValue = 0;

int valueIndex = 0;

/* This is the array of values storing the data from Processing. */

int values[NUM_OF_VALUES];

void setup() {

 Serial.begin(9600);

 pinMode(13, OUTPUT);

 pinMode(9, OUTPUT);

}

void loop() {

 getSerialData();

 int freq = map(values[0], 0, 500, 31, 500000);

 tone(9, freq, values[1]);

}

//recieve serial data from Processing

void getSerialData() {

 if (Serial.available()) {

   char c = Serial.read();

   //switch – case checks the value of the variable in the switch function

   //in this case, the char c, then runs one of the cases that fit the value of the variable

   //for more information, visit the reference page: https://www.arduino.cc/en/Reference/SwitchCase

   switch (c) {

     //if the char c from Processing is a number between 0 and 9

     case ‘0’…’9′:

       //save the value of char c to tempValue

       //but simultaneously rearrange the existing values saved in tempValue

       //for the digits received through char c to remain coherent

       //if this does not make sense and would like to know more, send an email to me!

       tempValue = tempValue * 10 + c – ‘0’;

       break;

     //if the char c from Processing is a comma

     //indicating that the following values of char c is for the next element in the values array

     case ‘,’:

       values[valueIndex] = tempValue;

       //reset tempValue value

       tempValue = 0;

       //increment valuesIndex by 1

       valueIndex++;

       break;

     //if the char c from Processing is character ‘n’

     //which signals that it is the end of data

     case ‘n’:

       //save the tempValue

       //this will b the last element in the values array

       values[valueIndex] = tempValue;

       //reset tempValue and valueIndex values

       //to clear out the values array for the next round of readings from Processing

       tempValue = 0;

       valueIndex = 0;

       break;

     //if the char c from Processing is character ‘e’

     //it is signalling for the Arduino to send Processing the elements saved in the values array

     //this case is triggered and processed by the echoSerialData function in the Processing sketch

     case ‘e’: // to echo

       for (int i = 0; i < NUM_OF_VALUES; i++) {

         Serial.print(values[i]);

         if (i < NUM_OF_VALUES – 1) {

           Serial.print(‘,’);

         }

         else {

           Serial.println();

         }

       }

       break;

   }

 }

}

import processing.serial.*;

int NUM_OF_VALUES = 2;  /** YOU MUST CHANGE THIS ACCORDING TO YOUR PROJECT **/

Serial myPort;

String myString;

// This is the array of values you might want to send to Arduino.

int values[] = new int[NUM_OF_VALUES];

void setup() {

 size(500, 500);

 background(0);

 printArray(Serial.list());

 myPort = new Serial(this, Serial.list()[ 4 ], 9600);

 myPort.clear();

 // Throw out the first reading,

 // in case we started reading in the middle of a string from the sender.

 myString = myPort.readStringUntil( 10 );  // 10 = ‘\n’ Linefeed in ASCII

 myString = null;

}

void draw() {

 background(255);

 paw(mouseX, mouseY);

 // changes the values

 for (int i=0; i<values.length; i++) {

   values[0] = mouseX;  /** Feel free to change this!! **/

   values[1] = mouseY;  

 }

 // sends the values to Arduino.

 sendSerialData();

 echoSerialData(200);

}

void paw(float x, float y) {

 pushMatrix();

 translate(x, y);

 noStroke();

 fill(30,100);

 ellipse(70, 90, 80, 55);

 ellipse(25, 60, 20, 30);

 ellipse(55, 40, 20, 30);

 ellipse(85, 40, 20, 30);

 ellipse(115, 60, 20, 30);

 popMatrix();

}

void sendSerialData() {

 String data = “”;

 for (int i=0; i<values.length; i++) {

   data += values[i];

   //if i is less than the index number of the last element in the values array

   if (i < values.length-1) {

     data += “,”; // add splitter character “,” between each values element

   }

   //if it is the last element in the values array

   else {

     data += “n”; // add the end of data character “n”

   }

 }

 //write to Arduino

 myPort.write(data);

}

void echoSerialData(int frequency) {

 //write character ‘e’ at the given frequency

 //to request Arduino to send back the values array

 if (frameCount % frequency == 0) myPort.write(‘e’);

 String incomingBytes = “”;

 while (myPort.available() > 0) {

   //add on all the characters received from the Arduino to the incomingBytes string

   incomingBytes += char(myPort.read());

 }

 //print what Arduino sent back to Processing

 print( incomingBytes );

}

Leave a Reply