Digital ChallengeArduino × Processing
F2Foundation module

Processing — Real-Time Visualization

Turn raw sensor numbers into live graphics on your screen.

Processing is the visual front-end for every project: it receives data from Arduino over USB and draws it as text, bars, colours and animations. Learn the sketch structure, the drawing API, map() and the serial pattern used everywhere.

3 × 45 min difficultyComputer ScienceMathematicsVisual Arts
Processing — Real-Time Visualization
setup() & draw()serialEvent()map()CSV parsingSerial.write()
01Before you start

What you’ll learn

By the end of this module you can…
  • 1Describe how Arduino and Processing communicate over a serial (USB) connection at the same baud rate.
  • 2Write active Processing sketches using setup() and draw(), shapes, colours and text.
  • 3Use the coordinate system (origin top-left, Y grows downward) to place elements precisely.
  • 4Scale sensor values to screen sizes with map() and format numbers with nf().
  • 5Receive, validate and parse single values and comma-separated values (CSV) in serialEvent().
  • 6Send commands from Processing back to Arduino with mouse clicks and key presses.
Key vocabulary
Processing
A free, Java-based language and environment for visual and interactive programs, created at the MIT Media Lab in 2001.
PDE
Processing Development Environment — the editor, console and toolbar where you write sketches.
Serial communication
Sending data one bit after another over a wire — here, the USB cable between Arduino and computer.
Baud rate
Speed of serial communication in bits per second (e.g. 9600). Both sides must match.
COM port
The name your computer gives the Arduino’s serial connection (e.g. COM3 or /dev/ttyUSB0).
CSV
Comma-Separated Values, e.g. 23.5,61.0 — several numbers in one line of text.
Parsing
Turning text (a String) into usable data (numbers).
Frame
One execution of draw(). Processing draws ~60 frames per second.
02Kit list

Required equipment

ComponentQtyPurpose
Processing IDE 4.x1Writing and running visualizations — processing.org
Arduino IDE 2.x1Programming the Arduino board — arduino.cc
Arduino Uno1Sending sensor data over serial
USB cable1Connecting Arduino to the computer
Any sensor1DHT11, LDR, HC-SR04 … to generate data
03Theory

What is Processing?

Processing is a free, open-source programming environment designed for visual output, animation and interaction. In Arduino projects it is the visual dashboard: it cannot control hardware directly, but it is excellent at receiving data and turning numbers into compelling visuals.

FeatureArduino IDEProcessing
Primary purposeControl hardware (sensors, motors)Create visual output (graphics, charts)
Runs onMicrocontroller (Arduino board)Computer (Windows, macOS, Linux)
OutputSignals to componentsGraphics on screen
Data flowSends data via SerialReceives data via Serial
Language baseC / C++Java (also Python & JavaScript modes)
Sketch structuresetup() + loop()setup() + draw()
Tip
Processing is free and runs on Windows, macOS and Linux. Download it from processing.org/download.
04Architecture

How Arduino and Processing Work Together

The two programs talk through serial communication over the USB cable. Every project in the series follows the same pipeline:

InteractiveSerial pipelineThe data pipeline used in all five projects.
Sensor
Arduino
USB
Processing
Screen
Arduino sends
Serial.println("22.0,63.0");
Processing parses
split(…) → ["22.0", "63.0"]
Screen draws
  1. 01A sensor reads a physical value (temperature, distance, light …).
  2. 02Arduino processes the value and sends it with Serial.println().
  3. 03Processing receives the text, parses it and converts it to a number.
  4. 04Processing draws text, bars, colours or shapes on the screen.
Same speed on both sides
Both programs must use the same baud rate, e.g. 9600. Arduino: Serial.begin(9600) — Processing: new Serial(this, port, 9600).
05Core concepts

Sketch Structure & Events

Every Processing program (a sketch) has two main functions — just like Arduino — plus optional event functions that run when something happens.

FunctionWhen it runsTypical use
setup()Once, at program startsize(), serial setup, initial variables
draw()Continuously (~60 fps)background(), text(), rect(), shapes
serialEvent()When new serial data arrivesRead and parse incoming Arduino data
mousePressed()When a mouse button is clickedUI buttons, interactions
keyPressed()When a key is pressedSend commands back to Arduino
Skeleton.pdeProcessing · Java
void setup() {
  // Runs ONCE at the start
  // Set window size, initialize serial port
}

