Comparing Accuracy of ToF Sensor (VL53L0X) vs Ultrasonic Sensor (HC-SR04) using I2C LCD

Project Objective

In this project, we compare distance measurement accuracy of:

  • Time of Flight (ToF) sensor – VL53L0X
  • Ultrasonic sensor – HC-SR04

The measured distances from both sensors are displayed side-by-side on a 16×2 I2C LCD, allowing easy real-time comparison using a physical scale.


Components Required

ComponentQuantity
Arduino UNO1
VL53L0X ToF sensor1
HC-SR04 Ultrasonic sensor1
16×2 I2C LCD1
Breadboard1
Jumper wiresAs required
USB cable1

Pin Connections (Very Important)

VL53L0X (I2C)

VL53L0X PinArduino UNO
VIN5V
GNDGND
SDAA4
SCLA5
XSHUTNot connected
GPIO1Not connected

HC-SR04 Ultrasonic Sensor

HC-SR04 PinArduino UNO
VCC5V
GNDGND
TRIGD8
ECHOD9

I2C LCD (16×2)

LCD PinArduino UNO
VCC5V
GNDGND
SDAA4
SCLA5

Note:

  • LCD address is usually 0x27 or 0x3F
  • 0x3Fx is a hex digit, NOT multiplication

Required Libraries

Install from Arduino Library Manager:

  • Adafruit VL53L0X
  • LiquidCrystal I2C

Arduino Code:

#include <Wire.h>
#include <Adafruit_VL53L0X.h>
#include <LiquidCrystal_I2C.h>

// LCD address: change to 0x3F if needed
LiquidCrystal_I2C lcd(0x27, 16, 2);

// VL53L0X object
Adafruit_VL53L0X lox;

// Ultrasonic pins
#define TRIG_PIN 8
#define ECHO_PIN 9

long duration;
float distanceUS = 0;
float distanceTOF = 0;

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

  pinMode(TRIG_PIN, OUTPUT);
  pinMode(ECHO_PIN, INPUT);

  // LCD init
  lcd.init();
  lcd.backlight();
  lcd.setCursor(0, 0);
  lcd.print("Sensor Compare");
  lcd.setCursor(0, 1);
  lcd.print("Initializing");

  // ToF init
  if (!lox.begin()) {
    lcd.clear();
    lcd.print("VL53L0X FAIL");
    while (1);
  }

  delay(2000);
  lcd.clear();
}

float readUltrasonicCM() {
  digitalWrite(TRIG_PIN, LOW);
  delayMicroseconds(2);
  digitalWrite(TRIG_PIN, HIGH);
  delayMicroseconds(10);
  digitalWrite(TRIG_PIN, LOW);

  duration = pulseIn(ECHO_PIN, HIGH, 30000); // timeout 30ms

  if (duration == 0) return -1;  // invalid

  return (duration * 0.0343) / 2.0;
}

float readTOFCM() {
  VL53L0X_RangingMeasurementData_t measure;
  lox.rangingTest(&measure, false);

  if (measure.RangeStatus != 4) {
    return measure.RangeMilliMeter / 10.0;
  }
  return -1;
}

void loop() {
  distanceTOF = readTOFCM();
  distanceUS  = readUltrasonicCM();

  lcd.setCursor(0, 0);
  lcd.print("ToF: ");
  if (distanceTOF > 0) {
    lcd.print(distanceTOF, 1);
    lcd.print(" cm ");
  } else {
    lcd.print("Invalid   ");
  }

  lcd.setCursor(0, 1);
  lcd.print("US : ");
  if (distanceUS > 0) {
    lcd.print(distanceUS, 1);
    lcd.print(" cm ");
  } else {
    lcd.print("Invalid   ");
  }

  Serial.print("ToF: ");
  Serial.print(distanceTOF);
  Serial.print(" cm | US: ");
  Serial.print(distanceUS);
  Serial.println(" cm");

  delay(500);
}

VL53L0X (ToF Sensor)

✔ Uses laser time-of-flight
✔ High precision at short distance
✔ Less affected by object color
❌ Can fluctuate with ambient light
❌ Sensitive to reflective surfaces

HC-SR04 (Ultrasonic)

✔ Works well for medium distance
✔ Not affected by light
✔ Cheap and widely used
❌ Affected by angle and soft objects
❌ Less accurate at close range

Best Practices (Important)

✔ Keep sensor steady
✔ Use flat object (book / scale)
✔ Avoid glass or shiny metal
✔ Maintain 2–200 cm range