Wokwi is an online electronics simulator that runs in your web browser. It supports Arduino, ESP32, Raspberry Pi Pico, and other microcontrollers, allowing you to write, test, and debug code without physical hardware.
Why Wokwi?
- No Hardware Needed: Learn and prototype without buying components
- Browser-Based: Works on any device with a web browser
- Real-Time Simulation: See LED blinks, sensor readings instantly
- Interactive: Adjust sensors, press buttons during simulation
- Free: No cost for basic usage
- Shareable: Share projects via URL
Getting Started
Access Wokwi
- Go to https://wokwi.com/
- Click “Start Simulation”
- Choose Arduino Uno (or other board)
- Write code and click “Start Simulation”
Basic Blink Example
// Arduino blink program
void setup() {
pinMode(LED_BUILTIN, OUTPUT);
}
void loop() {
digitalWrite(LED_BUILTIN, HIGH);
delay(1000);
digitalWrite(LED_BUILTIN, LOW);
delay(1000);
}
Supported Hardware
Microcontrollers
- Arduino: Uno, Mega, Nano
- ESP32: WiFi-enabled microcontroller
- Raspberry Pi Pico: RP2040-based board
- ATtiny85: Small 8-pin microcontroller
Components
- LEDs, buttons, switches
- Sensors (temperature, distance, light)
- Displays (LCD, 7-segment, OLED)
- Motors and servos
- Potentiometers and resistors
Arduino Programming in Wokwi
Digital Output (LED)
void setup() {
pinMode(13, OUTPUT); // Set pin 13 as output
}
void loop() {
digitalWrite(13, HIGH); // Turn LED on
delay(500);
digitalWrite(13, LOW); // Turn LED off
delay(500);
}
Digital Input (Button)
const int buttonPin = 2;
const int ledPin = 13;
void setup() {
pinMode(buttonPin, INPUT_PULLUP);
pinMode(ledPin, OUTPUT);
}
void loop() {
int buttonState = digitalRead(buttonPin);
if (buttonState == LOW) { // Button pressed
digitalWrite(ledPin, HIGH);
} else {
digitalWrite(ledPin, LOW);
}
}
Analog Input (Potentiometer)
void setup() {
Serial.begin(9600);
}
void loop() {
int sensorValue = analogRead(A0); // Read analog pin
Serial.println(sensorValue); // Print value
delay(100);
}
PWM Output (LED Brightness)
const int ledPin = 9; // PWM-capable pin
void setup() {
pinMode(ledPin, OUTPUT);
}
void loop() {
// Fade in
for (int brightness = 0; brightness <= 255; brightness++) {
analogWrite(ledPin, brightness);
delay(10);
}
// Fade out
for (int brightness = 255; brightness >= 0; brightness--) {
analogWrite(ledPin, brightness);
delay(10);
}
}
Serial Monitor
Printing to Serial
void setup() {
Serial.begin(9600); // Initialize serial at 9600 baud
Serial.println("Arduino started!");
}
void loop() {
int value = analogRead(A0);
Serial.print("Sensor value: ");
Serial.println(value);
delay(1000);
}
View output in Wokwi’s Serial Monitor (bottom of screen).
Adding Components
Using diagram.json
Wokwi projects include a diagram.json file that defines the circuit:
{
"version": 1,
"author": "Your Name",
"editor": "wokwi",
"parts": [
{ "type": "wokwi-arduino-uno", "id": "uno" },
{
"type": "wokwi-led",
"id": "led1",
"attrs": { "color": "red" }
},
{
"type": "wokwi-resistor",
"id": "r1",
"attrs": { "value": "220" }
}
],
"connections": [
[ "led1:A", "uno:13", "green", [] ],
[ "led1:C", "r1:1", "green", [] ],
[ "r1:2", "uno:GND", "black", [] ]
]
}
Sensors and Modules
Temperature Sensor (DHT22)
#include <DHT.h>
#define DHTPIN 2
#define DHTTYPE DHT22
DHT dht(DHTPIN, DHTTYPE);
void setup() {
Serial.begin(9600);
dht.begin();
}
void loop() {
float temp = dht.readTemperature();
float humidity = dht.readHumidity();
Serial.print("Temperature: ");
Serial.print(temp);
Serial.print("°C, Humidity: ");
Serial.print(humidity);
Serial.println("%");
delay(2000);
}
Ultrasonic Distance Sensor
const int trigPin = 9;
const int echoPin = 10;
void setup() {
Serial.begin(9600);
pinMode(trigPin, OUTPUT);
pinMode(echoPin, INPUT);
}
void loop() {
// Send pulse
digitalWrite(trigPin, LOW);
delayMicroseconds(2);
digitalWrite(trigPin, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin, LOW);
// Read echo
long duration = pulseIn(echoPin, HIGH);
float distance = duration * 0.034 / 2; // cm
Serial.print("Distance: ");
Serial.print(distance);
Serial.println(" cm");
delay(500);
}
LCD Display
#include <LiquidCrystal.h>
// LiquidCrystal lcd(RS, E, D4, D5, D6, D7);
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
void setup() {
lcd.begin(16, 2); // 16x2 LCD
lcd.print("Hello, Wokwi!");
}
void loop() {
lcd.setCursor(0, 1); // Column 0, Row 1
lcd.print("Time: ");
lcd.print(millis() / 1000);
delay(1000);
}
Teaching with Wokwi
Interactive Demonstrations
- Share project link with students
- Students can modify and re-run instantly
- No hardware setup or troubleshooting
- Works on any device (computer, tablet)
Progressive Complexity
// Step 1: Basic blink
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
// Step 2: Add variable
int delayTime = 1000;
digitalWrite(13, HIGH);
delay(delayTime);
// Step 3: Add input
int sensorValue = analogRead(A0);
int delayTime = map(sensorValue, 0, 1023, 100, 2000);
// Step 4: Add function
void blinkLED(int pin, int duration) {
digitalWrite(pin, HIGH);
delay(duration);
digitalWrite(pin, LOW);
delay(duration);
}
Practical Applications
Experimental Trigger System
// Generate TTL trigger for experiments
const int triggerPin = 8;
void setup() {
pinMode(triggerPin, OUTPUT);
Serial.begin(9600);
}
void sendTrigger() {
digitalWrite(triggerPin, HIGH);
delayMicroseconds(100); // 100µs pulse
digitalWrite(triggerPin, LOW);
}
void loop() {
if (Serial.available()) {
char command = Serial.read();
if (command == 'T') {
sendTrigger();
Serial.println("Trigger sent");
}
}
}
Behavioral Task Controller
// Simple reaction time task
const int stimLED = 13;
const int responseButton = 2;
void setup() {
pinMode(stimLED, OUTPUT);
pinMode(responseButton, INPUT_PULLUP);
Serial.begin(9600);
randomSeed(analogRead(0));
}
void loop() {
// Random delay
int iti = random(1000, 3000);
delay(iti);
// Stimulus
digitalWrite(stimLED, HIGH);
unsigned long startTime = millis();
// Wait for response
while (digitalRead(responseButton) == HIGH) {
// Waiting...
}
unsigned long rt = millis() - startTime;
digitalWrite(stimLED, LOW);
Serial.print("RT: ");
Serial.print(rt);
Serial.println(" ms");
delay(2000); // ITI
}
Limitations
- Speed: Slower than real hardware
- Timing: Not precise enough for critical timing
- Components: Limited component library
- No Analog Output: Can’t simulate true DAC
- Internet Required: Needs web browser
Alternatives
- TinkerCAD Circuits: Autodesk’s simulator
- Arduino IDE: For real hardware
- SimulIDE: Desktop simulator
Best Practices
- Start simple, add complexity gradually
- Use Serial.println() for debugging
- Test timing with delays first
- Comment your code
- Share projects for collaboration
- Validate on real hardware before deployment
Integration with Jupyter
You can embed Wokwi in Jupyter notebooks:
from IPython.display import IFrame
# Embed Wokwi project
IFrame('https://wokwi.com/projects/YOUR_PROJECT_ID', width=800, height=600)
Resources
- Wokwi: https://wokwi.com/
- Documentation: https://docs.wokwi.com/
- Examples: https://wokwi.com/projects
- Arduino Reference: https://www.arduino.cc/reference/
Summary
Wokwi is perfect for:
- Learning: No hardware required
- Prototyping: Test ideas quickly
- Teaching: Share interactive examples
- Validation: Debug before building
It’s an excellent tool for learning embedded systems and Arduino programming without initial hardware investment.