From 5fddc6733ce595dd21db220a1a1f7f2b0a8a804e Mon Sep 17 00:00:00 2001 From: Maurice Makaay Date: Tue, 13 Apr 2021 22:10:16 +0200 Subject: [PATCH] The slider sensor now has a configurable value range. --- doc/example-full.yaml | 26 ++++++++++++++++++++++++-- doc/example.yaml | 6 +++--- sensor/__init__.py | 6 +++++- sensor/sensor.h | 30 ++++++++++++++++-------------- 4 files changed, 48 insertions(+), 20 deletions(-) diff --git a/doc/example-full.yaml b/doc/example-full.yaml index 0e9edf6..fa97d96 100644 --- a/doc/example-full.yaml +++ b/doc/example-full.yaml @@ -73,8 +73,9 @@ light: transition_length: 3s update_interval: 3s -# The binary sensor is used to handle front panel touch events. binary_sensor: + + # When pressing the power button, turn on the light. - platform: yeelight_bs2 id: ${name}_power_button part: power button @@ -82,13 +83,34 @@ binary_sensor: then: - light.toggle: ${name} -# The sensor is used to publish a slider level when the slider is touched. + # When holding the color button, turn on night light mode. + - platform: yeelight_bs2 + id: ${name}_color_button + part: color button + on_multi_click: + - timing: + - ON for at least 0.8s + then: + - light.turn_on: + id: ${name} + brightness: 0.01 + red: 0 + green: 1 + blue: 0 + sensor: + + # When the slider is touched, update the brightness. + # Brightness 0.01 initiates the light night mode, which has already + # been handle above. Therefore, brightness starts from 0.02 here, + # so night mode is not triggered from the slider. - platform: yeelight_bs2 id: ${name}_slider_level + range_from: 0.02 on_value: then: - light.turn_on: id: ${name} brightness: !lambda return x; + diff --git a/doc/example.yaml b/doc/example.yaml index 76f5630..3eb197f 100644 --- a/doc/example.yaml +++ b/doc/example.yaml @@ -48,8 +48,9 @@ light: transition_length: 3s update_interval: 3s -# The binary sensor is used to handle front panel touch events. binary_sensor: + + # When pressing the power button, turn on the light. - platform: yeelight_bs2 id: ${name}_power_button part: power button @@ -57,8 +58,8 @@ binary_sensor: then: - light.toggle: ${name} -# The sensor is used to publish a slider level when the slider is touched. sensor: + # When touching the slider, update the brightness. - platform: yeelight_bs2 id: ${name}_slider_level on_value: @@ -67,4 +68,3 @@ sensor: id: ${name} brightness: !lambda return x; - diff --git a/sensor/__init__.py b/sensor/__init__.py index 88e5511..f2f3ed2 100644 --- a/sensor/__init__.py +++ b/sensor/__init__.py @@ -1,7 +1,7 @@ import esphome.codegen as cg import esphome.config_validation as cv from esphome.components import sensor -from esphome.const import CONF_ID, CONF_FORCE_UPDATE +from esphome.const import CONF_ID, CONF_FORCE_UPDATE, CONF_RANGE_FROM, CONF_RANGE_TO from .. import ( bs2_ns, CODEOWNERS, CONF_FRONT_PANEL_HAL_ID, FrontPanelHAL @@ -17,6 +17,8 @@ CONFIG_SCHEMA = sensor.SENSOR_SCHEMA.extend( cv.GenerateID(): cv.declare_id(YeelightBS2SliderSensor), cv.GenerateID(CONF_FRONT_PANEL_HAL_ID): cv.use_id(FrontPanelHAL), cv.Optional(CONF_FORCE_UPDATE, default=True): cv.boolean, + cv.Optional(CONF_RANGE_FROM, default=0.01): cv.float_, + cv.Optional(CONF_RANGE_TO, default=1.00): cv.float_, } ).extend(cv.COMPONENT_SCHEMA) @@ -27,3 +29,5 @@ def to_code(config): front_panel_hal_var = yield cg.get_variable(config[CONF_FRONT_PANEL_HAL_ID]) cg.add(var.set_parent(front_panel_hal_var)) + cg.add(var.set_range_from(config[CONF_RANGE_FROM])) + cg.add(var.set_range_to(config[CONF_RANGE_TO])) diff --git a/sensor/sensor.h b/sensor/sensor.h index 0f1f410..c5cfa4e 100644 --- a/sensor/sensor.h +++ b/sensor/sensor.h @@ -20,32 +20,31 @@ namespace bs2 { */ class YeelightBS2SliderSensor : public sensor::Sensor, public Component { public: - void set_parent(FrontPanelHAL *front_panel) { - front_panel_ = front_panel; - } + void set_parent(FrontPanelHAL *front_panel) { front_panel_ = front_panel; } + void set_range_from(float from) { range_from_ = from; } + void set_range_to(float to) { range_to_ = to; } void setup() { ESP_LOGCONFIG(TAG, "Setting up slider sensor ..."); + ESP_LOGCONFIG(TAG, " Range from: %f", range_from_); + ESP_LOGCONFIG(TAG, " Range to: %f", range_to_); + + slope_ = (range_to_ - range_from_) / 19.0f; front_panel_->add_on_event_callback( [this](EVENT ev) { if ((ev & FLAG_PART_MASK) == FLAG_PART_SLIDER) { - auto level = (ev & FLAG_LEVEL_MASK) >> FLAG_LEVEL_SHIFT; + float level = (ev & FLAG_LEVEL_MASK) >> FLAG_LEVEL_SHIFT; // Slider level 1 is really hard to touch. It is between // the power button and the slider space, so it doesn't // look like this one was ever meant to be used, or that // the design was faulty on this. Therefore, level 1 is - // ignored here. - level = max(1.0f, level - 1.0f); - - // Convert the slider level to a float between 0.01 and - // 1.00, which is useful as a representation for a - // brightness value. The input level is now between - // 1 and 20. - auto publish_level = max(0.01f, (level-1.0f) * (1.00f / 19.0f)); - - this->publish_state(publish_level); + // ignored. The resulting range of levels is 0-19. + float corrected_level = max(0.0f, level - 2.0f); + + float final_level = range_from_ + (slope_ * corrected_level); + this->publish_state(final_level); } } ); @@ -53,6 +52,9 @@ public: protected: FrontPanelHAL *front_panel_; + float range_from_; + float range_to_; + float slope_; }; } // namespace bs2