LED Blink Workshops & Interactive Multi-Pattern Chaser Sequencer
From the essential Hello World LED blink to advanced Knight Rider scanning chasers, master C++ array iterations, bit-shifting, and non-blocking multitasking using millis().
1. Aim of the Project
Project Objective
The aim of this workshop is to guide students through the progressive fundamentals of digital electronics: wiring an array of 5 LEDs, controlling discrete GPIO pin states with loop arrays, switching between 4 animation sequences with a push button, and eliminating blocking delay() calls using millisecond timers.
2. Interactive 3D Assembly & Circuit Wiring Model
Rotate the 3D model 360 degrees, zoom in/out, disassemble/explode parts to inspect individual hardware layers, toggle realistic circuit wires, and click any component to inspect its engineering specifications.
3. Laboratory Video Masterclass Tutorial
Step-by-step video walkthrough covering breadboard circuit assembly, wiring verification, and testing. Enrolled students and instructors can access video streaming below.
2. Learning Outcomes
C++ Array Traversal
Program dynamic LED arrays using for loops and pointer indices instead of duplicating repetitive code lines.
Non-Blocking Multitasking
Master the fundamental Arduino programming paradigm: polling timer intervals without pausing the processor.
3. Required Components
| Component Name | Quantity | Specification | Interface |
|---|---|---|---|
| Arduino Uno | 1 | ATmega328P Board | USB / 5V |
| 5mm LEDs (Assorted Colors) | 5 | Red, Yellow, Green, Blue, White | Pins D2 through D6 |
| 220 Ohm Resistors | 5 | Current limiting resistors | Passive |
| Push Button Switch | 1 | Pattern toggle button | Pin D7 (INPUT_PULLUP) |
4. Complete Arduino Source Code
/*
* Project: Interactive Multi-Pattern LED Sequencer
* Author: ElectronLab STEM Curriculum
*/
const int ledPins[] = {2, 3, 4, 5, 6};
const int numLeds = 5;
const int BUTTON_PIN = 7;
int currentPattern = 0;
int lastButtonState = HIGH;
unsigned long lastDebounceTime = 0;
unsigned long lastAnimationTime = 0;
int animationStep = 0;
void setup() {
for (int i = 0; i < numLeds; i++) {
pinMode(ledPins[i], OUTPUT);
}
pinMode(BUTTON_PIN, INPUT_PULLUP);
}
void loop() {
// Read button with debounce
int reading = digitalRead(BUTTON_PIN);
if (reading != lastButtonState && (millis() - lastDebounceTime) > 50) {
if (reading == LOW) {
currentPattern = (currentPattern + 1) % 3;
clearLeds();
animationStep = 0;
}
lastDebounceTime = millis();
}
lastButtonState = reading;
// Execute Non-Blocking Animation
if (millis() - lastAnimationTime >= 100) {
lastAnimationTime = millis();
if (currentPattern == 0) {
// Pattern 1: Knight Rider Scanning
clearLeds();
digitalWrite(ledPins[animationStep], HIGH);
animationStep = (animationStep + 1) % numLeds;
} else if (currentPattern == 1) {
// Pattern 2: Alternating Strobe
for (int i = 0; i < numLeds; i++) {
digitalWrite(ledPins[i], (i % 2 == animationStep % 2) ? HIGH : LOW);
}
animationStep = (animationStep + 1) % 2;
} else if (currentPattern == 2) {
// Pattern 3: All Blink
for (int i = 0; i < numLeds; i++) {
digitalWrite(ledPins[i], (animationStep == 0) ? HIGH : LOW);
}
animationStep = (animationStep + 1) % 2;
}
}
}
void clearLeds() {
for (int i = 0; i < numLeds; i++) {
digitalWrite(ledPins[i], LOW);
}
}
5. Working Principle
An internal 32-bit hardware timer runs automatically inside the ATmega328P microcontroller, tracking milliseconds elapsed since power-up. By comparing millis() - lastTime >= interval, the Arduino creates multi-threaded style LED animations while simultaneously reading user button presses instantaneously with zero latency.
6. Troubleshooting Guide
Button Skips Patterns Multiple Times
Mechanical button contacts bounce physically when pressed. The software debounce check (millis() - lastDebounceTime > 50) prevents false triggering.