Showing posts with label Code example. Show all posts
Showing posts with label Code example. Show all posts

Wednesday, March 16, 2022

Get user input from Serial Monitor

 To get user input from Serial Monitor:

void setup() {
  Serial.begin(9600);

}

void loop() {
  if (Serial.available() > 0){
    String stringIn = Serial.readString();
    stringIn.toUpperCase();
    Serial.println(stringIn);
  }
}


Monday, August 24, 2020

millis() overflow? BlinkWithoutDelay question?

 Normal if we want to run some code in fixed interval, we will use the following pattern:

void loop() {
	// check if the fixed interval reached
	unsigned long currentMillis = millis();
	if (currentMillis - previousMillis >= interval) {
		//do something in fixed interval
		//...
		
		
	}
}

It's a general practice as show in Arduino BlinkWithoutDelay example.

Where millis() returns the number of milliseconds passed since the Arduino board began running the current program. This number will overflow (go back to zero), after approximately 50 days.

So, what will happen if it overflow? Will it be a bug in the statement (currentMillis - previousMillis >= interval)?
The answer is NO.

Lets try the following example, run on Uno.
void setup() {
  Serial.begin(9600);
  while (!Serial) {
  }     // wait for serial port to connect.

  unsigned long i =0;
  unsigned long j = i-1;
  unsigned long k = j+1000;
  
  Serial.print("i = ");
  Serial.println(i);
  Serial.print("j = ");
  Serial.println(j);
  Serial.print("k = ");
  Serial.println(k);

  Serial.print("(k > j) : ");
  Serial.println((k > j) ? "true" : "false");

  Serial.print("k-j : ");
  Serial.println(k-j);
  
  Serial.print("((k-j) >= 1000) : ");
  Serial.println(((k-j) >= 1000) ? "true" : "false");
   
}

void loop() {
  // put your main code here, to run repeatedly:

}

Friday, June 16, 2017

Python run on Raspberry Pi (and PC running Ubuntu) to plot serial data from ESP8266/NodeMCU

Last post show a simple program run on ESP8266/NodeMCU to read Analog Input and send to Serial. And display the data on Raspberry Pi 3 using Arduino IDE Serial Plotted. This post show a Python example run on Raspberry Pi 3/Raspbian Jessie with PIXEL, to plot the serial data graphically using matplotlib library.



pyserialplot.py
import numpy as np
import matplotlib as mpl
import matplotlib.pyplot as plt
import matplotlib.animation as animation
import serial
import platform

print("Python version: " + platform.python_version())
print("matplotlib version: " + mpl.__version__)

fig, ax = plt.subplots()
line, = ax.plot(np.random.rand(10))
ax.set_ylim(0, 1030)
xdata, ydata = [0]*100, [0]*100
SerialIn = serial.Serial("/dev/ttyUSB0",9600)

def update(data):
    line.set_ydata(data)
    return line,

def run(data):
    global xdata, ydata
    x,y = data
    if (x == 0):
        xdata = [0]*100
        ydata = [0]*100
    del xdata[0]
    del ydata[0]
    xdata.append(x)
    ydata.append(y)
    line.set_data(xdata, ydata)
    return line,

def data_gen():
    x = 9
    while True:
        if (x >= 9):
            x = 0
        else:
            x += 0.1
            
        try:
            inRaw = SerialIn.readline()
            inInt = int(inRaw)
        except:
            inInt = 0
            
        yield x, inInt

ani = animation.FuncAnimation(fig, run, data_gen, interval=0, blit=True)
plt.show()


This python example can be run on both Python 2 and 3. To run this on Raspberry Pi/Raspbian Jessie with PIXEL, matplotlib library is need.

For Python 2:
$ sudo apt-get install python-matplotlib

For Python 3:
$ sudo apt-get install python3-matplotlib

In the following code, we have to get the port connected.
SerialIn = serial.Serial("/dev/ttyUSB0",9600)

In Raspberry Pi/Raspbian Jessie with PIXEL, it is /dev/ttyUSB0 normal. We can check it with:
$ ls /dev/ttyUSB0*




Run on Ubuntu:

The Python script work on PC/Ubuntu also. This video show running on Ubuntu 17.04/Payton 3.6 (actually behind Windows 10/VirtualBox).


In order to run with newest Python 3.6 on Ubuntu 17.04, you have to install Python 3.6 and corresponding IDLE and pip.

And install packages using command:
$ sudo python3.6 -m pip install numpy
$ sudo python3.6 -m pip install matplotlib
$ sudo python3.6 -m pip install pyserial


About Saving graph of matplotlib:

Suppose I can click the Save button on matplotlib navigation toolbar to save the graph to file (reference: matplotlib - Interactive navigation).

But when I test it on Raspberry Pi with matplotlib 1.4.2, it is not work.

When test it on PC running Ubuntu 17.04/Python 3.6 with matplotlib 2.0.2, I can save the graph. But the navigation toolbar disappear after saved.



Thursday, June 15, 2017

ESP8266/NodeMCU read Analog Input and send to Raspberry Pi via Serial/USB

This example of ESP8266/NodeMCU read input from A0, and output to Serial. The receiving side is a Raspberry Pi 3 running Raspbian Jessie with PIXEL and Arduino IDE installed, the result is display graphically using Arduino IDE's Serial Plotter. All job done on Raspberry Pi 3. ESP8266/NodeMCU connect to the Raspberry Pi 3 with USB.


To run the whole in Raspberry Pi, you have to:
- Install Arduino IDE on Raspberry Pi/Raspbian Jessie with PIXEL
Add Arduino core for ESP8266 to Arduino IDE

The simple program run on ESP8266/NodeMCU, ESP8266_AnalogIn_SerialOut.ino. (Suppose it work on other Arduino also, such as Uno.)
const int analogIn = A0;
int analogVal = 0;
bool led = 1;

void setup() {
  Serial.begin(9600);
  pinMode(LED_BUILTIN, OUTPUT);
}

void loop() {

  digitalWrite(LED_BUILTIN, led);
  led = !led; 
  analogVal = analogRead(analogIn);
  Serial.println(analogVal);
  delay(500);
}

Next:
A Python example run on Raspberry Pi 3/Raspbian Jessie with PIXEL, to plot the serial data graphically using matplotlib library.

Friday, April 3, 2015

Find usb device of specified idVendor and idProduct in Python with PyUSB.

This simple example show how to find the USB device with specified idVendor and idProduct in Python with PyUSB, and print it's details.


- To install PyUSB, refer to the post "Download and Install PyUSB for Python 2 and 3".

- To know the Vendor ID and Product ID of your device, refer the post "Get idVendor and idProduct of your Arduino/USB devices".

- Enter the code, replace with your idVendor and idProduct. It run on both Python 2 and 3.