void draw() {
  // Runs CONTINUOUSLY — like loop() in Arduino
  // Draw shapes, text, update the display
}

The Serial library

SerialSetup.pdeProcessing · Java
import processing.serial.*;   // 1. Import the library

Serial myPort;                // 2. Declare the serial port object

void setup() {
  size(400, 300);
  printArray(Serial.list());  // 3. List available ports
  // 4. Open the port — index [0] is usually the first available
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil('\n');   // 5. Call serialEvent() once per full line
}
Tip
If Serial.list()[0] is the wrong port, look at the list printed by printArray(Serial.list()) in the console and change the index.
Warning
Close the Arduino IDE Serial Monitor before running Processing — both cannot use the same port at the same time.
06Graphics API

Drawing, Colour & Coordinates

FunctionDescriptionExample
size(w, h)Set window width and heightsize(600, 400)
background(r,g,b)Fill background with a colourbackground(255) — white
fill(r,g,b)Set fill colour for shapesfill(255, 0, 0) — red
stroke(r,g,b)Set outline colourstroke(0) — black
text(str, x, y)Draw text at a positiontext("Hello", 50, 100)
textSize(n)Set font sizetextSize(20)
rect(x, y, w, h)Draw a rectanglerect(50, 100, 200, 30)
ellipse(x, y, w, h)Draw an ellipse / circleellipse(200, 200, 50, 50)
line(x1,y1,x2,y2)Draw a lineline(0, 0, 200, 200)
map(v,lo1,hi1,lo2,hi2)Scale a value to a new rangemap(temp, 0, 100, 0, 300)
nf(n, d1, d2)Format a number as textnf(3.14159, 1, 2) → "3.14"

Colour in Processing

Processing uses RGB values from 0 to 255. A fourth value (alpha) sets transparency.

One number means greyscale: fill(0) is black, fill(255) is white.

sketchProcessing · Java
fill(255, 0, 0);      // Red
fill(0, 255, 0);      // Green
fill(0, 0, 255);      // Blue
fill(255, 255, 0);    // Yellow
fill(128, 0, 128);    // Purple
fill(0);              // Black (shorthand)
fill(255);            // White (shorthand)
fill(255, 0, 0, 150); // Semi-transparent red

The coordinate system

The origin (0, 0) is in the upper-left corner. X grows to the right; Y grows downward. In a 320 × 240 window, (319, 239) is the last visible pixel in the lower-right corner.

InteractiveCoordinate explorerMove your mouse over the canvas: notice that Y increases downward.
xy(0, 0)(400, 240)rect(50, 100, 200, 30)
mouseX, mouseY
260, 150
ellipse(260, 150, 10, 10);
Distance from bottom: 90 px
Note
rect(50, 100, 200, 30) starts 100 pixels from the top — not the bottom. To draw a bar that grows upward, start at height - barHeight.
07Mathematics

map() — the Most Important Function

map() rescales a value from one range to another. Sensor values (0–1023) almost never fit your screen directly, so you will use map() in every project.

Formula
result = lo2 + (value − lo1) × (hi2 − lo2) / (hi1 − lo1)
This is a linear function — the same “y = kx + n” you know from maths class.
sketchProcessing · Java
// Sensor value 0–1023 mapped to bar width 0–300 pixels:
float barWidth = map(sensorValue, 0, 1023, 0, 300);
rect(50, 100, barWidth, 30);

// Temperature 0–50 °C mapped to the red colour component:
float r = map(temperature, 0, 50, 0, 255);
fill(r, 0, 0);
Interactivemap() playgroundDrag the slider and change the ranges — watch the formula update.
map(512, 0, 1023, 0, 300) = 0 + (512 − 0) × (300 − 0) / (1023 − 0) = 150.15
rect(50, 100, result, 30)
150 px
Tip
map() does not clamp. If the value goes outside the input range, the result goes outside the output range. Wrap it in constrain(x, min, max) when you need limits.
08Tools

