AJ-SR04M not working with ESPHome

Hello all,
I have the following problem with the sensor mentioned above. I have hooked it to an ESP32-S3, trigger to pin 21, echo to pin 47. When trying to measure the distance I have the following error message:
“Distance measurement timed out”. I have tried all the suggestions, increasing the distance, adjusting the timeout, nothing works. I have also tried other pins with the same result.
I power the sensor from a 3.3 volts power supply, the same used for ESP32-S3 to run.
The code I’m using in yaml file is the following:

  - platform: ultrasonic
    name: "Water in Tank"
    id: water_volume
    echo_pin: GPIO47
    trigger_pin:
      number: GPIO21
      inverted: True
    update_interval: 30s
    accuracy_decimals: 0
    timeout: '20m'
    # pulse_time: 
    #   microseconds: 30
    unit_of_measurement: "l"
    filters:
      - lambda: return ((0.96 - x)* 0.6 * 0.6 * 1000);
      # - lambda: return x;
      - filter_out: nan

The sensor itself is functional, I have tried it with Arduino code (see below) and it works like a charm. Only when trying to hook it up with ESPHome, it stops working.

Please help me with this, in case you have suggestions. Really appreciate your help and support.

const int trigPin = GPIO21;
const int echoPin = GPIO47;

//define sound velocity in cm/uS
#define SOUND_VELOCITY 0.034
#define CM_TO_INCH 0.393701

long duration;
float distanceCm;
float distanceInch;

void setup() {
  Serial.begin(115200); // Starts the serial communication
  pinMode(trigPin, OUTPUT); // Sets the trigPin as an Output
  pinMode(echoPin, INPUT); // Sets the echoPin as an Input
}

void loop() {
  // Clears the trigPin
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  // Sets the trigPin on HIGH state for 10 micro seconds
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  
  // Reads the echoPin, returns the sound wave travel time in microseconds
  duration = pulseIn(echoPin, HIGH);
  
  // Calculate the distance
  distanceCm = duration * SOUND_VELOCITY/2;
  
  // Convert to inches
  distanceInch = distanceCm * CM_TO_INCH;
  
  // Prints the distance on the Serial Monitor
  Serial.print("Distance (cm): ");
  Serial.println(distanceCm);
  Serial.print("Distance (inch): ");
  Serial.println(distanceInch);
  
  delay(1000);
}

Did you try with
JSN-SR04T Waterproof Ultrasonic Range Finder — ESPHome

Hi Karosm,
thank you for your reply. I haven’t, until now, but now I did. I added the uart as well, but I do not know what port should I specify in the uart descriptor and without it I cannot compile. Any idea how can I get the port?

Thank you once again.

Default uart1 pins for your esp are 18rx and 17tx.
But afaik you need to physically change mode-resistor on your sensor to put it in UART mode.
I would just try it with default settings without uart first

I did that. I have soldered 120k ohm resistor, before writing on the forum. Didn’t work.
I have connected then the sensor to the pins GIPO43 and GPIO44 (the serial port from ESP). From the serial of the esp 32-s3. Now, I have managed to have the sensor LED blinking with high frequency, I do not have the “Distance measurement timed out” error but the distance it measures remains constant to 0.018m. :frowning:
I will try to connect it to the pins you’ve mention but I do not think it is from there…

If so, why you posted both esphome- and arduino-code that uses trigger-echo mode? That doesn’t work with 120ohm on board…

Default uart0 is used by logger. Did you disable it?

Yes, I have disabled the logger. I do not understand what do you mean by 120k resistor, though. Should I choose another value (47k) instead?

You wrote that you soldered that.
It’s setting the sensor in continuous uart mode.

So what you get with this?

uart:
  tx_pin: GPIO17
  rx_pin: GPIO18
  baud_rate: 9600

sensor:
  - platform: "jsn_sr04t"
    name: "Distance"
    model: aj_sr04m

There is no answer from the sensor now. At least, when it was connected to the default UART, when the LED was flashing fast, now, there is no blinking. :frowning: There is no output in the console either.

my code looks like that, now:

uart:
  tx_pin: GPIO17
  rx_pin: GPIO18
  baud_rate: 9600