import usb.core
import usb.util

# find Arduino Uno
dev = usb.core.find(idVendor=0x2341, idProduct=0x0043)

# was it found?
if dev is None:
    raise ValueError('Device not found')

print(repr(dev))
print('VendorID  = 0x%04x'%dev.idVendor)
print('ProductID = 0x%04x'%dev.idProduct)
print
print(dev)


Example output of Arduino Uno rev 3, with idVendor=2341, idProduct=0043
<DEVICE ID 2341:0043 on Bus 002 Address 010>
VendorID  = 0x2341
ProductID = 0x0043
DEVICE ID 2341:0043 on Bus 002 Address 010 =================
 bLength                :   0x12 (18 bytes)
 bDescriptorType        :    0x1 Device
 bcdUSB                 :  0x110 USB 1.1
 bDeviceClass           :    0x2 Communications Device
 bDeviceSubClass        :    0x0
 bDeviceProtocol        :    0x0
 bMaxPacketSize0        :    0x8 (8 bytes)
 idVendor               : 0x2341
 idProduct              : 0x0043
 bcdDevice              :    0x1 Device 0.01
 iManufacturer          :    0x1 Error Accessing String
 iProduct               :    0x2 Error Accessing String
 iSerialNumber          :   0xdc Error Accessing String
 bNumConfigurations     :    0x1
  CONFIGURATION 1: 100 mA ==================================
   bLength              :    0x9 (9 bytes)
   bDescriptorType      :    0x2 Configuration
   wTotalLength         :   0x3e (62 bytes)
   bNumInterfaces       :    0x2
   bConfigurationValue  :    0x1
   iConfiguration       :    0x0 
   bmAttributes         :   0xc0 Self Powered
   bMaxPower            :   0x32 (100 mA)
    INTERFACE 0: CDC Communication =========================
     bLength            :    0x9 (9 bytes)
     bDescriptorType    :    0x4 Interface
     bInterfaceNumber   :    0x0
     bAlternateSetting  :    0x0
     bNumEndpoints      :    0x1
     bInterfaceClass    :    0x2 CDC Communication
     bInterfaceSubClass :    0x2
     bInterfaceProtocol :    0x1
     iInterface         :    0x0 
      ENDPOINT 0x82: Interrupt IN ==========================
       bLength          :    0x7 (7 bytes)
       bDescriptorType  :    0x5 Endpoint
       bEndpointAddress :   0x82 IN
       bmAttributes     :    0x3 Interrupt
       wMaxPacketSize   :    0x8 (8 bytes)
       bInterval        :   0xff
    INTERFACE 1: CDC Data ==================================
     bLength            :    0x9 (9 bytes)
     bDescriptorType    :    0x4 Interface
     bInterfaceNumber   :    0x1
     bAlternateSetting  :    0x0
     bNumEndpoints      :    0x2
     bInterfaceClass    :    0xa CDC Data
     bInterfaceSubClass :    0x0
     bInterfaceProtocol :    0x0
     iInterface         :    0x0 
      ENDPOINT 0x4: Bulk OUT ===============================
       bLength          :    0x7 (7 bytes)
       bDescriptorType  :    0x5 Endpoint
       bEndpointAddress :    0x4 OUT
       bmAttributes     :    0x2 Bulk
       wMaxPacketSize   :   0x40 (64 bytes)
       bInterval        :    0x1
      ENDPOINT 0x83: Bulk IN ===============================
       bLength          :    0x7 (7 bytes)
       bDescriptorType  :    0x5 Endpoint
       bEndpointAddress :   0x83 IN
       bmAttributes     :    0x2 Bulk
       wMaxPacketSize   :   0x40 (64 bytes)
       bInterval        :    0x1

Tuesday, September 9, 2014

Arduino Uno: scan LED Matrix in Timer Interrupt

The original tutorial "Row-columm Scanning to control an 8x8 LED Matrix" call refreshScreen() to draw the screen repeatly in main loop(). If anything in loop() have to do something for times, will block the program, and make the duty cycle (and the brightness) will become unstable. This example show how to scan LED Matrix in Timer Interrupt ISR, such that it will not be affect by the jobs in loop(). But the timing of Timer Interrupt will affect the performance. This video show how:



// 2-dimensional array of row pin numbers:
const int row[8] = {
  2, 7, 19, 5, 13, 18, 12, 16
};

// 2-dimensional array of column pin numbers:
const int col[8] = {
  6, 11, 10, 3, 17, 4, 8, 9
};

// 2-dimensional array of pixels:
int pixels[8][8];

int posX = 7;
int posY = 7;
int count = 30;
bool bg = false;

unsigned int timer1_counter;
int scanningRow = 0;

void setup() {
  Serial.begin(9600);
  
  // initialize the I/O pins as outputs
  // iterate over the pins:
  for (int thisPin = 0; thisPin < 8; thisPin++) {
    // initialize the output pins:
    pinMode(col[thisPin], OUTPUT);
    pinMode(row[thisPin], OUTPUT);
    // take the col pins (i.e. the cathodes) high to ensure that
    // the LEDS are off:
    digitalWrite(col[thisPin], HIGH);
  }

  // initialize timer1 
  noInterrupts();           // disable all interrupts
  TCCR1A = 0;
  TCCR1B = 0;

  //timer1_counter for 1 sec, with prescaler=256
  //65536 - 16000000/256
  //timer1_counter = 3036;
  //timer1_counter for 0.5 sec, with prescaler=256
  //65536 - 16000000/(256*2)
  //timer1_counter = 34286;
  //timer1_counter for 0.1 sec, with prescaler=256
  //65536 - 16000000/(256*10)
  //timer1_counter = 59286;
  //timer1_counter for 0.001 sec, with prescaler=256
  //65536 - 16000000/(256*100)
  //timer1_counter = 64911;
  //timer1_counter for 0.0002 sec, with prescaler=256
  //65536 - 16000000/(256*500)
  timer1_counter = 65411;
  
  TCNT1 = timer1_counter;   // preload timer
  TCCR1B |= (1 << CS12);    // 256 prescaler 
  TIMSK1 |= (1 << TOIE1);   // enable timer overflow interrupt
  interrupts();             // enable all interrupts
  
  //init pixels
  for (int x = 0; x < 4; x++) {
    for (int y = 0; y < 8; y++) {
      pixels[x][y] = HIGH;
    }
  }
  for (int x = 4; x < 8; x++) {
    for (int y = 0; y < 8; y++) {
      pixels[x][y] = LOW;
    }
  }
  
  pixels[1][3] = LOW;

}