The Processing Development Environment

The PDE contains a text editor, a compiler and a display window. It has a message area, a text console, tabs for files, a toolbar and menus. Full reference: processing.org/environment.

ComponentPurpose
Text editorWrite and edit sketch code
Message areaFeedback while saving, exporting and errors
ConsoleText output from print() and println()
Toolbar▶ Run (compile + open window) and ■ Stop
TabsManage multiple files within one sketch
MenusFile, Edit, Sketch, Debug, Tools, Help

Most-used menu commands

MenuCommandWhat it does
FileNew / Open / Save As…Create, open, or save a copy of a sketch
FileExamples…Browse built-in example sketches — great for learning
FileExport Application…Create a standalone program from your sketch
EditAuto FormatTidy indentation (Ctrl+T)
EditComment / UncommentToggle // on the selected lines
SketchPresentRun full-screen (Esc to exit)
SketchTweakChange numbers and colours live while running
SketchImport Library…Add import lines or install new libraries
SketchAdd File…Copy images/fonts into the sketch’s data/ folder
DebugEnable DebuggerBreakpoints, Step, Step Into, Step Out
ToolsColor Selector…Pick colours and copy RGB/HSB/Hex values
ToolsArchive SketchSave a .zip copy of the sketch

Sketches and the Sketchbook

Each sketch lives in its own folder; the main file has the same name as the folder with a .pde extension. Images, fonts and sounds go into a data/ sub-folder. Find the Sketchbook location in File → Preferences.

sketchText
MyProject/              ← sketch folder
├── MyProject.pde       ← main file (same name as folder)
└── data/               ← images, fonts, sounds

Renderers

RendererDescriptionBest for
DefaultStandard 2D rendererMost 2D sketches and sensor displays
P2DFaster OpenGL 2DHigh-speed 2D graphics
P3D3D with camera, lighting, materials3D visualizations
FX2DHigh-quality JavaFX 2DLarge / high-resolution displays

Choose a renderer as the third argument of size(), e.g. size(400, 300, P3D);.

Static vs. active sketches

Static — no setup()/draw(); runs once. Good for learning coordinates, shapes and colour.

sketchProcessing · Java
size(200, 200);
background(255);
noStroke();
fill(255, 204, 0);
rect(30, 20, 50, 50);

Active — uses setup() + draw() for animation, sensors and interaction.

sketchProcessing · Java
void setup() {
  size(200, 200);
  noStroke();
  fill(0, 102, 153, 204);
}
void draw() {
  background(255);
  rect(width - mouseX, height - mouseY, 50, 50);
  rect(mouseX, mouseY, 50, 50);
}
Libraries, tools & modes
Library: Sketch → Import Library → Add Library… · Tool: Tools → Manage Tools… · Mode: Mode menu → Add Mode…. The Serial library is built in — start every project sketch with import processing.serial.*;.
09Hands-on · no hardware

Lab 1 — Your First Processing Sketch

Before connecting Arduino, get comfortable with the environment: draw a rounded rectangle, some text, and a circle whose colour changes over time.

FirstSketch.pdeProcessing · Java
float t = 0;

void setup() {
  size(500, 300);
  textAlign(CENTER, CENTER);
}

void draw() {
  background(30);                 // dark grey background
  t++;

  // Animated colour using sine waves
  float r = 127 + 127 * sin(t * 0.05);
  float g = 127 + 127 * sin(t * 0.03);

  // Rounded rectangle (last argument = corner radius)
  fill(r, g, 100);
  rect(50, 80, 400, 60, 10);

  // White text centred in the rectangle
  fill(255);
  textSize(22);
  text("Processing + Arduino = Power!", 250, 110);

  // Animated circle
  fill(r, 50, 200);
  ellipse(250, 220, 60, 60);
}
UpdatedUses a new variable t instead of redeclaring Processing’s built-in frameCount.
ConceptWhere in the code
Window sizesize(500, 300) in setup()
Continuous animationdraw() runs ~60 times per second
Dynamic colour using mathssin() of a growing number
Rectanglerect(x, y, width, height, radius)
Texttext(), textSize(), textAlign()
Circleellipse(cx, cy, width, height)
Tip
Press Ctrl+R (Cmd+R on Mac) to run, Ctrl+. to stop — or use the ▶ / ■ buttons.
10Hands-on

