Skip to content

Commit

Permalink
button: custom action + ifan fixes
Browse files Browse the repository at this point in the history
  • Loading branch information
mcspr committed Jan 14, 2021
1 parent a40eca3 commit ef194c9
Show file tree
Hide file tree
Showing 6 changed files with 210 additions and 133 deletions.
208 changes: 130 additions & 78 deletions code/espurna/button.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -136,7 +136,34 @@ ButtonProvider convert(const String& value) {
return ButtonProvider::None;
}

} // namespace settings::internal
template<>
ButtonAction convert(const String& value) {
auto num = strtoul(value.c_str(), nullptr, 10);
if (num < ButtonsActionMax) {
auto action = static_cast<ButtonAction>(num);
switch (action) {
case ButtonAction::None:
case ButtonAction::Toggle:
case ButtonAction::On:
case ButtonAction::Off:
case ButtonAction::AccessPoint:
case ButtonAction::Reset:
case ButtonAction::Pulse:
case ButtonAction::FactoryReset:
case ButtonAction::Wps:
case ButtonAction::SmartConfig:
case ButtonAction::BrightnessIncrease:
case ButtonAction::BrightnessDecrease:
case ButtonAction::DisplayOn:
case ButtonAction::Custom:
return action;
}
}

return ButtonAction::None;
}

} // namespace internal
} // namespace settings

// -----------------------------------------------------------------------------
Expand All @@ -156,15 +183,15 @@ constexpr debounce_event::types::Config _buttonDecodeConfigBitmask(int bitmask)
};
}

constexpr button_action_t _buttonDecodeEventAction(const button_actions_t& actions, button_event_t event) {
constexpr ButtonAction _buttonDecodeEventAction(const ButtonActions& actions, button_event_t event) {
return (
(event == button_event_t::Pressed) ? actions.pressed :
(event == button_event_t::Released) ? actions.released :
(event == button_event_t::Click) ? actions.click :
(event == button_event_t::DoubleClick) ? actions.dblclick :
(event == button_event_t::LongClick) ? actions.lngclick :
(event == button_event_t::LongLongClick) ? actions.lnglngclick :
(event == button_event_t::TripleClick) ? actions.trplclick : 0U
(event == button_event_t::TripleClick) ? actions.trplclick : ButtonAction::None
);
}

Expand All @@ -181,7 +208,7 @@ constexpr button_event_t _buttonMapReleased(uint8_t count, unsigned long length,
);
}