ISR(TIMER1_OVF_vect)        // interrupt service routine 
{
  TCNT1 = timer1_counter;   // preload timer

  
  //scan LED Matrix in ISR
  digitalWrite(row[scanningRow], LOW);

  if(++scanningRow>=8){
    scanningRow = 0;
  }

  for (int thisCol = 0; thisCol < 8; thisCol++) {
    int thisPixel = pixels[scanningRow][thisCol];
    digitalWrite(col[thisCol], thisPixel);
  }
  digitalWrite(row[scanningRow], HIGH);
  
}

void loop() {
  //refreshScreen();
  
  //Do something, block the loop
  Serial.println("Hello!");
  //Serial.println("Hello! again");

}

void refreshScreen() {
  // iterate over the rows (anodes):
  for (int thisRow = 0; thisRow < 8; thisRow++) {
    // take the row pin (anode) high:
    digitalWrite(row[thisRow], HIGH);
    // iterate over the cols (cathodes):
    for (int thisCol = 0; thisCol < 8; thisCol++) {
      // get the state of the current pixel;
      int thisPixel = pixels[thisRow][thisCol];
      // when the row is HIGH and the col is LOW,
      // the LED where they meet turns on:
      digitalWrite(col[thisCol], thisPixel);
      // turn the pixel off:
      if (thisPixel == LOW) {
        digitalWrite(col[thisCol], HIGH);
      }
    }
    // take the row pin low to turn off the whole row:
    digitalWrite(row[thisRow], LOW);
  }
}

Monday, September 8, 2014

Using Timer Interrupt of Arduino Uno

Example to use Timer Interrupt of Arduino Uno.


WalkingLedMatrix.ino
// 2-dimensional array of row pin numbers:
const int row[8] = {
  2, 7, 19, 5, 13, 18, 12, 16
};

// 2-dimensional array of column pin numbers:
const int col[8] = {
  6, 11, 10, 3, 17, 4, 8, 9
};

// 2-dimensional array of pixels:
int pixels[8][8];

int posX = 7;
int posY = 7;
int count = 30;
bool bg = false;

volatile unsigned long lasttime;
volatile unsigned long now;

int timer1_counter;

void setup() {
  Serial.begin(9600);
  
  // initialize the I/O pins as outputs
  // iterate over the pins:
  for (int thisPin = 0; thisPin < 8; thisPin++) {
    // initialize the output pins:
    pinMode(col[thisPin], OUTPUT);
    pinMode(row[thisPin], OUTPUT);
    // take the col pins (i.e. the cathodes) high to ensure that
    // the LEDS are off:
    digitalWrite(col[thisPin], HIGH);
  }

  setupScreen();
  
  // initialize timer1 
  noInterrupts();           // disable all interrupts
  TCCR1A = 0;
  TCCR1B = 0;

  //timer1_counter for 1 sec, with prescaler=256
  //65536 - 16000000/256
  //timer1_counter = 3036;
  //timer1_counter for 0.5 sec, with prescaler=256
  //65536 - 16000000/(256*2)
  //timer1_counter = 34286;
  //timer1_counter for 0.1 sec, with prescaler=256
  //65536 - 16000000/(256*10)
  timer1_counter = 59286;
  
  
  TCNT1 = timer1_counter;   // preload timer
  TCCR1B |= (1 << CS12);    // 256 prescaler 
  TIMSK1 |= (1 << TOIE1);   // enable timer overflow interrupt
  interrupts();             // enable all interrupts
  
  lasttime = millis();

}

ISR(TIMER1_OVF_vect)        // interrupt service routine 
{
  TCNT1 = timer1_counter;   // preload timer

  if(posX--==0){
    posX = 7;
    if(posY--==0){
      posY = 7;
      bg = !bg;
    }
  }
  setupScreen();
  
  now = millis();
  Serial.println(now - lasttime);
  lasttime = now;
}

void loop() {
  refreshScreen();
}

void setupScreen(){
  if(bg){
    //ON all others
    for (int x = 0; x < 8; x++) {
      for (int y = 0; y < 8; y++) {
        pixels[x][y] = LOW;
      }
    }
    
    //OFF current pos
    pixels[posX][posY] = HIGH;
  }else{
    //OFF all others
    for (int x = 0; x < 8; x++) {
      for (int y = 0; y < 8; y++) {
        pixels[x][y] = HIGH;
      }
    }
    
    //ON current pos
    pixels[posX][posY] = LOW;
  }
}

void refreshScreen() {
  // iterate over the rows (anodes):
  for (int thisRow = 0; thisRow < 8; thisRow++) {
    // take the row pin (anode) high:
    digitalWrite(row[thisRow], HIGH);
    // iterate over the cols (cathodes):
    for (int thisCol = 0; thisCol < 8; thisCol++) {
      // get the state of the current pixel;
      int thisPixel = pixels[thisRow][thisCol];
      // when the row is HIGH and the col is LOW,
      // the LED where they meet turns on:
      digitalWrite(col[thisCol], thisPixel);
      // turn the pixel off:
      if (thisPixel == LOW) {
        digitalWrite(col[thisCol], HIGH);
      }
    }
    // take the row pin low to turn off the whole row:
    digitalWrite(row[thisRow], LOW);
  }
}

Thursday, April 10, 2014

Arduino Esplora example: read bmp from SD Card, display on TFT screen

Example of Arduino Esplora, read bmp from AD Card, and display on TFT screen.

#include <Esplora.h>
#include <SPI.h>
#include <SD.h>
#include <TFT.h>

// SD Chip Select pin
#define SD_CS    8

// this variable represents the image to be drawn on screen
PImage image;
int prvSwitch1, prvSwitch2, prvSwitch3, prvSwitch4;

void setup() {
  Esplora.writeRGB(255, 255, 255);
  
  EsploraTFT.begin();
  EsploraTFT.background(0, 0, 0);
  EsploraTFT.stroke(255,255,255);
  
  // initialize the serial port
  Serial.begin(9600);
  while (!Serial) {
    // wait for serial line to be ready
  }

  // try to access the SD card
  Serial.print("Initializing SD card...");
  EsploraTFT.text("Initializing SD card...", 0, 10);
  if (!SD.begin(SD_CS)) {
    Serial.println("failed!");
    EsploraTFT.text("failed!", 0, 10);
    return;
  }
  Serial.println("OK!");
  EsploraTFT.text("OK!", 0, 10);

  image = EsploraTFT.loadImage("arduino.bmp");

  if (image.isValid() != true) {
    Serial.println("error while loading arduino.bmp");
    EsploraTFT.text("error while loading arduino.bmp", 0, 10);
  }
  
  Esplora.writeRGB(0, 0, 0);
  EsploraTFT.background(0, 0, 0);
  Serial.println("started");
  EsploraTFT.text("started", 0, 10);

}

