找回密碼
 立即註冊
惟家LINE群QRCODE
    查看: 0|回覆: 0

    一個按鈕做四件事:ESPHome 的單擊、雙擊、長按、多擊

    [複製鏈接]

    !lvup!   100%

    363

    主題

    27

    回帖

    2200萬

    積分

    管理員

    積分
    22005752
    發表於 3 天前 | 顯示全部樓層 |閱讀模式
    一個實體按鈕比你想的能做更多事。

    這篇講怎麼讓同一個按鈕依照按法做不同的事。



    最基本:接一個按鈕

    接線
    1. 按鈕的一腳  →  GPIO(例如 GPIO13)
    2. 按鈕的另一腳 →  GND
    複製代碼

    不用接電阻 —— ESP32 內建上拉電阻,在設定裡打開就好。

    設定
    1. binary_sensor:
    2.   - platform: gpio
    3.     pin:
    4.       number: GPIO13
    5.       mode:
    6.         input: true
    7.         pullup: true      # 打開內建上拉
    8.       inverted: true      # 按下時是「低電位」,所以要反轉
    9.     name: "按鈕"
    10.     filters:
    11.       - delayed_on: 20ms     # 去彈跳
    12.       - delayed_off: 20ms
    複製代碼

    delayed_on / delayed_off 是「去彈跳」

    機械按鈕按下的瞬間電路會震盪
    不去彈跳的話一次按壓可能被讀成三四次。

    20-50ms 是常見的值。



    多擊偵測:on_multi_click

    這是 ESPHome 最強大的按鈕功能。
    1. binary_sensor:
    2.   - platform: gpio
    3.     pin:
    4.       number: GPIO13
    5.       mode: {input: true, pullup: true}
    6.       inverted: true
    7.     name: "客廳按鈕"
    8.     filters:
    9.       - delayed_on: 20ms
    10.     on_multi_click:
    11.       # ===== 單擊 =====
    12.       - timing:
    13.           - ON for at most 0.6s
    14.           - OFF for at least 0.3s
    15.         then:
    16.           - homeassistant.service:
    17.               service: light.toggle
    18.               data:
    19.                 entity_id: light.living_room
    20.       # ===== 雙擊 =====
    21.       - timing:
    22.           - ON for at most 0.5s
    23.           - OFF for at most 0.4s
    24.           - ON for at most 0.5s
    25.           - OFF for at least 0.2s
    26.         then:
    27.           - homeassistant.service:
    28.               service: scene.turn_on
    29.               data:
    30.                 entity_id: scene.movie
    31.       # ===== 三擊 =====
    32.       - timing:
    33.           - ON for at most 0.4s
    34.           - OFF for at most 0.3s
    35.           - ON for at most 0.4s
    36.           - OFF for at most 0.3s
    37.           - ON for at most 0.4s
    38.           - OFF for at least 0.2s
    39.         then:
    40.           - homeassistant.service:
    41.               service: script.turn_on
    42.               data:
    43.                 entity_id: script.all_off
    44.       # ===== 長按 =====
    45.       - timing:
    46.           - ON for at least 1s
    47.         then:
    48.           - homeassistant.service:
    49.               service: light.turn_on
    50.               data:
    51.                 entity_id: light.living_room
    52.                 brightness_pct: "8"
    53.                 color_temp_kelvin: "2200"
    複製代碼

    timing 的語法

    這是最需要理解的部分。


    • ON for at most 0.6s —— 按下去不超過 0.6 秒
    • OFF for at least 0.3s —— 放開之後至少 0.3 秒沒有再按
    • ON for at least 1s —— 按著超過 1 秒


    為什麼單擊要有「OFF for at least 0.3s」

    因為要等一下,確認你不是要雙擊。


    • 沒有這一行的話,雙擊會被當成兩次單擊
    • 但這也代表單擊會有 0.3 秒的延遲


    取捨


    • 不需要雙擊的話 → 單擊的 OFF 時間可以設很短(0.05s),反應快
    • 要雙擊的話 → 單擊一定會有延遲


    我的建議最常用的功能放單擊,而且如果那個按鈕不需要雙擊,
    就不要設雙擊
    —— 反應快很多。



    重要:本地控制 vs 呼叫 HA

    上面的範例用的是 homeassistant.service
    意思是「叫 HA 去做事」

    問題:HA 掛了或網路斷了,按鈕就沒用了。

    如果那個按鈕控制的是同一片板子上的繼電器,一定要用本地控制
    1. switch:
    2.   - platform: gpio
    3.     pin: GPIO12
    4.     id: relay1
    5.     name: "客廳燈"
    6.     restore_mode: RESTORE_DEFAULT_OFF
    7. binary_sensor:
    8.   - platform: gpio
    9.     pin:
    10.       number: GPIO13
    11.       mode: {input: true, pullup: true}
    12.       inverted: true
    13.     name: "按鈕"
    14.     on_press:
    15.       - switch.toggle: relay1      # ← 本地,不經過 HA
    複製代碼

    這樣就算 Wi-Fi 斷了、HA 掛了,按鈕還是能開關燈。

    這是 ESPHome 相對於「純雲端開關」的最大優勢。

    混合做法:本地優先 + 通知 HA
    1.     on_press:
    2.       - switch.toggle: relay1
    3.       # HA 會自動知道 relay1 的狀態變了,不用額外通知
    複製代碼

    ESPHome 的實體狀態會自動同步給 HA
    所以你不用特別「通知」它。

    其他常用的按鈕事件
    1.     on_press:            # 按下的瞬間
    2.     on_release:          # 放開的瞬間
    3.     on_click:            # 短按(可設時間範圍)
    4.     on_double_click:     # 雙擊
    5.     on_multi_click:      # 多擊(最彈性)
    6.     on_state:            # 狀態改變(按下或放開都會觸發)
    複製代碼

    on_click 的簡化寫法
    1.     on_click:
    2.       - min_length: 50ms
    3.         max_length: 400ms
    4.         then:
    5.           - switch.toggle: relay1
    6.       - min_length: 600ms
    7.         max_length: 3000ms
    8.         then:
    9.           - homeassistant.service:
    10.               service: script.turn_on
    11.               data:
    12.                 entity_id: script.all_off
    複製代碼

    比 on_multi_click 好讀,但只能分「短按」和「長按」。



    加碼:旋轉編碼器(旋鈕)

    旋鈕做調光比按鈕好用太多。
    1. sensor:
    2.   - platform: rotary_encoder
    3.     name: "亮度旋鈕"
    4.     id: brightness_knob
    5.     pin_a:
    6.       number: GPIO32
    7.       mode: {input: true, pullup: true}
    8.     pin_b:
    9.       number: GPIO33
    10.       mode: {input: true, pullup: true}
    11.     min_value: 0
    12.     max_value: 100
    13.     resolution: 2          # 每格轉動算幾步
    14.     on_value:
    15.       then:
    16.         - homeassistant.service:
    17.             service: light.turn_on
    18.             data:
    19.               entity_id: light.living_room
    20.             data_template:
    21.               brightness_pct: "{{ value }}"
    22.             variables:
    23.               value: |-
    24.                 return id(brightness_knob).state;
    複製代碼

    常見的旋轉編碼器:EC11(很便宜,而且通常內建一個按鈕)。

    接線
    1. 編碼器    ESP32
    2. ------    -----
    3. CLK (A)  →  GPIO32
    4. DT  (B)  →  GPIO33
    5. SW(按鈕)→  GPIO25
    6. GND      →  GND
    7. + / VCC  →  3.3V
    複製代碼

    注意


    • 轉動方向反了 → 把 pin_a 和 pin_b 對調
    • 跳太快或太慢 → 調 resolution(1、2 或 4)
    • 會亂跳 → 加濾波或檢查接線


    實際的應用場景

    場景一:床頭按鈕


    • 單擊 → 開關床頭燈
    • 雙擊 → 全屋關燈(睡覺模式)
    • 長按 → 調成 5% 夜燈


    場景二:玄關按鈕


    • 單擊 → 玄關燈
    • 雙擊 → 離家模式(關全部、鎖門)
    • 三擊 → 回家模式


    場景三:桌面旋鈕


    • 轉動 → 調書桌燈亮度
    • 按下 → 開關
    • 長按 → 切換色溫模式


    實務建議


    • 雙擊和三擊很少人會用 —— 除非你自己記得住
    • 家人只會用單擊,所以最重要的功能一定放單擊
    • 長按比雙擊直覺,優先用長按
    • 做一張小卡片貼在旁邊說明功能(真的有用)


    ---

    下一篇:用 ESP32 做藍牙代理 ——
    2026 年更多板子能跑了。
    您需要登入後纔可以回帖 登入 | 立即註冊

    本版積分規則

    Archiver|手機版|惟家的智能論壇

    GMT+8, 2026-9-24 10:29 , Processed in 0.078112 second(s), 26 queries .

    快速回覆 返回頂部 返回列表