13. Interface and Application Programming



This week I attempted to create a simple application (with GUI) that interfaced with my input device.

Tutorials

I spent time reviewing the basic tutorials on The Coding Train youtube channel and read up on a more specific tutorial on connecting Arduino to Processing.

The tutorials discussed the aspects of going from Arduino to Processing, Processing to Arduino and simultaneously to both (named a 'handshake').

Initially I had some errors when selecting the serial port. I used

 ls /dev/tty.* 
in the terminal line to find out specific name of port for Processing code. On the mac the left port is 1411, the right is 1421, but you enter the serial line as follows,

myPort = new Serial(this, "/dev/tty.usbmodem1421", 9600);

I thought about what interaction I could create with my input board and button. Using the code on How To Mechatronics as a starting point, I created a basic interaction between the arduino and breadboard. Enabling the button (breadboard) to light both the led and alter the colour of a rectangle on screen.

Mouse Click (Arduino)


#include **SoftwareSerial.h**
#define rxPin 0
#define txPin 1
int button = 12;
SoftwareSerial serial(rxPin, txPin);
            

You need to define an integer for the button and include a link to the Software Serial library. A variable is also defined for this, referencing the rx and tx pins.

void setup() 
{
pinMode(rxPin, INPUT);
pinMode(txPin, OUTPUT);
pinMode(button, INPUT);
serial.begin(9600);
}

Defines the Rx and Tx as input and output.


            void loop()
{
  if(serial.available() > 0) {
    char ledState = serial.read();
  }
    serial.println("Hello, world!");
    delay(100);
    //value_B_sensor = digitalRead(pin_B_sensor);
    int buttonState = digitalRead(button);
    if ( buttonState == HIGH){
      serial.println("Button is pressed");
      delay(500);
    }
}
            

Mouse Click (Processing)

import processing.serial.*;


Serial myPort;  // Create object from Serial class
String val;     // Data received from the serial port
int rectX, rectY;      // Position of square button
int rectSize = 90;     // Diameter of rect
color rectColor, baseColor;
color rectHighlight;
color currentColor;
boolean rectOver = false;
String myText="";
            