void loop(){
  int sw = Esplora.readButton(SWITCH_1);
  if(sw != prvSwitch1){
    prvSwitch1 = sw;
    if(sw == LOW){
      Esplora.writeRGB(255, 255, 255);
      Serial.println("Switch1 pressed");
      EsploraTFT.image(image, 0, 0);
      Esplora.writeRGB(0, 0, 0);
    }
  }
  
  sw = Esplora.readButton(SWITCH_2);
  if(sw != prvSwitch2){
    prvSwitch2 = sw;
    if(sw == LOW){
      Esplora.writeRGB(255, 255, 255);
      Serial.println("Switch2 pressed");
      EsploraTFT.background(255, 0, 0);
      Esplora.writeRGB(0, 0, 0);
    }
  }
  
  sw = Esplora.readButton(SWITCH_3);
  if(sw != prvSwitch3){
    prvSwitch3 = sw;
    if(sw == LOW){
      Esplora.writeRGB(255, 255, 255);
      Serial.println("Switch3 pressed");
      EsploraTFT.background(0, 255, 0);
      Esplora.writeRGB(0, 0, 0);
    }
  }
  
  sw = Esplora.readButton(SWITCH_4);
  if(sw != prvSwitch4){
    prvSwitch4 = sw;
    if(sw == LOW){
      Esplora.writeRGB(255, 255, 255);
      Serial.println("Switch4 pressed");
      EsploraTFT.background(0, 0, 255);
      Esplora.writeRGB(0, 0, 0);
    }
  }
  
}

Monday, March 31, 2014

Send string command from Android to Arduino in USB Host Mode

This is a example in my another blog show how Android send command to Arduino in USB Host mode. When user toggle the LED by clicking on the button, or change the screen color by slideing the bars, the commands will be add in a command queue, and then send to Arduino in background.

The code in Arduino Esplora is same as the previous example of Node.js + Arduino, running on PC.


Tuesday, March 18, 2014

Arduino detect string command from serial port

This example receive char and detect command terminal '\n', and compare with predefined command ("LEDON" and "LEDOFF") with strcmp() function, to turn on/off Esplora's on-board LED accordingly.



serialReadCmd.ino
#include <Esplora.h>
#include <TFT.h>
#include <SPI.h>

int MAX_CMD_LENGTH = 10;
char cmd[10];
int cmdIndex;
char incomingByte;

void setup() {
  
    EsploraTFT.begin();  
    EsploraTFT.background(0,0,0);
    EsploraTFT.stroke(255,255,255);  //preset stroke color
     
    //Setup Serial Port with baud rate of 9600
    Serial.begin(9600);
    
    //indicate start
    Esplora.writeRGB(255, 255, 255);
    delay(250);
    Esplora.writeRGB(0, 0, 0);
    
    cmdIndex = 0;
    
}
 
void loop() {
    
    if (incomingByte=Serial.available()>0) {
      
      char byteIn = Serial.read();
      cmd[cmdIndex] = byteIn;
      
      if(byteIn=='\n'){
        //command finished
        cmd[cmdIndex] = '\0';
        Serial.println(cmd);
        cmdIndex = 0;
        
        if(strcmp(cmd, "LEDON")  == 0){
          Serial.println("Command received: LEDON");
          Esplora.writeRGB(255, 255, 255);
        }else if (strcmp(cmd, "LEDOFF")  == 0) {
          Serial.println("Command received: LEDOFF");
          Esplora.writeRGB(0, 0, 0);
        }else{
          Serial.println("Command received: unknown!");
        }
        
      }else{
        if(cmdIndex++ >= MAX_CMD_LENGTH){
          cmdIndex = 0;
        }
      }
    }
    
}


Monday, February 10, 2014

Esplora example: read temperature sensor

This example read and display temperature sensor of Arduino Esplora on TFT screen, in celsius and fahrenheit.

Read temperature sensor on Arduino Esplora
Read temperature sensor on Arduino Esplora

#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

int celsius = 0;
int fahrenheit = 0;
char printoutC[3];
char printoutF[3];

void setup()
{
    EsploraTFT.begin();
    EsploraTFT.background(0,0,0);
    
    //preset dummy reading to print
    String dummy = "0";
    dummy.toCharArray(printoutC, 3);
    dummy.toCharArray(printoutC, 3);
    
    EsploraTFT.stroke(255,255,255);
    EsploraTFT.text("degree C: ", 0, 10);
    EsploraTFT.text("degree F: ", 0, 20);
} 

void loop()
{
    //read the temperature sensor
    celsius = Esplora.readTemperature(DEGREES_C);  
    fahrenheit = Esplora.readTemperature(DEGREES_F);

    //clear previous print of reading
    EsploraTFT.stroke(0,0,0);
    EsploraTFT.text(printoutC, 60, 10);
    EsploraTFT.text(printoutF, 60, 20);
    
    String(celsius).toCharArray(printoutC,3);
    String(fahrenheit).toCharArray(printoutF,3);
    EsploraTFT.stroke(255,255,255);
    EsploraTFT.text(printoutC, 60, 10);
    EsploraTFT.text(printoutF, 60, 20);

    delay(1000);
}

Tuesday, January 28, 2014

Send data to Arduino from Linux PC, program in C with GUI of GTK+3, as ColorChooser

In this example, we are going to develop a GUI program on Ubuntu Linux using C with GTK+3, select color to set LCD screen and LED on Arduino Esplora via USB serial.


In order to program with GTK+3, we have to install it on our PC, read last post "Install GTK+3 and compile with gcc in Linux". For the USB Serial communication part, refer to the post "Serial communication between Arduino and PC using C with termios".

Here is the code combine the termios and GTK+3 GtkColorChooser to build GUI for user to choice color, and send to Arduino Esplora via USB serial.

GtkEsploraColor.c:
#include <gtk/gtk.h>

#include <string.h>
#include <fcntl.h>
#include <termios.h>

int tty_fd;
struct termios old_stdio;

static void 
chooser_color_activated(GtkColorChooser *chooser, 
 GdkRGBA *color, gpointer user_data)
{
 GtkWidget *window = user_data;
 
 int intR = (int)((color->red)*65535);
 int intG = (int)((color->green)*65535);
 int intB = (int)((color->blue)*65535);
 GdkColor gColor = {
  0,
  intR, 
  intG, 
  intB};
 gtk_widget_modify_bg(GTK_WIDGET(window), GTK_STATE_NORMAL, &gColor);
 
 char bytes[] = {
  (char)(intB>>8), 
  (char)(intG>>8), 
  (char)(intR>>8)};
 
 write(tty_fd, bytes, 3);
}

void destroy( GtkWidget *widget,
              gpointer   data )
{
 close(tty_fd);
 tcsetattr(STDOUT_FILENO,TCSANOW,&old_stdio);
 
 g_print ("Bye!\n");
    gtk_main_quit();
}

