How the 40kHz Waterproof Ultrasonic Sensor Works

At the core of sensors like the JSN-SR04T V2.0 or the industrial A02YYUW is a sealed piezoelectric transducer that vibrates at exactly 40kHz when driven by an internal oscillator. When the microcontroller sends a brief trigger signal, the transducer emits an eight-cycle burst of ultrasonic sound waves into the air. These waves travel outward in a roughly 15-degree cone, strike a solid target, and reflect back to the same transducer, which then acts as a microphone to detect the returning echo. The sensor's internal timing circuit measures the exact Time of Flight (ToF) between the emission and the reception of the echo.

Crucially, the output of a standard 40kHz waterproof ultrasonic sensor is a digital pulse width, not an analog voltage or current. The microcontroller pulls the Trigger pin HIGH for 10 microseconds, and in response, the sensor pulls its Echo pin HIGH for the exact duration it takes the sound to make the round trip. By measuring how long the Echo pin stays HIGH in microseconds, you can calculate the physical distance. There is no analog scaling or voltage division happening inside the sensor itself; it is purely a digital time-delay signal.

Wiring Pinout and 3.3V Logic Protection

The most common hobbyist variant, the JSN-SR04T V2.0, operates strictly at 5V logic and requires a 5V power supply. If you are using an Arduino Uno or Mega, you can wire it directly. However, if you are interfacing with a 3.3V microcontroller like the ESP32, Raspberry Pi Pico, or ESP8266, feeding the 5V Echo pin directly into a 3.3V GPIO will eventually degrade or destroy the silicon.

JSN-SR04T V2.0 Pinout and Supply Specifications
Pin Label Function Voltage Level ESP32 / 3.3V Connection Strategy
VCC Power Supply 4.8V to 5.5V DC Connect to 5V pin (VIN or 5V out)
Trig (Trigger) Start Measurement Input (Accepts 3.3V or 5V) Connect directly to any digital GPIO
Echo Return Time Signal Output (Pushes 5V HIGH) Must use voltage divider to step down to 3.3V
GND Common Ground 0V Connect to MCU GND
⚠️ Callout: The ESP32 Voltage Divider
To safely read the 5V Echo pin on an ESP32, build a simple voltage divider. Connect a 1kΩ resistor in series between the sensor's Echo pin and the ESP32 GPIO. Then, connect a 2kΩ resistor from that same GPIO to GND. This drops the 5V signal to a safe ~3.33V. Do not rely on the ESP32's internal clamping diodes to handle continuous 5V overvoltage; they are not rated for this sustained current.

Raw-to-Unit Math: Microseconds to Centimeters

To convert the raw microsecond reading from the pulseIn() function into a usable physical unit, you must account for the speed of sound and the fact that the sound wave travels to the target and back. According to standard acoustic physics, the speed of sound in dry air at 20°C is approximately 343 meters per second, which translates to 0.0343 centimeters per microsecond (Engineering Toolbox).

The raw-to-unit formula is:

Distance (cm) = (Pulse_Width_µs × 0.0343) / 2

Here is the complete, compilable Arduino/ESP32 C++ code to read the sensor, apply the math, and include basic temperature compensation for high-accuracy setups.

// Pin Definitions
const int trigPin = 5;  // GPIO 5
const int echoPin = 18; // GPIO 18 (via voltage divider)

// Variables
long duration;
float distanceCm;
float temperatureC = 20.0; // Update with a real temp sensor like DS18B20 if possible

void setup() {
  Serial.begin(115200);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
}

void loop() {
  // 1. Clear the trigger pin
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  
  // 2. Send 10us pulse to trigger
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  
  // 3. Read the echo pin (timeout set to 30ms to prevent blocking)
  // See: https://docs.arduino.cc/language-reference/en/functions/advanced-io/pulseIn/
  duration = pulseIn(echoPin, HIGH, 30000); 
  
  if (duration == 0) {
    Serial.println("Error: Timeout / No echo received.");
  } else {
    // Calculate speed of sound based on temperature: v = 331.4 + 0.6 * T
    float speedOfSoundCmPerUs = (331.4 + 0.6 * temperatureC) / 10000.0;
    
    // Calculate one-way distance
    distanceCm = (duration * speedOfSoundCmPerUs) / 2.0;
    
    Serial.print("Distance: ");
    Serial.print(distanceCm);
    Serial.println(" cm");
  }
  
  delay(100); // 10Hz sampling rate max for this sensor
}

