Taking the old ceiling fan for a smart spin

I have recently bought a Brilliant Smart WiFi Ceiling Fan Controller for a bedroom ceiling fan in our house. This is a Tuya device but I wanted to avoid signing up to the Tuya cloud service to operate my ceiling fan under all circumstances. In this article I just wanted to share a few learnings and observations.

Like many other devices the controller uses the ESP to communicate with the world and a separate MCU to control the fan and lights.

Unfortunately – as far as I know – ESPHome does not yet fully support all use-cases to control an MCU, so I decided to give Tasmota a chance which has recently added and improved support to control an MCU. Thanks to some amazing pre-work in the HA community forum I did not have to start at zero. Still, the learning curve is pretty steep if you have never used Tasmota before and the concept is quite different to ESPHome which has become my number one choice when adopting ESP devices into my home automation system.

Prerequisites

Tasmota firmware from development branch

The old Tasmota 6.7.1 did not yet support all the features required to use this fan controller, so I had to compile my own firmware. I followed the instructions in the Tasmota wiki, used VS Studio and were able to compile a 7.0.0.4 firmware within an hour.

In the meantime a new Tasmota major release has been published, and I have flashed a standard image, using version 7.1.1 now.

Tuya-Convert

I have adopted plenty of Tuya devices using Tuya-Convert. I am now using a dedicated Raspberry Pi 3 running Raspbian 10. It is connected via Ethernet to my network so that I keep full remote control while Tuya-Convert uses the WiFi adapter.

I used Tuya-Convert version 2.2.0 with a manual patch of one file that was required to convert some other devices.

Configuration

Tasmota

Tasmota Module Parameters

There are 3 items that need to be mapped to Tasmota controls. The following configuration worked for me and correctly linked light and dimmer, and also automatically generated a light entity and fan power switch entity using auto-discovery.

# Configure Power1 (fnId=11) as Fan power (dpId=1)
TuyaMCU 11,1
# Configure Power2 (fnId=12) as Light (dpId=9)
TuyaMCU 12,9
# Configure Dimmer (fnId=21) as Light Dimmer (dpId=10)
TuyaMCU 21,10

I connected an LED light to my fan which comes with its own LED driver. The driver itself has a control input which is not compatible with the fan controller. Instead the fan controller dims by changing the voltage which would make the LED to blink. To avoid that I just limited the dimmer range.

# Dimmer is not working with my LED driver. Limit range.
DimmerRange 100,100

The following rule listens to changes coming from the MCU and initiated by using the remote control. Each code corresponds to a fan speed, and the action then publishes the current speed value via MQTT so that Home Asssistant can update the fan entity. I decided to go with non-retained messages in this case and instead query the speed on Home Assistant start-up.

# Rule: Publish speed to MQTT when using the remote control.
Rule1 on TuyaReceived#Data=55AA03070005030400010016 DO Publish esp_fan_bedroom/stat/RESULT {"Speed":1} endon on TuyaReceived#Data=55AA03070005030400010117 DO Publish esp_fan_bedroom/stat/RESULT {"Speed":2} endon on TuyaReceived#Data=55AA03070005030400010218 DO Publish esp_fan_bedroom/stat/RESULT {"Speed":3} endon
Rule1 ON

The second rule listens to incoming triggers initiated from changing the speed of the Home Assistant fan entity. The payload in the MQTT message is something like speed=1 and the action taken is to turn on the fan (Power1 1) and then send the speed value. For example, TuyaSend4 3,0 sends an enum value of 0 (speed 1/low) to dpId 3.

# Rule: Set speed when commands arrive from HA via MQTT.
Rule2 on Event#speed=1 DO Backlog Power1 1; TuyaSend4 3,0 endon on Event#speed=2 DO Backlog Power1 1; TuyaSend4 3,1 endon on Event#speed=3 DO Backlog Power1 1; TuyaSend4 3,2 endon
Rule2 ON

I configured auto-discovery which generates a status sensor, a light switch and a power switch for the fan. This also swaps the MQTT command and topic around.

# Set HA auto discover.
SetOption19 1

Home Assistant

Auto-discovery

Assuming that you have MQTT already set up in general, the new device should automatically appear in Home Assistant, and you should see 3 entities:

  • Light
  • Fan power
  • Status

Fan

The fan configuration is a bit more complex, so let’s have a look in detail:

  • Availability: The Tasmota device sends telemetry data on <device>/tele/LWT, and we can subscribe to those updates.
  • State: In the above configuration we have tied the fan power to POWER1 and have to subscribe to the corresponding stat messages and send via the cmnd topic.
  • Speed: This is a bit trickier. To change the speed, a payload like speed=2 needs to be sent to the <device>/cmnd/Event topic. This is then picked up by Rule2 in the Tasmota configuration. When the fan speed changes – as defined in Rule1 – the device confirms the speed as JSON payload which can be extracted and transformed into a payload like speed=2 that the fan definition below understands.