int main( int argc, char *argv[])
{
 //Prepare for termios
 struct termios tio;
 struct termios stdio;
 //struct termios old_stdio;
 //int tty_fd;
 
 unsigned char c='D';
 tcgetattr(STDOUT_FILENO,&old_stdio);
 
 printf("Please start with %s /dev/ttyACM0 (for example)\n",argv[0]);
 memset(&stdio,0,sizeof(stdio));
 stdio.c_iflag=0;
 stdio.c_oflag=0;
 stdio.c_cflag=0;
 stdio.c_lflag=0;
 stdio.c_cc[VMIN]=1;
 stdio.c_cc[VTIME]=0;
 tcsetattr(STDOUT_FILENO,TCSANOW,&stdio);
 tcsetattr(STDOUT_FILENO,TCSAFLUSH,&stdio);
 fcntl(STDIN_FILENO, F_SETFL, O_NONBLOCK); // make the reads non-blocking
 
 memset(&tio,0,sizeof(tio));
 tio.c_iflag=0;
 tio.c_oflag=0;
 tio.c_cflag=CS8|CREAD|CLOCAL; // 8n1, see termios.h for more information
 tio.c_lflag=0;
 tio.c_cc[VMIN]=1;
 tio.c_cc[VTIME]=5;
 
 tty_fd=open(argv[1], O_RDWR | O_NONBLOCK);
 cfsetospeed(&tio,B9600); // 9600 baud
 cfsetispeed(&tio,B9600); // 9600 baud
 
 tcsetattr(tty_fd,TCSANOW,&tio);
 //---
 
    GtkWidget *window;
    GtkWidget *box;
    GtkWidget *label;
    GtkWidget *chooser;

    gtk_init(&argc, &argv);
    window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
    gtk_window_set_default_size(GTK_WINDOW(window), 400, 250);
    gtk_window_set_title(GTK_WINDOW(window), "arduino-er.blogspot.com");

    box = gtk_box_new(GTK_ORIENTATION_VERTICAL, 5);

 label = gtk_label_new("GtkColorChooser to Arduino Esplora");
    gtk_box_pack_start(GTK_BOX(box), label, FALSE, FALSE, 3);

 //Create GtkColorChooser
    chooser = gtk_color_chooser_widget_new();
    gtk_box_pack_start(GTK_BOX(box), chooser, FALSE, FALSE, 3);
    g_signal_connect (GTK_COLOR_CHOOSER(chooser),
                    "color-activated", 
                    G_CALLBACK (chooser_color_activated), 
                    window);

    g_signal_connect(G_OBJECT(window), "destroy", 
        G_CALLBACK(destroy), NULL);

    gtk_container_add(GTK_CONTAINER(window), box);
    gtk_widget_show_all(window);
    gtk_main();

    return 0;
}

Compile it with command:
$ gcc GtkEsploraColor.c -o GtkEsploraColor `pkg-config --cflags --libs gtk+-3.0`

Arduino Esplora code, SerialColor.ino:
It's same as in the post "Serial communication between Arduino Esplora and PC")
#include <Esplora.h>
#include <TFT.h>
#include <SPI.h>

void setup() {
  
    EsploraTFT.begin();  
    EsploraTFT.background(0,0,0);
    EsploraTFT.stroke(255,255,255);  //preset stroke color
     
    //Setup Serial Port with baud rate of 9600
    Serial.begin(9600);
    
    //indicate start
    Esplora.writeRGB(255, 255, 255);
    delay(250);
    Esplora.writeRGB(0, 0, 0);
    
}
 
void loop() {
    
    if(Serial.available()){
      char bytesIn[3] = {0x00, 0x00, 0x00};
      int i = 0;
      while(Serial.available()){
        bytesIn[i] = Serial.read();
        i++;
        if(i==3)
          break;
      }
      
      EsploraTFT.background(bytesIn[0], bytesIn[1], bytesIn[2]);
      Esplora.writeRGB(bytesIn[0], bytesIn[1], bytesIn[2]);
    }
}


Before run GtkEsploraColor, determine the connect USB port with dmesg:
- Insert Arduino Esploar to USB port
- Enter the command to check the port
$ dmesg
- The attached port should be listed in last lines. It's ttyACM0 in my setup
- Enter the command to run:
$ ./GtkEsploraColor /dev/ttyACM0
- Double Click on the color buttons to set color. The LCD screen and LED on Arduino Esplora should be changed accordingly.

Monday, January 27, 2014

Serial communication between Arduino and PC using C with termios

This example show how to implement Serial communication using C language with termios.h. It run on Ubuntu, and send and receive data to and from Arduino Esplora connected with USB cable.


The C program, testTermios.c, in Ubuntu side copy from example in http://en.wikibooks.org/wiki/Serial_Programming/Serial_Linux#termios, it is a simple terminal program with termios.h.
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <termios.h>
 
int main(int argc,char** argv)
{
 struct termios tio;
 struct termios stdio;
 struct termios old_stdio;
 int tty_fd;
 
 unsigned char c='D';
 tcgetattr(STDOUT_FILENO,&old_stdio);
 
 printf("Please start with %s /dev/ttyS1 (for example)\n",argv[0]);
 memset(&stdio,0,sizeof(stdio));
 stdio.c_iflag=0;
 stdio.c_oflag=0;
 stdio.c_cflag=0;
 stdio.c_lflag=0;
 stdio.c_cc[VMIN]=1;
 stdio.c_cc[VTIME]=0;
 tcsetattr(STDOUT_FILENO,TCSANOW,&stdio);
 tcsetattr(STDOUT_FILENO,TCSAFLUSH,&stdio);
 fcntl(STDIN_FILENO, F_SETFL, O_NONBLOCK); // make the reads non-blocking
 
 memset(&tio,0,sizeof(tio));
 tio.c_iflag=0;
 tio.c_oflag=0;
 tio.c_cflag=CS8|CREAD|CLOCAL; // 8n1, see termios.h for more information
 tio.c_lflag=0;
 tio.c_cc[VMIN]=1;
 tio.c_cc[VTIME]=5;
 
 tty_fd=open(argv[1], O_RDWR | O_NONBLOCK);
 cfsetospeed(&tio,B115200); // 115200 baud
 cfsetispeed(&tio,B115200); // 115200 baud
 
 tcsetattr(tty_fd,TCSANOW,&tio);
 while (c!='q')
 {
  if (read(tty_fd,&c,1)>0)        write(STDOUT_FILENO,&c,1);
  // if new data is available on the serial port, print it out
  if (read(STDIN_FILENO,&c,1)>0)  write(tty_fd,&c,1);
  // if new data is available on the console, send it to the serial port
 }
 
 close(tty_fd);
 tcsetattr(STDOUT_FILENO,TCSANOW,&old_stdio);
 
 return EXIT_SUCCESS;
}

