mirror of
https://github.com/esphome/esphome.git
synced 2024-12-22 13:34:54 +01:00
Add on_clockwise and on_anticlockwise triggers to rotary encoder (#1330)
This commit is contained in:
parent
e4636b99f7
commit
20dd744680
4 changed files with 52 additions and 1 deletions
|
@ -94,10 +94,12 @@ void ICACHE_RAM_ATTR HOT RotaryEncoderSensorStore::gpio_intr(RotaryEncoderSensor
|
||||||
if ((new_state & arg->resolution & STATE_HAS_INCREMENTED) != 0) {
|
if ((new_state & arg->resolution & STATE_HAS_INCREMENTED) != 0) {
|
||||||
if (arg->counter < arg->max_value)
|
if (arg->counter < arg->max_value)
|
||||||
arg->counter++;
|
arg->counter++;
|
||||||
|
arg->on_clockwise_callback_.call();
|
||||||
}
|
}
|
||||||
if ((new_state & arg->resolution & STATE_HAS_DECREMENTED) != 0) {
|
if ((new_state & arg->resolution & STATE_HAS_DECREMENTED) != 0) {
|
||||||
if (arg->counter > arg->min_value)
|
if (arg->counter > arg->min_value)
|
||||||
arg->counter--;
|
arg->counter--;
|
||||||
|
arg->on_anticlockwise_callback_.call();
|
||||||
}
|
}
|
||||||
|
|
||||||
arg->state = new_state;
|
arg->state = new_state;
|
||||||
|
|
|
@ -27,6 +27,9 @@ struct RotaryEncoderSensorStore {
|
||||||
int32_t last_read{0};
|
int32_t last_read{0};
|
||||||
uint8_t state{0};
|
uint8_t state{0};
|
||||||
|
|
||||||
|
CallbackManager<void()> on_clockwise_callback_;
|
||||||
|
CallbackManager<void()> on_anticlockwise_callback_;
|
||||||
|
|
||||||
static void gpio_intr(RotaryEncoderSensorStore *arg);
|
static void gpio_intr(RotaryEncoderSensorStore *arg);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -62,6 +65,14 @@ class RotaryEncoderSensor : public sensor::Sensor, public Component {
|
||||||
|
|
||||||
float get_setup_priority() const override;
|
float get_setup_priority() const override;
|
||||||
|
|
||||||
|
void add_on_clockwise_callback(std::function<void()> callback) {
|
||||||
|
this->store_.on_clockwise_callback_.add(std::move(callback));
|
||||||
|
}
|
||||||
|
|
||||||
|
void add_on_anticlockwise_callback(std::function<void()> callback) {
|
||||||
|
this->store_.on_anticlockwise_callback_.add(std::move(callback));
|
||||||
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
GPIOPin *pin_a_;
|
GPIOPin *pin_a_;
|
||||||
GPIOPin *pin_b_;
|
GPIOPin *pin_b_;
|
||||||
|
@ -81,5 +92,19 @@ template<typename... Ts> class RotaryEncoderSetValueAction : public Action<Ts...
|
||||||
RotaryEncoderSensor *encoder_;
|
RotaryEncoderSensor *encoder_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class RotaryEncoderClockwiseTrigger : public Trigger<> {
|
||||||
|
public:
|
||||||
|
explicit RotaryEncoderClockwiseTrigger(RotaryEncoderSensor *parent) {
|
||||||
|
parent->add_on_clockwise_callback([this]() { this->trigger(); });
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
class RotaryEncoderAnticlockwiseTrigger : public Trigger<> {
|
||||||
|
public:
|
||||||
|
explicit RotaryEncoderAnticlockwiseTrigger(RotaryEncoderSensor *parent) {
|
||||||
|
parent->add_on_anticlockwise_callback([this]() { this->trigger(); });
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
} // namespace rotary_encoder
|
} // namespace rotary_encoder
|
||||||
} // namespace esphome
|
} // namespace esphome
|
||||||
|
|
|
@ -3,7 +3,7 @@ import esphome.config_validation as cv
|
||||||
from esphome import pins, automation
|
from esphome import pins, automation
|
||||||
from esphome.components import sensor
|
from esphome.components import sensor
|
||||||
from esphome.const import CONF_ID, CONF_RESOLUTION, CONF_MIN_VALUE, CONF_MAX_VALUE, UNIT_STEPS, \
|
from esphome.const import CONF_ID, CONF_RESOLUTION, CONF_MIN_VALUE, CONF_MAX_VALUE, UNIT_STEPS, \
|
||||||
ICON_ROTATE_RIGHT, CONF_VALUE, CONF_PIN_A, CONF_PIN_B
|
ICON_ROTATE_RIGHT, CONF_VALUE, CONF_PIN_A, CONF_PIN_B, CONF_TRIGGER_ID
|
||||||
|
|
||||||
rotary_encoder_ns = cg.esphome_ns.namespace('rotary_encoder')
|
rotary_encoder_ns = cg.esphome_ns.namespace('rotary_encoder')
|
||||||
RotaryEncoderResolution = rotary_encoder_ns.enum('RotaryEncoderResolution')
|
RotaryEncoderResolution = rotary_encoder_ns.enum('RotaryEncoderResolution')
|
||||||
|
@ -14,11 +14,18 @@ RESOLUTIONS = {
|
||||||
}
|
}
|
||||||
|
|
||||||
CONF_PIN_RESET = 'pin_reset'
|
CONF_PIN_RESET = 'pin_reset'
|
||||||
|
CONF_ON_CLOCKWISE = 'on_clockwise'
|
||||||
|
CONF_ON_ANTICLOCKWISE = 'on_anticlockwise'
|
||||||
|
|
||||||
RotaryEncoderSensor = rotary_encoder_ns.class_('RotaryEncoderSensor', sensor.Sensor, cg.Component)
|
RotaryEncoderSensor = rotary_encoder_ns.class_('RotaryEncoderSensor', sensor.Sensor, cg.Component)
|
||||||
RotaryEncoderSetValueAction = rotary_encoder_ns.class_('RotaryEncoderSetValueAction',
|
RotaryEncoderSetValueAction = rotary_encoder_ns.class_('RotaryEncoderSetValueAction',
|
||||||
automation.Action)
|
automation.Action)
|
||||||
|
|
||||||
|
RotaryEncoderClockwiseTrigger = rotary_encoder_ns.class_('RotaryEncoderClockwiseTrigger',
|
||||||
|
automation.Trigger)
|
||||||
|
RotaryEncoderAnticlockwiseTrigger = rotary_encoder_ns.class_('RotaryEncoderAnticlockwiseTrigger',
|
||||||
|
automation.Trigger)
|
||||||
|
|
||||||
|
|
||||||
def validate_min_max_value(config):
|
def validate_min_max_value(config):
|
||||||
if CONF_MIN_VALUE in config and CONF_MAX_VALUE in config:
|
if CONF_MIN_VALUE in config and CONF_MAX_VALUE in config:
|
||||||
|
@ -40,6 +47,12 @@ CONFIG_SCHEMA = cv.All(sensor.sensor_schema(UNIT_STEPS, ICON_ROTATE_RIGHT, 0).ex
|
||||||
cv.Optional(CONF_RESOLUTION, default=1): cv.enum(RESOLUTIONS, int=True),
|
cv.Optional(CONF_RESOLUTION, default=1): cv.enum(RESOLUTIONS, int=True),
|
||||||
cv.Optional(CONF_MIN_VALUE): cv.int_,
|
cv.Optional(CONF_MIN_VALUE): cv.int_,
|
||||||
cv.Optional(CONF_MAX_VALUE): cv.int_,
|
cv.Optional(CONF_MAX_VALUE): cv.int_,
|
||||||
|
cv.Optional(CONF_ON_CLOCKWISE): automation.validate_automation({
|
||||||
|
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_id(RotaryEncoderClockwiseTrigger),
|
||||||
|
}),
|
||||||
|
cv.Optional(CONF_ON_ANTICLOCKWISE): automation.validate_automation({
|
||||||
|
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_id(RotaryEncoderAnticlockwiseTrigger),
|
||||||
|
}),
|
||||||
}).extend(cv.COMPONENT_SCHEMA), validate_min_max_value)
|
}).extend(cv.COMPONENT_SCHEMA), validate_min_max_value)
|
||||||
|
|
||||||
|
|
||||||
|
@ -61,6 +74,13 @@ def to_code(config):
|
||||||
if CONF_MAX_VALUE in config:
|
if CONF_MAX_VALUE in config:
|
||||||
cg.add(var.set_max_value(config[CONF_MAX_VALUE]))
|
cg.add(var.set_max_value(config[CONF_MAX_VALUE]))
|
||||||
|
|
||||||
|
for conf in config.get(CONF_ON_CLOCKWISE, []):
|
||||||
|
trigger = cg.new_Pvariable(conf[CONF_TRIGGER_ID], var)
|
||||||
|
yield automation.build_automation(trigger, [], conf)
|
||||||
|
for conf in config.get(CONF_ON_ANTICLOCKWISE, []):
|
||||||
|
trigger = cg.new_Pvariable(conf[CONF_TRIGGER_ID], var)
|
||||||
|
yield automation.build_automation(trigger, [], conf)
|
||||||
|
|
||||||
|
|
||||||
@automation.register_action('sensor.rotary_encoder.set_value', RotaryEncoderSetValueAction,
|
@automation.register_action('sensor.rotary_encoder.set_value', RotaryEncoderSetValueAction,
|
||||||
cv.Schema({
|
cv.Schema({
|
||||||
|
|
|
@ -586,6 +586,10 @@ sensor:
|
||||||
- sensor.rotary_encoder.set_value:
|
- sensor.rotary_encoder.set_value:
|
||||||
id: rotary_encoder1
|
id: rotary_encoder1
|
||||||
value: !lambda 'return -1;'
|
value: !lambda 'return -1;'
|
||||||
|
on_clockwise:
|
||||||
|
- logger.log: "Clockwise"
|
||||||
|
on_anticlockwise:
|
||||||
|
- logger.log: "Anticlockwise"
|
||||||
- platform: pulse_width
|
- platform: pulse_width
|
||||||
name: Pulse Width
|
name: Pulse Width
|
||||||
pin: GPIO12
|
pin: GPIO12
|
||||||
|
|
Loading…
Reference in a new issue