fan:
  - platform: mqtt
    name: "Fan Bedroom"
    availability_topic: "esp_fan_bedroom/tele/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"
    state_topic: "esp_fan_bedroom/stat/POWER1"
    command_topic: "esp_fan_bedroom/cmnd/POWER1"
    payload_on: "ON"
    payload_off: "OFF"
    speed_state_topic: "esp_fan_bedroom/stat/RESULT"
    speed_value_template: "{% if value_json is defined and value_json.Speed is defined %}speed={{ value_json.Speed }}{% endif %}"
    speed_command_topic: "esp_fan_bedroom/cmnd/Event"
    payload_low_speed: "speed=1"
    payload_medium_speed: "speed=2"
    payload_high_speed: "speed=3"
    qos: 1
    speeds:
      - low
      - medium
      - high

The following automation is required to retrieve the latest state of the fan – power and speed. It executes two commands with empty payloads which should trigger the device to send the current state as a result.

automation:
  - alias: "Update fan power state on start-up"
    trigger:
      platform: homeassistant
      event: start
    action:
      - service: mqtt.publish
        data:
          topic: "esp_fan_bedroom/cmnd/POWER1"
          payload: ""
      - service: mqtt.publish
        data:
          topic: "esp_fan_bedroom/cmnd/Event/speed"
          payload: ""
Fan Entity Details (MQTT fan via Tasmota)

Device Monitoring

After having deployed many ESP based devices already, I found it quite useful to keep some information about the device itself in HA. I have added the following sensors and script which replicated from what I normally get in ESPHome.

binary_sensor:
  - platform: mqtt
    name: "ESP Fan Bedroom Status"
    state_topic: "esp_fan_bedroom/tele/LWT"
    payload_on: 'Online'
    payload_off: 'Offline'
    device_class: connectivity

sensor:
  - platform: template
    sensors:
      # Fan Master Bedroom
      esp_fan_bedroom_ip_address:
        friendly_name: "ESP Fan Bedroom IP Address"
        value_template: "{{ state_attr('sensor.esp_fan_bedroom_status', 'IPAddress') }}"
        availability_template: "{{ is_state('binary_sensor.esp_fan_bedroom_status', 'on') }}"
      esp_fan_bedroom_rssi:
        friendly_name: "ESP Fan Bedroom RSSI"
        value_template: "{{ state_attr('sensor.esp_fan_bedroom_status', 'RSSI') }}"
        icon_template: 'mdi:wifi'
        unit_of_measurement: 'dB'
        availability_template: "{{ is_state('binary_sensor.esp_fan_bedroom_status', 'on') }}"
      esp_fan_bedroom_uptime:
        friendly_name: "ESP Fan Bedroom Uptime"
        value_template: "{{ state_attr('sensor.esp_fan_bedroom_status', 'Uptime') | regex_replace(find='T', replace='d, ', ignorecase=False) }}"
        icon_template: 'mdi:clock-start'
        availability_template: "{{ is_state('binary_sensor.esp_fan_bedroom_status', 'on') }}"
      esp_fan_bedroom_version:
        friendly_name: "ESP Fan Bedroom Version"
        value_template: "{{ state_attr('sensor.esp_fan_bedroom_status', 'Version') }}"
        icon_template: 'mdi:information'
        availability_template: "{{ is_state('binary_sensor.esp_fan_bedroom_status', 'on') }}"

script:
  esp_fan_bedroom_restart:
    alias: "ESP Fan Bedroom Restart"
    sequence:
      - service: mqtt.publish
        data:
          topic: "esp_fan_bedroom/cmnd/Restart"
          payload: "1"
Fan Device Monitoring

Ceiling Fan

Originally I was planning to use this fan controller with a Spyda 36″ ceiling fan in one of the kid’s bedrooms. Unfortunately it turned out that the speed control did not really work with that fan, i.e. there was no noticeable difference in fan speed when changing between the 3 speeds.

Ceiling Fan

Instead I had this fan controller retrofitted onto an Lucci ceiling fan where the previous non-smart ceiling controller’s speed control was already broken. This is a better fit and the 3 speeds actually work. The built-in lamp can be turned on and off, but like the LED in the Spyda fan, the lamp in this ceiling fan does not support dimming.

Fan Remote Control