Compile it with the command:
$ gcc testTermios.c -o testTermios

To run it with specified device port, run the command dmesg to check the Arduino Esplora connected post:
$ dmesg

It's ttyACM0 in my case.

Run:
$ ./testTermios /dev/ttyACM0

Press any key will send to ttyACM0, press 'q' to quit.

In Arduino Esplora side, testSerial.ino. (It is same as the example in "Serial communication between Arduino Esplora and PC", using Arduino IDE's Serial Monitor.)
#include <Esplora.h>
#include <TFT.h>
#include <SPI.h>

int prevSw1 = HIGH;
int incomingByte = 0;
String charsIn = "";
char printout[20];  //max char to print: 20
 
void setup() {
  
    EsploraTFT.begin();  
    EsploraTFT.background(0,0,0);
    EsploraTFT.stroke(255,255,255);  //preset stroke color
     
    //Setup Serial Port with baud rate of 9600
    Serial.begin(9600);
    
    //indicate start
    Esplora.writeRGB(255, 255, 255);
    delay(250);
    Esplora.writeRGB(0, 0, 0);
    
}
 
void loop() {
    int sw1 = Esplora.readButton(SWITCH_1);
    if(sw1 != prevSw1){
      if(sw1 == LOW){
        Serial.println("Hello from Arduino Esplora");
      }
      prevSw1 = sw1;
    }
    
    while (Serial.available()) {
      char charRead = Serial.read();
      charsIn.concat(charRead);
    }
    if(charsIn != ""){
      Serial.println("How are you, " + charsIn);
      charsIn.toCharArray(printout, 21);
      EsploraTFT.background(0,0,0);
      EsploraTFT.text(printout, 0, 10);
      charsIn = "";
    }
}


Next:
- Send data to Arduino from Linux PC, program in C with GUI of GTK+3, as ColorChooser

Saturday, January 25, 2014

Serial communication between Arduino Esplora and PC

This example show bi-direction serial communication between Arduino Esplora and PC. In PC side, the Serial Monitor can be used as terminal to send data to and receive data from Arduino Esplora.


Arduino Esplora sample code:
#include <Esplora.h>
#include <TFT.h>
#include <SPI.h>

int prevSw1 = HIGH;
int incomingByte = 0;
String charsIn = "";
char printout[20];  //max char to print: 20
 
void setup() {
  
    EsploraTFT.begin();  
    EsploraTFT.background(0,0,0);
    EsploraTFT.stroke(255,255,255);  //preset stroke color
     
    //Setup Serial Port with baud rate of 9600
    Serial.begin(9600);
    
    //indicate start
    Esplora.writeRGB(255, 255, 255);
    delay(250);
    Esplora.writeRGB(0, 0, 0);
    
}
 
void loop() {
    int sw1 = Esplora.readButton(SWITCH_1);
    if(sw1 != prevSw1){
      if(sw1 == LOW){
        Serial.println("Hello from Arduino Esplora");
      }
      prevSw1 = sw1;
    }
    
    while (Serial.available()) {
      char charRead = Serial.read();
      charsIn.concat(charRead);
    }
    if(charsIn != ""){
      Serial.println("How are you, " + charsIn);
      charsIn.toCharArray(printout, 21);
      EsploraTFT.background(0,0,0);
      EsploraTFT.text(printout, 0, 10);
      charsIn = "";
    }
}

Related:
Serial communication between Arduino and PC using C with termios

Wednesday, January 22, 2014

Arduino Esplora example for Accelerometer

This example read Accelerometer senser on Esplora board, and display on LCD screen accordingly; such that you can know how Accelerometer work.


#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

const int MAX_W = 160;
const int MAX_H = 128;
int xCenter = MAX_W/2;
int yCenter = MAX_H/2;

int xPos = xCenter; 
int yPos = yCenter;
int xPrev = xCenter;
int yPrev = yCenter;
char printoutX[5];
char printoutY[5];
char printoutZ[5];


void setup(){
  Serial.begin(9600);
  Mouse.begin();
  
  EsploraTFT.begin();  
  EsploraTFT.background(0,0,0);

  //preset dummy reading to print
  String dummy = "0";
  dummy.toCharArray(printoutX,5);
  dummy.toCharArray(printoutY,5);
  dummy.toCharArray(printoutZ,5);
}

void loop(){
  
  if(Esplora.readButton(SWITCH_1) == LOW){
    EsploraTFT.background(0,0,0);
  }
  
  int xValue = Esplora.readAccelerometer(X_AXIS);
  int yValue = Esplora.readAccelerometer(Y_AXIS);
  int zValue = Esplora.readAccelerometer(Z_AXIS);
  
  
  xPos = map(xValue, -512, 512, MAX_H, 0);
  yPos = map(yValue, -512, 512, 0, MAX_H);
  
  //clear previous print of reading
  EsploraTFT.stroke(0,0,0);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutZ,0,30);
  
  String(xValue).toCharArray(printoutX,5);
  String(yValue).toCharArray(printoutY,5);
  String(zValue).toCharArray(printoutZ,5);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutZ,0,30);
  
  if(xPos!=xPrev || yPos!=yPrev){
    
    EsploraTFT.line(xPrev, yPrev, xPos, yPos);
    
    xPrev=xPos;
    yPrev=yPos;
  }
  
  delay(10);
}

Saturday, January 18, 2014

Arduino Esplora Joystick Mouse with Button function

This example work on last post "Auto center Arduino Esplora Joystick Mouse of Arduino Esplora", with button function added.

#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

const int MAX_W = 160;
const int MAX_H = 128;
int xCenter = MAX_W/2;
int yCenter = MAX_H/2;

int xPos = xCenter; 
int yPos = yCenter;
int xPrev = xCenter;
int yPrev = yCenter;
char printoutX[5];
char printoutY[5];
char printoutSlider[5];

int centerJoystickX, centerJoystickY;

int JoystickButton;
int prevJoystickButton;

void setup(){
  Serial.begin(9600);
  Mouse.begin();
  
  EsploraTFT.begin();  
  EsploraTFT.background(0,0,0);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.line(xCenter, 0, xCenter, MAX_H);
  EsploraTFT.line(0, yCenter, MAX_W, yCenter);

  //preset dummy reading to print
  String dummy = "0";
  dummy.toCharArray(printoutX,5);
  dummy.toCharArray(printoutY,5);
  dummy.toCharArray(printoutSlider,5);
  
  //Read Joystick center position at start-up
  centerJoystickX = Esplora.readJoystickX();
  centerJoystickY = Esplora.readJoystickY();
  
  //preset JoystickSwitch states
  JoystickButton = HIGH;
  prevJoystickButton = HIGH;
}