Real-World Interference and the "Blind Spot" Problem

When deploying a 40kHz waterproof ultrasonic sensor in the field, the math is only half the battle. The physical housing of waterproof sensors introduces a massive acoustic quirk: the blind spot. Because the transducer is mounted behind a waterproof membrane and inside a threaded housing, the initial 40kHz burst causes the housing itself to vibrate (acoustic ring-down). The sensor's internal comparator blanks out the receiver for roughly 20 to 25 milliseconds to wait for this ringing to stop. Consequently, these sensors cannot detect any object closer than 20cm to 25cm. If your target is inside this blind spot, the sensor will either output 0 or falsely report the maximum distance (usually 400cm).

Beyond the blind spot, you must engineer around three common interference sources:

  • Cross-talk: If you mount multiple 40kHz sensors facing the same body of water or tank, Sensor A will trigger off the echo from Sensor B. You must poll them sequentially in software with at least a 50ms delay between readings, or physically baffle them with acoustic foam.
  • Surface Angle and Absorption: Ultrasonic waves reflect specularly (like light off a mirror). If the water surface is agitated by wind, or if the target is angled greater than 15 degrees off-axis, the echo will scatter away from the transducer. Similarly, soft materials like acoustic foam or thick dust layers will absorb the 40kHz energy, returning a timeout.
  • Thermal Gradients: In outdoor tanks, the air temperature near the water surface might be 10°C while the air near the sensor lid is 30°C. This gradient bends the acoustic wave (refraction), slightly altering the ToF. For millimeter-precision tank leveling, you must mount a DS18B20 temperature probe near the transducer face to dynamically adjust the speedOfSoundCmPerUs variable in your code.
💡 Pro-Tip: Avoid the V1.0 Hardware Bug
If you are buying the JSN-SR04T, ensure the PCB is explicitly marked V2.0. The older V1.0 revision lacked a hardware timeout on the Echo pin. If the sound wave scattered and no echo returned, the V1.0 Echo pin would stay HIGH indefinitely, hanging the pulseIn() function and freezing your entire microcontroller loop. V2.0 forces the pin LOW after roughly 30ms regardless of echo status.

Frequently Asked Questions

Can a 40khz waterproof ultrasonic sensor measure water level inside a sealed plastic tank?

No, you cannot mount the sensor on the outside of a plastic tank to read through the wall. Unlike low-frequency ultrasound used in medical imaging, 40kHz airborne ultrasonic waves cannot penetrate solid barriers; the acoustic impedance mismatch between air and plastic causes nearly 100% of the wave to reflect off the outside of the tank wall. To measure the water level, you must drill a hole in the top of the tank, mount the sensor using its provided threaded nut so the transducer face is exposed to the air gap inside, and seal it with a rubber O-ring or silicone.

Why is my 40khz waterproof ultrasonic sensor reading stuck at 0 or max distance?

If your serial monitor reads exactly 0.00 cm or jumps to the sensor's maximum limit (usually 400cm or 450cm), your target is likely inside the acoustic blind spot (closer than 25cm). The sensor is still emitting the burst, but the internal receiver is intentionally deafened by the ring-down of the waterproof housing. Move the sensor further back from the water surface. If the reading is stuck at 0 continuously regardless of distance, check your wiring: a missing common ground between the sensor's 5V supply and the ESP32's 3.3V logic will cause the Echo pin to float, resulting in zero-duration pulse readings.

How do I wire a 5V 40khz waterproof ultrasonic sensor to a 3.3V ESP32 without frying it?

You must step down the 5V Echo output to a 3.3V logic level before it reaches the ESP32 GPIO. The most reliable method is a passive resistor voltage divider. Solder a 1kΩ resistor in line with the Echo wire, and a 2kΩ resistor from the ESP32 side of that 1kΩ resistor down to GND. This creates a 2/3 voltage divider, safely dropping the 5V HIGH signal to ~3.33V. The Trigger pin, however, can be wired directly from the ESP32 to the sensor, as the JSN-SR04T V2.0 reliably recognizes a 3.3V HIGH signal as a valid trigger.