Lab 2 — Receiving Data from Arduino

Arduino sends a counter (0–100) every 500 ms; Processing shows it as text and as a bar.

Step 1 — Counter.ino (upload first)Arduino · C++
int counter = 0;

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

void loop() {
  Serial.println(counter);   // send number to Processing
  counter++;
  if (counter > 100) counter = 0;
  delay(500);
}
Warning
Upload to Arduino, then close the Serial Monitor before running Processing.
Step 2 — Receiver.pdeProcessing · Java
import processing.serial.*;

Serial myPort;
int receivedValue = 0;

void setup() {
  size(400, 250);
  printArray(Serial.list());              // check available ports
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil('\n');
}

void draw() {
  background(240);

  fill(50);
  textSize(20);
  text("Received from Arduino: " + receivedValue, 50, 80);

  fill(100, 150, 255);
  float barW = map(receivedValue, 0, 100, 0, 300);
  rect(50, 120, barW, 40);

  fill(0);
  textSize(16);
  text(receivedValue + " / 100", 50 + barW/2, 145);
}

void serialEvent(Serial p) {
  String incoming = p.readStringUntil('\n');
  if (incoming != null) {
    incoming = trim(incoming);
    if (incoming.matches("\\d+")) {       // only digits? then it is safe
      receivedValue = int(incoming);
    }
  }
}
PartExplanation
import processing.serial.*Imports the serial communication library
Serial myPortObject that represents the serial port connection
Serial.list()[0]Selects the first available COM port
serialEvent(Serial p)Called automatically when new data arrives
readStringUntil('\n')Reads one line of text up to the newline
trim()Removes spaces and newline characters
matches("\\d+")True only if the text contains digits only (safe parsing)
map(value, 0, 100, 0, 300)Scales 0–100 to a pixel width of 0–300
11Hands-on

Lab 3 — Parsing Multiple Values (CSV)

In Projects 1, 3 and 5 Arduino sends several values in one line, separated by commas. This is the pattern you’ll reuse again and again.

SendTwoValues.inoArduino · C++
void setup() {
  Serial.begin(9600);
}

void loop() {
  float temperature = 23.5;   // in the real project: a sensor reading
  float humidity    = 61.0;

  Serial.print(temperature);
  Serial.print(",");          // comma separator
  Serial.println(humidity);   // newline at the end
  delay(1000);
}
ParseTwoValues.pdeProcessing · Java
import processing.serial.*;

Serial myPort;
float temperature = 0;
float humidity = 0;

void setup() {
  size(500, 300);
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil('\n');
}

void draw() {
  background(255);
  fill(0);
  textSize(22);
  text("Temperature: " + nf(temperature, 1, 1) + " \u00B0C", 50, 100);
  text("Humidity:    " + nf(humidity, 1, 1) + " %", 50, 150);

  fill(220, 50, 50);                                   // temperature bar
  rect(50, 170, map(temperature, 0, 50, 0, 380), 25);

  fill(50, 100, 220);                                  // humidity bar
  rect(50, 210, map(humidity, 0, 100, 0, 380), 25);
}

void serialEvent(Serial p) {
  String data = p.readStringUntil('\n');
  if (data != null && data.contains(",")) {
    String[] values = split(trim(data), ",");
    if (values.length == 2) {
      temperature = float(values[0]);
      humidity    = float(values[1]);
    }
  }
}
The CSV parsing pattern — used in all projects
StepCodeWhy
1. Read linereadStringUntil('\n')Wait for a complete line
2. Check not nullif (data != null)Avoid errors on empty reads
3. Check formatdata.contains(",")Confirm it is CSV
4. Splitsplit(trim(data), ",")Divide into an array at each comma
5. Check lengthvalues.length == 2Ensure the right number of values
6. Convertfloat(values[0])Turn text into a number
InteractiveCSV parserType a line as Arduino would send it and watch each parsing step.
  1. 1readStringUntil('\n')"23.5,61.0"
  2. 2data != null
  3. 3data.contains(",")
  4. 4split(trim(data), ",")["23.5", "61.0"]
  5. 5values.length == 2length = 2
  6. 6float(values[0]), float(values[1])23.5, 61
