OLED print ON/OFF relay state

Hello,
I need some help to make the code works, the idea is simple, I have a esp8266 D1 with a relay which have to start something, and on my OLED display I will like to see the status, like “RELAY ON” or OFF
I have the following yaml config and its not working, its printig OFF and stay OFF

esphome:
  name: termostat-etaj

esp8266:
  board: d1_mini

wifi:
  ssid: "HomeSweetHome"
  password: "******"
  fast_connect: true
  manual_ip:
    static_ip: 192.168.1.30
    gateway: 192.168.1.1
    subnet: 255.255.255.0
    dns1: 192.168.1.1


# Enable logging
logger:

# Enable Home Assistant API
api:
  password: "******"
  
ota:
  password: "*******"
  
  # Sync time with Home Assistant.
time:
  - platform: homeassistant
    id: homeassistant_time

switch:
  - platform: gpio
    pin: D4
    name: "switch-etaj"
    id: "control"

font:
  - file: "ComicSansMS3.ttf"
    id: font_1
    size: 12

i2c:
  sda: D2
  scl: D1
  scan: true

display:
  - platform: ssd1306_i2c
    model: "SSD1306 64x48"
    reset_pin: D0
    address: 0x3C
    lambda: |-
      it.printf(0, 18, id(font_1), "State: %s", id(control).state ? "ON" : "OFF");

Thanks
Marius

Hey,
your display should refresh once per second by default. SSD1306 OLED Display — ESPHome → “update_interval”
As you say it doesn’t, I wonder if there is another error with your setup. What does the serial console say?
Alternative approach would be that you need to trigger a display update after the switch changed it’s state. This kind of event-driven updating is often better anyhow. Switch Component — ESPHome → “switch.on-turn-on”

switch:
  - platform: gpio  # or any other platform
    # ...
    on_turn_on:
      - component.update: mydisplay

Hope this helps!

Hi Thom,
Thanks for your answer, I tried also to specify the update interval also to trigger the display…not working.
In the serial console everything its working fine and I can hear the relay working when HA trigger the relay ,


Cheers!
Marius

Hi,

Could you post the complete log, so including the part where the config is dumped (pink part).

Please also enter the following line to the lambda in the display: part to check if you have the right data in this lambda and the lambda is executed:
ESP_LOGD("in display lambda", "control state: %d", id(control).state);

Jos

Hi Jos,

Thank you for your answer.
Well after I add the debug line I can confirm if the switch are off its printing:

[09:52:58][D][in display lambda:062]: control state: 0
[09:52:58][D][in display lambda:062]: control state: 0
[09:52:58][D][in display lambda:062]: control state: 0
[09:52:58][D][in display lambda:062]: control state: 0

when I turn it on the switch:

[09:53:46][D][switch:013]: 'switch-etaj' Turning ON.
[09:53:46][D][switch:037]: 'switch-etaj': Sending state ON
[09:53:46][D][in display lambda:062]: control state: 1
[09:53:46][D][in display lambda:062]: control state: 1
[09:53:46][D][in display lambda:062]: control state: 1

And here is the boot log:

[09:56:11][I][app:102]: ESPHome version 2021.12.3 compiled on Jan 27 2022, 09:55:12
[09:56:11][C][wifi:488]: WiFi:
[09:56:11][C][wifi:350]:   Local MAC: E8:DB:84:95:DE:90
[09:56:11][C][wifi:351]:   SSID: [redacted]
[09:56:11][C][wifi:352]:   IP Address: 192.168.1.30
[09:56:11][C][wifi:354]:   BSSID: [redacted]
[09:56:11][C][wifi:355]:   Hostname: 'termostat-etaj'
[09:56:11][C][wifi:357]:   Signal strength: -46 dB ▂▄▆█
[09:56:11][C][wifi:361]:   Channel: 5
[09:56:11][C][wifi:362]:   Subnet: 255.255.255.0
[09:56:11][C][wifi:363]:   Gateway: 192.168.1.1
[09:56:11][C][wifi:364]:   DNS1: 192.168.1.1
[09:56:11][C][wifi:365]:   DNS2: 0.0.0.0
[09:56:11][C][logger:233]: Logger:
[09:56:11][C][logger:234]:   Level: DEBUG
[09:56:11][C][logger:235]:   Log Baud Rate: 115200
[09:56:11][C][logger:236]:   Hardware UART: UART0
[09:56:11][C][i2c.arduino:032]: I2C Bus:
[09:56:11][C][i2c.arduino:033]:   SDA Pin: GPIO4
[09:56:11][C][i2c.arduino:034]:   SCL Pin: GPIO5
[09:56:11][C][i2c.arduino:035]:   Frequency: 50000 Hz
[09:56:11][C][i2c.arduino:038]:   Recovery: bus successfully recovered
[09:56:11][I][i2c.arduino:048]: Scanning i2c bus for active devices...
[09:56:11][I][i2c.arduino:053]: Found i2c device at address 0x3C
[09:56:11][C][switch.gpio:048]: GPIO Switch 'switch-etaj'
[09:56:12][C][switch.gpio:049]:   Pin: GPIO5
[09:56:12][C][switch.gpio:071]:   Restore Mode: Restore (Defaults to OFF)
[09:56:12][C][ssd1306_i2c:023]: I2C SSD1306
[09:56:12][C][ssd1306_i2c:023]:   Rotations: 0 °
[09:56:12][C][ssd1306_i2c:023]:   Dimensions: 64px x 48px
[09:56:12][C][ssd1306_i2c:024]:   Address: 0x3C
[09:56:12][C][ssd1306_i2c:025]:   Model: SSD1306 64x48
[09:56:12][C][ssd1306_i2c:026]:   Reset Pin: GPIO16
[09:56:12][C][ssd1306_i2c:027]:   External VCC: NO
[09:56:12][C][ssd1306_i2c:028]:   Flip X: YES
[09:56:12][C][ssd1306_i2c:029]:   Flip Y: YES
[09:56:12][C][ssd1306_i2c:030]:   Offset X: 0
[09:56:12][C][ssd1306_i2c:031]:   Offset Y: 0
[09:56:12][C][ssd1306_i2c:032]:   Inverted Color: NO
[09:56:12][C][ssd1306_i2c:033]:   Update Interval: 0.002s
[09:56:12][C][ota:082]: Over-The-Air Updates:
[09:56:12][C][ota:083]:   Address: 192.168.1.30:8266
[09:56:12][C][ota:086]:   Using Password.
[09:56:12][C][api:134]: API Server:
[09:56:12][C][api:135]:   Address: 192.168.1.30:6053
[09:56:12][C][api:139]:   Using noise encryption: NO
[09:56:12][C][sntp:050]: SNTP Time:
[09:56:12][C][sntp:051]:   Server 1: '0.pool.ntp.org'
[09:56:12][C][sntp:052]:   Server 2: '1.pool.ntp.org'
[09:56:12][C][sntp:053]:   Server 3: '2.pool.ntp.org'
[09:56:12][C][mdns:084]: mDNS:
[09:56:12][C][mdns:085]:   Hostname: termostat-etaj