void loop(){
  int xValue = Esplora.readJoystickX();
  int yValue = Esplora.readJoystickY();
  int sliderValue = Esplora.readSlider();
  
  //map stick value to TFT screen position
  if(xValue >= centerJoystickX){
    xPos = map(xValue, 512, centerJoystickX, 0, xCenter);
  }else{
    xPos = map(xValue, centerJoystickX, -512, xCenter, MAX_W);
  }
  
  int mouseX, mouseY;
  
  if(xValue >= centerJoystickX){
    xPos = map(xValue, 512, centerJoystickX, 0, xCenter);
    
    //report mouse position only if position offset > slider
    if((xValue - centerJoystickX) >= sliderValue){
      mouseX = map( xValue, 512, centerJoystickX, -10, 0);
    }else{
      mouseX = 0;
    }
  }else{
    xPos = map(xValue, centerJoystickX, -512, xCenter, MAX_W);
    
    //report mouse position only if position offset > slider
    if((centerJoystickX - xValue) >= sliderValue){
      mouseX = map( xValue, centerJoystickX, 512, 0, -10);
    }else{
      mouseX = 0;
    }
  }
  
  if(yValue >= centerJoystickY){
    yPos = map(yValue, 512, centerJoystickY, MAX_H, yCenter);
    
    //report mouse position only if position offset > slider
    if((yValue - centerJoystickY) >= sliderValue){
      mouseY = map( yValue, 512, centerJoystickY, 10, 0);
    }else{
      mouseY = 0;
    }
  }else{
    yPos = map(yValue, centerJoystickY, -512, yCenter, 0);
    
    //report mouse position only if position offset > slider
    if((centerJoystickY - yValue) >= sliderValue){
      mouseY = map( yValue, centerJoystickY, 512, 0, 10);
    }else{
      mouseY = 0;
    }
  }
  
  Mouse.move(mouseX, mouseY, 0);
  
  //clear previous print of reading
  EsploraTFT.stroke(0,0,0);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutSlider,0,30);
  
  String(xPos).toCharArray(printoutX,5);
  String(yPos).toCharArray(printoutY,5);
  String(sliderValue).toCharArray(printoutSlider,5);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutSlider,0,30);
  
  if(xPos!=xPrev || yPos!=yPrev){
    
    EsploraTFT.line(xPrev, yPrev, xPos, yPos);
    EsploraTFT.stroke(0,0,255);
    EsploraTFT.point(xPos, yPos);
    
    xPrev=xPos;
    yPrev=yPos;
  }
  
  //Read JoystickButton
  //send Mouse.press()/.release() if JoystickButton changed
  JoystickButton = Esplora.readJoystickButton();
  if(JoystickButton != prevJoystickButton){

    if(JoystickButton == LOW){
      Mouse.press();
      Esplora.writeRed(100);
    }else{
      Mouse.release();
      Esplora.writeRed(0);
    }
    prevJoystickButton = JoystickButton;
  }
  
  delay(10);
}

Friday, January 17, 2014

Auto center Arduino Esplora Joystick Mouse of Arduino Esplora

This example is a Arduino Esplora Joystick Mouse with auto center, and you can adjust the sensitivity using the Esplora's slider (the Linear Potentiometer).



Arduino IDE come with a EsploraJoystickMouse example (in Arduino IDE > File > Examples > Esplora > Beginners > EsploraJoystickMouse, or here), it will report mouse position to your PC base on Esplora's Joystick.

WARNING: this sketch will take over your mouse movement. If you lose control of your mouse do the following:
 1) unplug the Esplora.
 2) open the EsploraBlink sketch
 3) hold the reset button down while plugging your Esplora back in
 4) while holding reset, click "Upload"
 5) when you see the message "Done compiling", release the reset button.

It is possible that your mouse will auto-run when the joystick is in rest position. Because it assume the function Esplora.readJoystickX() and Esplora.readJoystickY() return 0 at center rest position. But it is not the actual case, most probably it return non-0 even the Joystick is in rest position.

The below example, modified from last example Read joystick and display on TFT, read the actual center postion at power up (assume it is in rest), to offset the x, y postion accordingly. And also it will compare the x, y values with the slider value to adjust the sensitivity. If the movement of x, y postion is less than slider, it will return no movement to PC.

#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

const int MAX_W = 160;
const int MAX_H = 128;
int xCenter = MAX_W/2;
int yCenter = MAX_H/2;

int xPos = xCenter; 
int yPos = yCenter;
int xPrev = xCenter;
int yPrev = yCenter;
char printoutX[5];
char printoutY[5];
char printoutSlider[5];

int centerJoystickX, centerJoystickY;

int JoystickButton;
int prevJoystickButton;

void setup(){
  Serial.begin(9600);
  Mouse.begin();
  
  EsploraTFT.begin();  
  EsploraTFT.background(0,0,0);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.line(xCenter, 0, xCenter, MAX_H);
  EsploraTFT.line(0, yCenter, MAX_W, yCenter);

  //preset dummy reading to print
  String dummy = "0";
  dummy.toCharArray(printoutX,5);
  dummy.toCharArray(printoutY,5);
  dummy.toCharArray(printoutSlider,5);
  
  //Read Joystick center position at start-up
  centerJoystickX = Esplora.readJoystickX();
  centerJoystickY = Esplora.readJoystickY();
  
  //preset JoystickSwitch states
  JoystickButton = HIGH;
  prevJoystickButton = HIGH;
}