Defining integers for a squares x/y position, colour and rollover colour.


            void setup()
{
    String portName = Serial.list()[2]; 
  myPort = new Serial(this, "/dev/tty.usbmodem1421", 9600);
  myPort.bufferUntil('n');
            
            

Defining the variable portName as a particular port (2, for the left usb port), before specifying it with Serial (cu.usbserial-FT94TKFS)


  size(640,360,P2D);
  rectColor = color(100,175,55);
  rectHighlight = color(225,50,125);
  baseColor = color(120,150,199);
  currentColor = baseColor;
  rectX = width/2-rectSize-10;
  rectY = height/2-rectSize/2;
  ellipseMode(CENTER); 
            

Defining the GUI: screen dimensions, background/square/rollover colour and shape of square.


        void draw()
{
  update(mouseX, mouseY);
  background(currentColor);
  
  if (mousePressed && (mouseButton == LEFT)) 
  {  // If data is available,
  //myPort.write('1');
  //val = myPort.readStringUntil('\n');         // read it and store it in val
  fill(rectHighlight);
} else {
    fill(rectColor);
  }
  background(102,102,176);
  text(myText, 120, 120);
  myText="";
  println(val); //print it out in the console
  stroke(175);
  rect(rectX, rectY, rectSize, rectSize);
}

Actually drawing the square on the screen. An if statement defining the change of colour on a click of the left (mouse button).

This program worked with the mouse click I needed was to adapt the both sets of code to work with my input, a tilt switch. I new I had to start simple and use the serial monitors first.

Tilt to Serial Monitor (Arduino)

I reviewed the code I had previously used and it appeared the lines referencing mouseX, mouseY and mouseButton needed to be changed to reflect input from my tilt switch board.

 digitalRead(buttonPin) == LOW  

I also needed to define numbers for tilt was rotated, a minimum length of time (could be used to rule out the wind in the final project).

int tiltLength = 0;  int minTime = 100; 

The remaining new code included a while statement to define the tilt duration and an if statement to print the line in the serial monitor (if the minTime was greater than 1 microsecond).



#include **SoftwareSerial.h**
#define rxPin 0
#define txPin 1

SoftwareSerial Serial(rxPin, txPin);

int tiltLength = 0; //the value for how long the tilt switch is rotated 
 
int minTime = 100; //min length of time rotated

int buttonPin = 3; // tilt switch on pin 3

void setup() {
  
  pinMode(rxPin, INPUT); 
  pinMode(txPin, OUTPUT); 
  pinMode(buttonPin, INPUT_PULLUP); //tilt switch input (activates internal resistor)

  Serial.begin(9600); 
}

void loop(){

  while (digitalRead(buttonPin) == LOW ){ 
 
    delay(100);  
    tiltLength = tiltLength + 100;   
}

 if (tiltLength >= minTime){
        
    Serial.println(tiltLength);
    }
  
 tiltLength = 0; //reset tiltDuree each loop 

}

Tilt to Serial Monitor (Processing)

The serial communication can also be reflected in Processing's Debug Window. The key update was to define the serial usb with one line only,

myPort = new Serial(this, "/dev/cu.usbserial-FT94TKFS", 9600)
.

Then in Processing, you can use the following code,

import processing.serial.*;

Serial myPort;   // Create object from Serial class

String val = "in";
int val_aux = 0;

void setup()
{
  myPort = new Serial(this, "/dev/cu.usbserial-FT94TKFS", 9600);
}

void draw() {
    if ( myPort.available() > 0){  // if data is available 
        val = myPort.readStringUntil('\n'); // read my port until \n symbol 
        val = trim(val); // trim the line, removing everything that is not content
        
        if (val == null){ // if there is no value, the value is empty
          val = "GOALLAZIO"; // give this value to not stop the process
        } else { // if not empty
        val_aux = Integer.parseInt(val); // transform char to a integer, a real number
        }
 } 

println(val_aux); // print the value

}
            

This system also used an if statement to give feedback if no input was detected. I had difficulty getting this to work. I uploaded the code in both Arduino IDE and Processing. I then plugged the FTDI cable between my tilt switch board and the left Mac usb port. In Arduino, changed the port to cu.usbserial-FT94TKFS. Opening the serial monitor, input numbers changed as I rotated the board. Note: The first image shows a gradual turn, the second a more direct.

Tilt to GUI (Arduino)

The final step to get my previous basic GUI to work with the tilt switch was to combine aspectes of both sets of code. The while and if statements were updated to reflect contrasting input from the tilt switch, defined as “buttonPin”



#include **SoftwareSerial.h**
#define rxPin 0
#define txPin 1

SoftwareSerial Serial(rxPin, txPin);

int tiltLength = 0; //the value for how long the tilt switch is rotated 
 
int minTime = 100; //min length of time rotated

int buttonPin = 3; // tilt switch on pin 3

void setup() {
  
  pinMode(rxPin, INPUT); 
  pinMode(txPin, OUTPUT); 
  pinMode(buttonPin, INPUT_PULLUP); //tilt switch input (activates internal resistor)

  Serial.begin(9600); 
}

void loop(){

  while (digitalRead(buttonPin) == LOW ){ 
 
    delay(100);  
    tiltLength = tiltLength + 100; 
    Serial.println(tiltLength);  
}

 if (digitalRead(buttonPin) == HIGH ){
    }
  
 tiltLength = 0; //reset tiltDuree each loop 

}

Tilt to GUI (Processing)

Using an two if statements, I was able to update not only the rectangle colour but also the text content when the tilt switch was rotated. The program uses a 'serialEvent' function to update the text. Again, this could be useful for indicating a fault in the triangle (football) game.


import processing.serial.*;
Serial myPort; 
String val = "in";     
String myText="";
int val_tilting = 0;
int rectX, rectY;      
int rectSize = 90;    
color rectColor, baseColor, rectHighlight, currentColor;
            

Above I am importing the serial library reference, declaring an object for the serial port, strings for the text value that will be written in the serial port and changed on screen and also, defining integers for the tilt rotation, rectangle size and X/Y position.

           
            
void setup()
{

  myPort = new Serial(this, "/dev/cu.usbserial-FT94TKFS", 9600);
  myPort.bufferUntil('n');
  size(640,360);
  rectColor = color(100,175,55);
  baseColor = color(100,225,170);
  rectHighlight = color(225,50,125);
  currentColor = baseColor;
  rectX = width/2-rectSize-10;
  rectY = height/2-rectSize/2;
  ellipseMode(CENTER);

}
    
 

The setup function defines the myPort object at the usb port address, sets the pixel size of output screen and various colour RGB settings for the rectangle's normal and highlightes state.

            
void draw(){
  
  if ( myPort.available() > 0){
  val = myPort.readStringUntil('\n');
  val = trim(val);
  fill(rectHighlight);
  myText="Fault";
  delay(2500);
  
  if (val == null){ // if no value
  } else { //if not empty
    val_tilting = Integer.parseInt(val);
  }
}
  println(val_tilting);
  background(currentColor);
  text(myText, 250, 250);
  myText="Game In Progress";
  stroke(175);
  rect(rectX, rectY, rectSize, rectSize);
}

void serialEvent (Serial myPort){
  myText = myPort.readStringUntil('n');
  
}

Within a draw function, two if statements declare that if myPort is available, to read the output and print the value of the tilt, but also to change the tex and rectangle's fill colour from white to pink. The text is also set to change for the duration of the loop, myText="Fault". This is appropriate to the triangle game as the programming would be insticated if one of the buoys was did tilt over.

I attempted to add a reset to the program when returning the tilt switch to an upright position. I followed the thread on this tutorial but failed to get it to work. Instead I added a basic delay of 1000 to the draw function. I changed this later to 2500 to indicate the change more clearly in the video.


Back to the top

Jump to...
Downloads right-click, save as