Processing window
Temperature: 23.5 °C
Humidity: 61.0 %

Line accepted and displayed.

12Hands-on

Lab 4 — Sending Commands Back to Arduino

Communication works both ways. Processing can send a character to switch a pump (Project 5) or start a servo (Project 3). Here, mouse clicks and keys switch the built-in LED.

ReceiveCommands.inoArduino · C++
void setup() {
  Serial.begin(9600);
  pinMode(13, OUTPUT);              // built-in LED
}

void loop() {
  if (Serial.available() > 0) {
    char cmd = Serial.read();
    if (cmd == '1')      digitalWrite(13, HIGH);  // LED ON
    else if (cmd == '0') digitalWrite(13, LOW);   // LED OFF
  }
}
LedControl.pdeProcessing · Java
import processing.serial.*;

Serial myPort;
boolean ledOn = false;

void setup() {
  size(400, 220);
  myPort = new Serial(this, Serial.list()[0], 9600);
  textAlign(CENTER, CENTER);
}

void draw() {
  background(240);
  fill(30);
  textSize(18);
  text("Arduino LED Control", 200, 30);
  text("Click buttons or press 1 / 0 on keyboard", 200, 60);

  fill(ledOn ? color(0, 200, 0) : color(180));     // ON button
  rect(60, 100, 120, 50, 8);
  fill(255);
  text("ON", 120, 125);

  fill(!ledOn ? color(200, 50, 50) : color(180));  // OFF button
  rect(220, 100, 120, 50, 8);
  fill(255);
  text("OFF", 280, 125);

  fill(30);
  textSize(16);
  text("Status: LED is " + (ledOn ? "ON" : "OFF"), 200, 190);
}

void setLed(boolean on) {
  myPort.write(on ? '1' : '0');
  ledOn = on;
}

void mousePressed() {
  if (mouseX > 60  && mouseX < 180 && mouseY > 100 && mouseY < 150) setLed(true);
  if (mouseX > 220 && mouseX < 340 && mouseY > 100 && mouseY < 150) setLed(false);
}

void keyPressed() {
  if (key == '1') setLed(true);
  if (key == '0') setLed(false);
}
Level up
All five projects use the same core pattern: serialEvent() → parse → draw(). Master it here, apply it everywhere.
How this introduction connects to the five projects
ProjectSensorVisualizationKey technique
1 — DHT11Temperature & humidityTwo-value text + barsCSV parsing, 2 values
2 — LDRLight intensitySingle bar + colour changemap(), background colour
3 — HC-SR04Distance (sonar)Radar sweep displayTrigonometry, ellipse, line
4 — Ohm meterResistanceNumeric display + gaugenf(), arc(), text
5 — IrrigationSoil moistureStatus display + barThreshold logic, fill colour
13Cheat sheet

Arduino vs. Processing — Quick Reference

ConceptArduino IDEProcessing
Program entry pointsetup() + loop()setup() + draw()
Print to consoleSerial.println()println()
Read inputSerial.read()myPort.readStringUntil()
Delay / pausedelay(ms)delay(ms) — avoid in draw()
Variable typesint, float, char, boolint, float, String, boolean
Draw rectangle / text— (no screen)rect(), text()
Colour— (no screen)fill(), stroke()
Event handling—mousePressed(), keyPressed()
Import library#include <Lib.h>import library.*;
14From the original handbook

Student tasks

Basic
Display a single number from Arduino as text
Serial, int(), text()
Intermediate
Draw a coloured bar proportional to the sensor value
map(), rect(), fill()
Advanced
Parse two values (CSV) and display both with bars
split(), multiple visual elements
Challenge
Add ON/OFF buttons that send commands to Arduino
mousePressed(), Serial.write()
Challenge
Create a real-time graph of the last 100 readings
Arrays, shifting values, line()
15When it doesn’t work

Troubleshooting