void loop(){
  int xValue = Esplora.readJoystickX();
  int yValue = Esplora.readJoystickY();
  int sliderValue = Esplora.readSlider();
  
  //map stick value to TFT screen position
  if(xValue >= centerJoystickX){
    xPos = map(xValue, 512, centerJoystickX, 0, xCenter);
  }else{
    xPos = map(xValue, centerJoystickX, -512, xCenter, MAX_W);
  }
  
  int mouseX, mouseY;
  
  if(xValue >= centerJoystickX){
    xPos = map(xValue, 512, centerJoystickX, 0, xCenter);
    
    //report mouse position only if position offset > slider
    if((xValue - centerJoystickX) >= sliderValue){
      mouseX = map( xValue, 512, centerJoystickX, -10, 0);
    }else{
      mouseX = 0;
    }
  }else{
    xPos = map(xValue, centerJoystickX, -512, xCenter, MAX_W);
    
    //report mouse position only if position offset > slider
    if((centerJoystickX - xValue) >= sliderValue){
      mouseX = map( xValue, centerJoystickX, 512, 0, -10);
    }else{
      mouseX = 0;
    }
  }
  
  if(yValue >= centerJoystickY){
    yPos = map(yValue, 512, centerJoystickY, MAX_H, yCenter);
    
    //report mouse position only if position offset > slider
    if((yValue - centerJoystickY) >= sliderValue){
      mouseY = map( yValue, 512, centerJoystickY, 10, 0);
    }else{
      mouseY = 0;
    }
  }else{
    yPos = map(yValue, centerJoystickY, -512, yCenter, 0);
    
    //report mouse position only if position offset > slider
    if((centerJoystickY - yValue) >= sliderValue){
      mouseY = map( yValue, centerJoystickY, 512, 0, 10);
    }else{
      mouseY = 0;
    }
  }
  
  Mouse.move(mouseX, mouseY, 0);
  
  //clear previous print of reading
  EsploraTFT.stroke(0,0,0);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutSlider,0,30);
  
  String(xPos).toCharArray(printoutX,5);
  String(yPos).toCharArray(printoutY,5);
  String(sliderValue).toCharArray(printoutSlider,5);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  EsploraTFT.text(printoutSlider,0,30);
  
  if(xPos!=xPrev || yPos!=yPrev){
    
    EsploraTFT.line(xPrev, yPrev, xPos, yPos);
    EsploraTFT.stroke(0,0,255);
    EsploraTFT.point(xPos, yPos);
    
    xPrev=xPos;
    yPrev=yPos;
  }
  
  delay(10);
}

Next: Arduino Esplora Joystick Mouse with Button function

Tuesday, January 14, 2014

Arduino Esplora example: read joystick and display on TFT

This example read joystick on Arduino Esplora, and display on TFT shield.


The function Esplora.readJoystickX() and Esplora.readJoystickY().
  • Esplora.readJoystickX() read the position of the X-axis of the joystick. When the joystick is in the center, it returns zero. Positive values indicate the joystick has moved to the right and negative values when moved to the left.
  • Esplora.readJoystickY() read the position of the Y-axis of the joystick. When the joystick is in the center, it returns zero. Positive values indicate the joystick has moved up and negative values when moved down.
With function map(value, fromLow, fromHigh, toLow, toHigh), it's easy to map value from joysticks to screen coordinates. It re-maps a number from one range to another. That is, a value of fromLow would get mapped to toLow, a value of fromHigh to toHigh, values in-between to values in-between.

Example code:
#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

const int MAX_W = 160;
const int MAX_H = 128;
int xCenter = MAX_W/2;
int yCenter = MAX_H/2;

int xPos = xCenter; 
int yPos = yCenter;
int xPrev = xCenter;
int yPrev = yCenter;
char printoutX[5];
char printoutY[5];

void setup(){
  EsploraTFT.begin();  
  EsploraTFT.background(0,0,0);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.line(xCenter, 0, xCenter, MAX_H);
  EsploraTFT.line(0, yCenter, MAX_W, yCenter);

  //preset dummy reading to print
  String dummy = "0";
  dummy.toCharArray(printoutX,5);
  dummy.toCharArray(printoutY,5);
}

void loop(){
  int xValue = Esplora.readJoystickX();
  int yValue = Esplora.readJoystickY();

  //clear previous print of reading
  EsploraTFT.stroke(0,0,0);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  
  String(xValue).toCharArray(printoutX,5);
  String(yValue).toCharArray(printoutY,5);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.text(printoutX,0,10);
  EsploraTFT.text(printoutY,0,20);
  
  //map stick value to TFT screen position
  xPos = map( xValue, 512, -512, 0, MAX_W);
  yPos = map( yValue, 512, -512, MAX_H, 0);
  
  if(xPos!=xPrev || yPos!=yPrev){
    
    EsploraTFT.line(xPrev, yPrev, xPos, yPos);
    EsploraTFT.stroke(0,0,255);
    EsploraTFT.point(xPos, yPos);
    
    xPrev=xPos;
    yPrev=yPos;
  }
  
  delay(50);
}

Next example: Auto center Arduino Esplora Joystick Mouse

Monday, January 13, 2014

Arduino Esplora example: read slider and display on TFT

The example run on Esplora, read from slider, and display on TFT.

#include <TFT.h>
#include <SPI.h>
#include <Esplora.h>

const int MAX_W = 160;
const int MAX_H = 128;
unsigned long ul_MAX_H = (unsigned long)MAX_H;
const int MAX_SLIDER = 1023;

int xPos = 0; 
int yPos = 0;
int xPrev = 0;
int yPrev = MAX_H;
char printout[5];

void setup(){
  EsploraTFT.begin();  
  EsploraTFT.background(0,0,0);

  //preset dummy reading to print
  String dummy = "0";
  dummy.toCharArray(printout,5);
}

void loop(){
  int slider = Esplora.readSlider();

  //clear previous print of reading
  EsploraTFT.stroke(0,0,0);
  EsploraTFT.text(printout,0,10);
  //update reading
  String(slider).toCharArray(printout,5);
  EsploraTFT.stroke(255,255,255);
  EsploraTFT.text(printout,0,10);

  // update the location of the dot
  xPos++;
  //align y-position
  yPos = MAX_H - slider * ul_MAX_H/MAX_SLIDER;
  EsploraTFT.line(xPrev, yPrev, xPos, yPos);

  // if the x position reach screen edges, 
  // clear screen
  if(xPos >= MAX_W){
    EsploraTFT.background(0,0,0);
    xPos = 0;
  }

  // update the point's previous location
  xPrev=xPos;
  yPrev=yPos;

  delay(50);
}

Friday, November 15, 2013

Communication between Arduino and Raspberry Pi (in Python)

This example show how to write a simple Python program on Raspberry Pi to get keyboard input and send to Arduino via USB. In Arduino, send back the received chars to Raspberry Pi, then print on screen in Pi side.



In this example, Raspberry Pi act as host and Arduino Due act as device, and connect with USB on Programming USB Port.

Python code in Raspberry Pi:
import serial
ser = serial.Serial('/dev/ttyACM1', 9600)

name_out = raw_input("Who are you?\n")
ser.write(name_out + "\n")
name_return = ser.readline()
print(name_return)

Code in Arduino side:
int pinLED = 13;
boolean ledon;

void setup() {
  Serial.begin(9600);
  pinMode(pinLED, OUTPUT);
  ledon = true;
  digitalWrite(pinLED, ledon = !ledon);
}
 
void loop() {
  if(Serial.available() > 0){
    Serial.print("Hello ");
    
    while(Serial.available()>0){
      char charIn = (char)Serial.read();
      Serial.print(charIn);
      if (charIn == '\n')
        break;
    }
    
    digitalWrite(pinLED, ledon = !ledon);
  }
}

Cross-post with my another blog: Hello Raspberry Pi