Thank you!
Marius

Well, that’s good news, the device is working fine! And something is going wrong with the it.printf statement. You could replace it by:

if (id(control).state) {
    it.print(0, 18, id(font_1), "State: ON");
  } else {
    it.print(0, 18, id(font_1), "State: OFF");
  }

Probably you have to erase the display before printing a changed line, because the two text lines don’t have the same length. This can be done with it.fill(COLOR_OFF);

Jos

Hi Jos,

Still not working :frowning:

My code looks like now:

switch:
  - platform: gpio
    pin: GPIO5
    name: "switch-etaj"
    id: "control"

font:
  - file: "ComicSansMS3.ttf"
    id: font_1
    size: 12

i2c:
  sda: D2
  scl: D1
  scan: true

display:
  - platform: ssd1306_i2c
    model: "SSD1306 64x48"
    update_interval: 2ms
    id: "mydisplay"
    reset_pin: D0
    address: 0x3C
    lambda: |-
     it.fill(COLOR_OFF);
     if (id(control).state) {
     it.print(0, 18, id(font_1), "State: ON");
     } else {
     it.print(0, 18, id(font_1), "State: OFF");
     }

But nothing is changed…my display show me State: OFF and nothing is changed if the relay is turned ON
Thanks a lot for your support

BR
Marius

Did you test the “on_turn_on” action I mentioned above?

Some remarks:

  • In your last yaml post you are using pin: GPIO5 in the switch part, however on a D1-mini is GPIO5 = D1 (see ESP8266 Pinout Reference: Which GPIO pins should you use? | Random Nerd Tutorials) and you also use the D1 as scl pin. That’s not correct.
  • You use a i2c OLED screen, that does only have 4 pins and does not have a reset_pin, so you can remove that line.
  • An update interval of 2 mili-seconds is much too short, i think this is preventing the esp to update the other components, it only busy with updating the screen… Just use the default of 1s.
  • You can put the previous ESP_LOGD statement back in the lambda, so you have your debug info back. It doesn’t hurt the operation :slight_smile:

Jos

U are my genius guy!!!
Thank u very much
Now…the hardware which open the path for my mistakes:
I’m using a ESP mini_D1 shield relay which are using the pin D1 for the relay
I also use the display mini_D1 shield which are using D1+D2 pins for I2C interface…that got me in troubles.
Thank you so much for your help. I will order a separate display(not shield) and I will remap the I2C pins.
Your remarks wake me up and make me to realize how such a big idiot I am :slight_smile:
After I change the relay pin from D1 to D3 everything works fine.
Thanks a lot!!!
Cheers!
Marius

Now Jos, maybe u can give me another hint to my problem, I will like to have the “ON” mode printed in RED color and the “OFF” mode in GREEN.
Thanks
Marius

Thanks and good to hear it is working now, also your first it.printf construction should work as well. I don’t see any 'grammatical` error in this construction.

No reason for that, learning is all about making mistakes!

Regarding your question about the color’s. What kind of screen do you have, I know only the ssd1306 I2C screens with mono color in White, Yellow or Blue or some screens where the upper part of the screen is Yellow and the lower part is Blue. I haven’t seen I2C versions which are full multicolor?

Jos

Jos,
U are so kind,

Thanks a lot for your help!!!

Cheers!!!
Marius