ProblemLikely causeFix
Port not found / empty Serial.list()Arduino not connected or driver missingCheck USB; install the CH340 driver for clone boards.
Port busy / in useArduino Serial Monitor still openClose the Serial Monitor in the Arduino IDE first.
No data receivedWrong index in Serial.list()[0]Run printArray(Serial.list()) and choose the right index.
Garbage charactersBaud rate mismatchUse 9600 on both sides.
NullPointerExceptiondata is null (incomplete line)Always check if (data != null).
Wrong / garbage values on screenParsing non-numeric textValidate with data.matches("\\d+") or check length after split().
Sketch freezesHeavy work or delay() inside draw()Read serial in serialEvent(); never block draw().
Golden rule
Check the physical connections first, then the code. If nothing works, unplug, close both programs, reconnect and try again.
16New in this edition

Exercises

Basic · 2Intermediate · 2Advanced · 1Challenge · 1
F2.1BasicCalculate 10 min

map() by hand

Calculate each result without a computer, then check with the playground above.

a) map(512, 0, 1023, 0, 300)
b) map(25, 0, 50, 0, 255)
c) map(750, 1023, 300, 0, 100)

result = lo2 + (value − lo1) × (hi2 − lo2) / (hi1 − lo1). In (c) the input range is reversed — that’s fine.
a) 512 × 300 / 1023 ≈ 150.1 px · b) 25 × 255 / 50 = 127.5 · c) (750 − 1023) × 100 / (300 − 1023) = (−273)(100)/(−723) ≈ 37.8 %
F2.2BasicPredict 5 min

Where will it appear?

In a size(400, 300) window, describe where each shape appears: ellipse(200, 150, 40, 40), rect(0, 280, 400, 20), ellipse(width, 0, 60, 60).

The first circle is exactly in the centre. The rectangle is a 20 px strip along the bottom edge. The last circle is centred on the top-right corner, so only a quarter of it is visible.
F2.3IntermediateCode 15 min

Bouncing ball

No hardware: make a ball move across the window and bounce off all four walls. Change its colour every time it hits a wall.

Store position (x, y) and speed (dx, dy). Each frame add the speed. If x < 0 or x > width, flip the sign of dx.
Bounce.pdeProcessing · Java
float x = 100, y = 100, dx = 3, dy = 2;
color c = color(61, 245, 255);

void setup() {
  size(500, 300);
  noStroke();
}

void draw() {
  background(20);
  x += dx;
  y += dy;
  if (x < 15 || x > width - 15)  { dx = -dx; c = color(random(255), random(255), random(255)); }
  if (y < 15 || y > height - 15) { dy = -dy; c = color(random(255), random(255), random(255)); }
  fill(c);
  ellipse(x, y, 30, 30);
}
F2.4IntermediateDebug 10 min

Why is the screen blank?

Arduino is sending numbers, but this sketch shows nothing and sometimes crashes with a NullPointerException. Find the problems.

starterProcessing · Java
import processing.serial.*;
Serial myPort;
int value;

void setup() {
  size(400, 200);
  myPort = new Serial(this, Serial.list()[0], 115200);
}

void draw() {
  fill(0);
  text(value, 50, 100);
}

void serialEvent(Serial p) {
  value = int(trim(p.readStringUntil('\n')));
}
Compare with Lab 2: what speed does Arduino use? What happens to old text when there is no background()? What if the line is not complete yet?
1) Baud rate is 115200 but Arduino uses 9600. 2) No background() in draw(), so numbers pile on top of each other (and default fill is drawn on grey — text may be unreadable). 3) readStringUntil() can return null — check before trim(). Adding myPort.bufferUntil('\n') in setup() also helps.
F2.5AdvancedCode 25 min

Real-time line graph

Extend Lab 2: keep the last 100 received values in an array and draw them as a scrolling line graph across the window.

Shift every element one place left (vals[i] = vals[i+1]) and put the new value at the end. Use map() for both X (index → width) and Y (value → height, reversed!).
LiveGraph.pdeProcessing · Java
import processing.serial.*;

Serial myPort;
int[] vals = new int[100];

void setup() {
  size(600, 300);
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil('\n');
}

