The TCRT5000 has an IR LED and a phototransistor side by side, looking down at a surface. White reflects the IR back and black absorbs it, which makes it the standard sensor for line-following robots. It can also count the marks on a spinning disc.
On the Uno it runs from 5V. The digital output DO goes to D2 and the analog output AO to A0. DO gives a clean black/white answer at the threshold you set with the pot. AO gives the reflectance as 0–1023, which is better when the robot should steer smoothly.
The sketch prints both, so you can set the pot and see the analog numbers for your own track surface.
Wiring
| Arduino Uno R3 | TCRT5000 IR reflective sensor module | Wire | Notes |
|---|---|---|---|
| 5V | VCC | red | |
| GND | GND | black | |
| D2 | DO | yellow | Comparator output — threshold set by the pot. |
| A0 | AO | orange | Analog reflectance, 4-pin modules only. |
3.3–5 V part, 5 V board. Outputs swing to VCC. Power it from 3.3 V on ESP32/Pico, 5 V on Uno.
Board quirks
- The sensor works at 2–10 mm above the surface. On a robot, mount it low; at 2 cm it can no longer tell black from white.
- On most modules DO goes LOW (LED on) over white and HIGH over black. Check yours with paper and black electrical tape — some boards are the other way round.
- Use AO when you need more than on/off. Two or more sensors read with
analogRead()let a robot steer smoothly (PID) instead of zig-zagging. - A line follower needs one sensor per input: the Uno’s six analog pins A0–A5 fit up to six AO outputs, but A4/A5 are then unavailable for I2C.
Code
// TCRT5000 reflective IR sensor module on an Arduino Uno R3.
// VCC → 5V, GND → GND, DO → D2, AO → A0.
// Hold it 2–10 mm above the surface. Lower AO = more reflection (white).
const uint8_t DO_PIN = 2, AO_PIN = A0;
void setup() {
pinMode(DO_PIN, INPUT);
Serial.begin(9600);
Serial.println(F("TCRT5000 - move it over white paper and black tape"));
}
void loop() {
int ao = analogRead(AO_PIN);
bool doLow = digitalRead(DO_PIN) == LOW; // on most boards LOW = reflective (white)
Serial.print(F("AO "));
Serial.print(ao);
Serial.print(F(" DO "));
Serial.print(doLow ? F("LOW ") : F("HIGH"));
Serial.println(doLow ? F(" -> white / reflective") : F(" -> black line / nothing"));
delay(200);
}// TCRT5000 reflective IR sensor module on an Arduino Uno R3.
// VCC → 5V, GND → GND, DO → D2, AO → A0.
// Hold it 2–10 mm above the surface. Lower AO = more reflection (white).
const uint8_t DO_PIN = 2, AO_PIN = A0;
void setup() {
pinMode(DO_PIN, INPUT);
Serial.begin(9600);
Serial.println(F("TCRT5000 - move it over white paper and black tape"));
}
void loop() {
int ao = analogRead(AO_PIN);
bool doLow = digitalRead(DO_PIN) == LOW; // on most boards LOW = reflective (white)
Serial.print(F("AO "));
Serial.print(ao);
Serial.print(F(" DO "));
Serial.print(doLow ? F("LOW ") : F("HIGH"));
Serial.println(doLow ? F(" -> white / reflective") : F(" -> black line / nothing"));
delay(200);
}Expected serial output
TCRT5000 - move it over white paper and black tape
AO 87 DO LOW -> white / reflective
AO 812 DO HIGH -> black line / nothingTCRT5000 - move it over white paper and black tape AO 87 DO LOW -> white / reflective AO 812 DO HIGH -> black line / nothing
Common errors
Always reads black (DO HIGH)
Too far from the surface, or the pot set too low. Hold it 5 mm above white paper and turn the pot until the LED lights.
Works on paper, fails on the floor
Glossy tiles reflect like white and matte dark floors absorb. Run the track on a matte white chart sheet with black electrical tape.
Readings change in sunlight
Ambient IR. Shield the sensor with a small skirt of black tape around it.