Observations

  • I have to admit that Tasmota is very powerful and supports many devices and sensors. However, there are also a lot of conventions and other magic going on under the hood which makes it quite hard as a beginner to get the configuration right. Luckily the Tasmota wiki is quite comprehensive, but I had to read a lot until I got my configuration right.
  • A while ago I made a switch from ESPEasy to ESPHome, and one of the reasons for that step was that I preferred a framework where I can define all the sensors and pins and everything upfront in a human-readable configuration file that I can version and easily backup. With Tasmota it feels like taking a step backwards – at least in this case – where I uploaded a generic firmware to the device and then had to configure the device through its web interface. This may be less of an issue in cases where the whole device configuration is available as a template.
  • Automated device discovery is great – if it works. I couldn’t really find out in which cases Tasmota exposes a relay as a switch or a light. There is an option to expose all relays as lights, but that is not what I needed for this fan controller.
  • Another user in the HA community forum has taken the above configuration and slightly refined it in a way that does not require any rules in the Tasmota device itself, which makes the HA configuration a bit more complex. Please have a look at the blog entry for a comparison.

Outlook

I am now still left with a new ceiling fan without smart control. Luckily there are alternatives, and I am in the process of adopting a SRL Tech fan controller which has turned out to work very similarly like the Brilliant one. I will share a working configuration as soon as possible.

Compatibility

At the time of writing this post, I used:

  • Home Assistant 0.103.4 with Python 3.7.5
  • Tasmota 7.1.1
  • Tuya-Convert 2.2.0 on Raspbian 10 (Buster)

Smarter Fans Series

  1. Retrofitted smart fan controller flashed with Tasmota onto old ceiling fan
  2. Flashed ESPHome on brand new ceiling fan controller
  3. Flashed ESPHome on Sonoff RF Bridge to control new ceiling fan.

16 Replies to “Taking the old ceiling fan for a smart spin”

  1. Excellent post! Thanks for the write up. I’ve found that getting ceiling fans to work just right depends on a lot of factors – especially how it’s wired in the house. I’m trying out the BOND device that communicates to ceiling fans over RF, but if it doesn’t work well I may go this route.

    1. Thanks for your feedback.
      I guess the main disadvantage of devices such as the Bond is that you don’t get any response from the fan. I am playing around with an IR controller and a wall fan to figure out a good sequence of commands to avoid having to guess the fan’s current state.

  2. You extract values from “sensor.esp_fan_bedroom_status” for getting the IP address and such. However, as far as i can see, the only “esp_fan_bedroom_status” sensor you define is a binary_sensor. How do you define a normal sensor called “esp_fan_bedroom_status” so you can extract it’s IP address?

    1. That is a good question – the entity “sensor.esp_fan_bedroom_status” is defined automatically because I have configured auto-discovery. The details are published via MQTT (topic “esp_fan_bedroom/tele/HASS_STATE” in my example) every 10 minutes.

  3. I’m about to get the sonoff ifan03 and hope to flash it with tasmota 🙂 enjoy your posts, keep them up!

  4. I made the mistake of getting a minka aire fan, which uses 303MHz. not easy to find a transmitter, so will probably rip apart the fan remote and connect up to an ESP.

  5. I have one of these: SRL Tech fan controller – I’d be really interested in your progress using that – I haven’t had much luck so far.

  6. Malte -thanks so much for such a detailed post. I am one of the unlucky ones and just purchased the fan controller and it has the new Tuya firmware which prevents OTA firmware upgrades.

    I have tried all sorts of ways to hardwire the unit to try and flash with serial cable connection. No luck .. I’m hoping someone else may have worked out how to flash manually.

    All the best and thanks again for the post !

    1. Thanks for your feedback, Jason.
      Sorry to hear that you’re having trouble flashing the controller. This appears to happen more and more with newer hardware.
      Good luck.

  7. Hi @malte, thanks to you and all the others who share their home automation adventures. Not sure what country you are in? I’m keen to get some of these wall switches…I already have sonoff controllers running tasmota, and these wall plates look like they would match my zemismart light switches quite well. I’m in NZ… local hardware store seems to have plenty of Brilliant Smart branded stuff… but not these, cheers z

    1. Hi zorruno, thanks for your feedback. I’m located in Australia. I bought this kit from JD Lighting and they say on their website that they deliver to NZ.
      However, the smarts are built into the controller (located in the fan’s canopy), not into the wall remote which is just talking RF to the controller. So, I’m not sure if you could make the wall switches work with a Sonoff controller…

      1. cheers – is it plain 433MHz do you know? Probably a lot to pay just for a 433MHz remote… but they look so similar to my switches!

        1. It says “Operating frequency: 433.9MHz” on the back. However, I just looked at my Sonoff RF Bridge’s log and it does not appear to receive anything from that Brilliant remote control.

Leave a Reply to Alex Dantoft Cancel reply

Your email address will not be published. Required fields are marked *