void draw() {
  background(15);
  stroke(61, 245, 255);
  strokeWeight(2);
  noFill();
  beginShape();
  for (int i = 0; i < vals.length; i++) {
    float x = map(i, 0, vals.length - 1, 20, width - 20);
    float y = map(vals[i], 0, 100, height - 20, 20);   // reversed: bigger = higher
    vertex(x, y);
  }
  endShape();
}

void serialEvent(Serial p) {
  String s = p.readStringUntil('\n');
  if (s == null) return;
  s = trim(s);
  if (!s.matches("\\d+")) return;
  for (int i = 0; i < vals.length - 1; i++) vals[i] = vals[i + 1];
  vals[vals.length - 1] = int(s);
}
F2.6ChallengeDesign 30 min

Three-value protocol

Design your own message format for three values (e.g. x,y,button from a joystick). Write the Arduino side with fake values from random(), and a Processing sketch that moves a circle with x/y and changes its colour when button = 1. Your parser must ignore malformed lines.

Check values.length == 3 and wrap each conversion. Test robustness by sending a broken line such as 12,, or hello.
ThreeValues.pde (receiver)Processing · Java
import processing.serial.*;
Serial myPort;
float px = 0, py = 0;
boolean pressed = false;

void setup() {
  size(500, 500);
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil('\n');
}

void draw() {
  background(20);
  fill(pressed ? color(198, 255, 61) : color(109, 74, 255));
  float x = map(px, 0, 1023, 25, width - 25);
  float y = map(py, 0, 1023, 25, height - 25);
  ellipse(x, y, 50, 50);
}

void serialEvent(Serial p) {
  String line = p.readStringUntil('\n');
  if (line == null) return;
  String[] v = split(trim(line), ",");
  if (v.length != 3) return;
  for (String s : v) if (!s.matches("\\d+")) return;   // reject malformed lines
  px = float(v[0]);
  py = float(v[1]);
  pressed = v[2].equals("1");
}
17Check yourself

Self-check quiz

Progress
0/6 answered · 0 correct
  1. Q01

    What is the Processing equivalent of Arduino’s loop()?

  2. Q02

    In Processing, where is the point (0, 0)?

  3. Q03

    Arduino uses Serial.begin(9600). What must Processing use?

  4. Q04

    What does map(50, 0, 100, 0, 400) return?

  5. Q05

    Arduino sends "24.5,60". What does split(trim(data), ",") give?

  6. Q06

    Why must the Serial Monitor be closed before running Processing?

18Beyond the classroom

Real world & extensions

Where this is used
industrial sensor dashboards and real-time monitoringscientific data visualization in research labsinteractive museum exhibits and installationscreative coding and generative digital artdata journalism and information designhealth monitoring and biofeedback devicesenvironmental monitoring (air quality, weather)game prototyping and interactive media
Extension ideas
  • +Real-time scrolling graph of the last 100 readings — arrays, shifting values (intermediate)
  • +Save sensor data to a CSV file with PrintWriter / saveStrings() (intermediate)
  • +Sound alarm on a threshold with the Minim library (advanced)
  • +Multi-sensor dashboard in one window (advanced)
  • +Web version with p5.js and the WebSerial API (challenge)
Cross-curricular connections
SubjectConnection
Computer ScienceEvents, data structures, string parsing — serialEvent(), arrays
MathematicsCoordinate systems, linear scaling, functions — map(), sin()
PhysicsInterpreting measurements — temperature bars, distance radar
Visual ArtsColour theory, composition, UI design
TechnologySystems thinking, hardware–software integration
19Think about it

Reflection & conclusion

?1

Explain the full journey of one sensor reading — from the physical world to a pixel on your screen — in your own words.

?2

Why is it a good idea to validate incoming data before using it?

?3

Where have you seen live data visualizations in everyday life (weather apps, fitness trackers, …)?

Conclusion

Processing is the visual bridge between the physical world and the screen. Once you understand how data flows from a sensor through Arduino’s serial port into Processing’s draw(), you can build any real-time visualization you can imagine. Serial setup, parsing, drawing with map(), and sending commands back to Arduino are a complete toolkit for every project that follows.