sensor:
  - platform: "jsn_sr04t"
    name: "Distance"
    model: aj_sr04m
    update_interval: 2s

The console output looks like:

[C][uart.arduino_esp32:151]: UART Bus 0:
[21:57:39][C][uart.arduino_esp32:152]:   TX Pin: GPIO17
[21:57:39][C][uart.arduino_esp32:153]:   RX Pin: GPIO18
[21:57:39][C][uart.arduino_esp32:155]:   RX Buffer Size: 256
[21:57:39][C][uart.arduino_esp32:157]:   Baud Rate: 9600 baud
[21:57:39][C][uart.arduino_esp32:158]:   Data Bits: 8
[21:57:39][C][uart.arduino_esp32:159]:   Parity: NONE
[21:57:39][C][uart.arduino_esp32:160]:   Stop bits: 1
[21:57:39][C][jsn_sr04t.sensor:060]: JST_SR04T Sensor 'Distance'
[21:57:39][C][jsn_sr04t.sensor:060]:   State Class: 'measurement'
[21:57:39][C][jsn_sr04t.sensor:060]:   Unit of Measurement: 'm'
[21:57:39][C][jsn_sr04t.sensor:060]:   Accuracy Decimals: 3
[21:57:39][C][jsn_sr04t.sensor:060]:   Icon: 'mdi:arrow-expand-vertical'
[21:57:39][C][jsn_sr04t.sensor:066]:   sensor model: aj_sr04m
[21:57:39][C][jsn_sr04t.sensor:069]:   Update Interval: 2.0s

And the connections on my board like in the picture.

I have uploaded another picture where you can see the 120k resistor. Don’t mind the connector, it has 5 pins because I have reused it, the green cable is not connected.

Uart0 is hardwired to 43/44, so if you want to try with uart1 on 17/18, you need to enable serial logger. I see from your log that Esphome tries to assign 17/18 to Uart0.

I’ve managed to fix it. I had to comment the
model: aj_sr04m
line and now it started to work like a charm.
Hey, I THANK YOU big time for your help and support, really appreciate, you made my night!!!
Thank you, wherever you are in this world, you did something amazing for today, helping me with this topic.

Is your sensor labeled AJ on the pcb?

I have no idea why it allocates UART0 to pins 17 and 18. How can I enable serial logger? Any idea how can I change from UART0 to UART1?

Yes, my sensor is labeled AJ on the board. Exactly like in your picture. Why?

You remove the line that disables it:

logger:
 # baud_rate: 0

that should occupy uart0 for logger and automatically assign the pins on uart component to uart1.

Because you wrote that commenting the model: aj_sr04m made it work.
So for Esphome it’s now jsn_sr04t (default).

Oh, I have misunderstood you with the serial logger. Mine was enabled most of the time, I have disabled it when connecting the sensor on UART0.

logger:
  level: ERROR

If I may, I still have one question. Regardless the

update_interval:
    - seconds: 10

or

update_interval: 10s

the sensor updates the values very fast. I have tried both of them, no result. Any idea how can I set to read the values every 10 seconds, let’s say?

Thank you.

No how, it’s in continuous mode. But you could use filters to output some averaging value, it would move fluctuation and give you better readings as well.

filters:
    - sliding_window_moving_average:
        window_size: 15
        send_every: 15

Or you change the resistor and put it in triggered uart mode.
The problem is that, I don’t understand if your board really is AJ since Esphome thinks it’s JSN.

Yeah, the manufacturer swears on blue it is AJ (see the picture…), but, who knows…

Changing the resistor to 47k will put the board on triggered UART mode, right?
Anyway I am not the only one having this issue I have found here someone who points to the same comment on removing the model from the yaml to make it work.

I might try tomorrow to see if it works on triggered UART mode. For now I am happy it works like it does.
Thank you once again.

Chinese manufacturers might use any pcb that they find in stock…
Did you try with filtering? You can set higher numbers to have more averaging and longer update interval. I don’t know if they have some max though.

You’re right. Bought the sensor from the mighty Aliexpress. :smiley:
I did try filtering, I think I will let it as is. Filtering gives me flexibility.

Thank you once again.