button_actions_t _buttonConstructActions(unsigned char index) {
ButtonActions _buttonConstructActions(unsigned char index) {
return {
_buttonPress(index),
_buttonRelease(index),
Expand Down Expand Up @@ -222,12 +249,12 @@ button_event_delays_t::button_event_delays_t(unsigned long debounce, unsigned lo
lnglngclick(lnglngclick)
{}

button_t::button_t(button_actions_t&& actions_, button_event_delays_t&& delays_) :
button_t::button_t(ButtonActions&& actions_, button_event_delays_t&& delays_) :
actions(std::move(actions_)),
event_delays(std::move(delays_))
{}

button_t::button_t(BasePinPtr&& pin, const debounce_event::types::Config& config, button_actions_t&& actions_, button_event_delays_t&& delays_) :
button_t::button_t(BasePinPtr&& pin, const debounce_event::types::Config& config, ButtonActions&& actions_, button_event_delays_t&& delays_) :
event_emitter(std::make_unique<debounce_event::EventEmitter>(std::move(pin), config, delays_.debounce, delays_.repeat)),
actions(std::move(actions_)),
event_delays(std::move(delays_))
Expand Down Expand Up @@ -382,14 +409,22 @@ bool _buttonWebSocketOnKeyCheck(const char * key, JsonVariant&) {

#endif // WEB_SUPPORT

ButtonCustomAction _button_custom_action { nullptr };

void buttonSetCustomAction(ButtonCustomAction action) {
_button_custom_action = action;
}

bool buttonState(unsigned char id) {
if (id >= _buttons.size()) return false;
return _buttons[id].state();
return (id < _buttons.size())
? _buttons[id].state()
: false;
}

button_action_t buttonAction(unsigned char id, const button_event_t event) {
if (id >= _buttons.size()) return 0;
return _buttonDecodeEventAction(_buttons[id].actions, event);
ButtonAction buttonAction(unsigned char id, const button_event_t event) {
return (id < _buttons.size())
? _buttonDecodeEventAction(_buttons[id].actions, event)
: ButtonAction::None;
}

// Note that we don't directly return F(...), but use a temporary to assign it conditionally
Expand Down Expand Up @@ -442,21 +477,28 @@ unsigned char _buttonRelaySetting(unsigned char id) {
return relays[id];
}

void _buttonRelayAction(unsigned char id, button_action_t action) {
void _buttonRelayAction(unsigned char id, ButtonAction action) {
auto relayId = _buttonRelaySetting(id);

switch (action) {
case BUTTON_ACTION_TOGGLE:
case ButtonAction::Toggle:
relayToggle(relayId);
break;

case BUTTON_ACTION_ON:
case ButtonAction::On:
relayStatus(relayId, true);
break;

case BUTTON_ACTION_OFF:
case ButtonAction::Off:
relayStatus(relayId, false);
break;

case ButtonAction::Pulse:
// TODO
break;

default:
break;
}
}

Expand All @@ -470,75 +512,88 @@ void buttonEvent(unsigned char id, button_event_t event) {
if (event == button_event_t::None) return;

auto& button = _buttons[id];

auto action = _buttonDecodeEventAction(button.actions, event);

#if BROKER_SUPPORT
ButtonBroker::Publish(id, event);
#endif
#if BROKER_SUPPORT
ButtonBroker::Publish(id, event);
#endif

#if MQTT_SUPPORT
if (action || _buttons_mqtt_send_all[id]) {
mqttSend(MQTT_TOPIC_BUTTON, id, _buttonEventString(event).c_str(), false, _buttons_mqtt_retain[id]);
}
#endif
#if MQTT_SUPPORT
if ((action != ButtonAction::None) || _buttons_mqtt_send_all[id]) {
mqttSend(MQTT_TOPIC_BUTTON, id, _buttonEventString(event).c_str(), false, _buttons_mqtt_retain[id]);
}
#endif

switch (action) {

#if RELAY_SUPPORT
case BUTTON_ACTION_TOGGLE:
case BUTTON_ACTION_ON:
case BUTTON_ACTION_OFF:
_buttonRelayAction(id, action);
break;
#endif
#if RELAY_SUPPORT
case ButtonAction::Toggle:
case ButtonAction::On:
case ButtonAction::Off:
case ButtonAction::Pulse:
_buttonRelayAction(id, action);
break;
#endif

case BUTTON_ACTION_AP:
if (wifiState() & WIFI_STATE_AP) {
wifiStartSTA();
} else {
wifiStartAP();
}
break;
case ButtonAction::AccessPoint:
if (wifiState() & WIFI_STATE_AP) {
wifiStartSTA();
} else {
wifiStartAP();
}
break;

case BUTTON_ACTION_RESET:
deferredReset(100, CUSTOM_RESET_HARDWARE);
break;
case ButtonAction::Reset:
deferredReset(100, CUSTOM_RESET_HARDWARE);
break;

case BUTTON_ACTION_FACTORY:
DEBUG_MSG_P(PSTR("\n\nFACTORY RESET\n\n"));
resetSettings();
deferredReset(100, CUSTOM_RESET_FACTORY);
break;
case ButtonAction::FactoryReset:
DEBUG_MSG_P(PSTR("\n\nFACTORY RESET\n\n"));
resetSettings();
deferredReset(100, CUSTOM_RESET_FACTORY);
break;

#if defined(JUSTWIFI_ENABLE_WPS)
case BUTTON_ACTION_WPS:
wifiStartWPS();
break;
#endif // defined(JUSTWIFI_ENABLE_WPS)
case ButtonAction::Wps:
#if defined(JUSTWIFI_ENABLE_WPS)
wifiStartWPS();
#endif
break;

#if defined(JUSTWIFI_ENABLE_SMARTCONFIG)
case BUTTON_ACTION_SMART_CONFIG:
wifiStartSmartConfig();
break;
#endif // defined(JUSTWIFI_ENABLE_SMARTCONFIG)
case ButtonAction::SmartConfig:
#if defined(JUSTWIFI_ENABLE_SMARTCONFIG)
wifiStartSmartConfig();
#endif
break;

#if LIGHT_PROVIDER != LIGHT_PROVIDER_NONE
case BUTTON_ACTION_DIM_UP:
lightBrightnessStep(1);
lightUpdate();
break;
case ButtonAction::BrightnessIncrease:
#if LIGHT_PROVIDER != LIGHT_PROVIDER_NONE
lightBrightnessStep(1);
lightUpdate();
#endif
break;

case BUTTON_ACTION_DIM_DOWN:
lightBrightnessStep(-1);
lightUpdate();
break;
#endif // LIGHT_PROVIDER != LIGHT_PROVIDER_NONE
case ButtonAction::BrightnessDecrease:
#if LIGHT_PROVIDER != LIGHT_PROVIDER_NONE
lightBrightnessStep(-1);
lightUpdate();
#endif
break;

#if THERMOSTAT_DISPLAY_SUPPORT
case BUTTON_ACTION_DISPLAY_ON:
displayOn();
break;
#endif
case ButtonAction::DisplayOn:
#if THERMOSTAT_DISPLAY_SUPPORT
displayOn();
#endif
break;

case ButtonAction::Custom:
if (_button_custom_action) {
_button_custom_action(id);
}
break;

case ButtonAction::None:
break;

}

Expand Down Expand Up @@ -746,8 +801,8 @@ BasePinPtr _buttonGpioPin(unsigned char index, ButtonProvider provider) {
return result;
}

inline button_actions_t _buttonActions(unsigned char index) {
button_actions_t actions {
ButtonActions _buttonActions(unsigned char index) {
return {
getSetting({"btnPress", index}, _buttonPress(index)),
getSetting({"btnRlse", index}, _buttonRelease(index)),
getSetting({"btnClick", index}, _buttonClick(index)),
Expand All @@ -756,20 +811,17 @@ inline button_actions_t _buttonActions(unsigned char index) {
getSetting({"btnLLclk", index}, _buttonLongLongClick(index)),
getSetting({"btnTclk", index}, _buttonTripleClick(index))
};

return actions;
}

// Note that we use settings without indexes as default values
// Note that we use settings without indexes as default values to preserve backwards compatibility

button_event_delays_t _buttonDelays(unsigned char index) {
button_event_delays_t delays {
return {
_buttonGetSetting("btnDebDel", index, _buttonDebounceDelay(index)),
_buttonGetSetting("btnRepDel", index, _buttonRepeatDelay(index)),
_buttonGetSetting("btnLclkDel", index, _buttonLongClickDelay(index)),
_buttonGetSetting("btnLLclkDel", index, _buttonLongLongClickDelay(index)),
};

return delays;
}

bool _buttonSetupProvider(unsigned char index, ButtonProvider provider) {
Expand Down
Loading

0 comments on commit ef194c9

Please sign in to comment.