AceButton  1.6
An adjustable, compact, event-driven button library for Arduino.
ButtonConfig.h
1 /*
2 MIT License
3 
4 Copyright (c) 2018 Brian T. Park
5 
6 Permission is hereby granted, free of charge, to any person obtaining a copy
7 of this software and associated documentation files (the "Software"), to deal
8 in the Software without restriction, including without limitation the rights
9 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 copies of the Software, and to permit persons to whom the Software is
11 furnished to do so, subject to the following conditions:
12 
13 The above copyright notice and this permission notice shall be included in all
14 copies or substantial portions of the Software.
15 
16 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 SOFTWARE.
23 */
24 
25 #ifndef ACE_BUTTON_BUTTON_CONFIG_H
26 #define ACE_BUTTON_BUTTON_CONFIG_H
27 
28 #include <Arduino.h>
29 #include "IEventHandler.h"
30 
31 // https://stackoverflow.com/questions/295120
32 #if defined(__GNUC__) || defined(__clang__)
33  #define DEPRECATED __attribute__((deprecated))
34 #elif defined(_MSC_VER)
35  #define DEPRECATED __declspec(deprecated)
36 #else
37  #pragma message("WARNING: You need to implement DEPRECATED for this compiler")
38  #define DEPRECATED
39 #endif
40 
41 namespace ace_button {
42 
43 class AceButton;
44 
66 class ButtonConfig {
67  public:
68  // Various timing constants, in milliseconds.
69  //
70  // Note that the timing constants are stored as uint16_t (2
71  // bytes) instead of unsigned long (4 bytes) which is the type returned by
72  // the millis() system method. It turns out that we can store and perform
73  // all timing calculations using uint16_t without ill effect, as long as the
74  // polling of AceButton::check() happens more frequently than the rollover
75  // time of a uint16_t (i.e. 65.536 seconds) and certain precautions (e.g.
76  // AceButton::checkOrphanedClick()) are taken before a uint16_t rollover
77  // happens. In theory, these additional precautions would be needed even if
78  // an 'unsigned long' is used but almost no one does them because they
79  // assume that their code won't be running continuously for the rollover
80  // time of an 'unsigned long' (i.e. 49.7 days).
81 
83  static const uint16_t kDebounceDelay = 20;
84 
86  static const uint16_t kClickDelay = 200;
87 
89  static const uint16_t kDoubleClickDelay = 400;
90 
92  static const uint16_t kLongPressDelay = 1000;
93 
95  static const uint16_t kRepeatPressDelay = 1000;
96 
98  static const uint16_t kRepeatPressInterval = 200;
99 
100  // Various features controlled by feature flags.
101 
107  typedef uint16_t FeatureFlagType;
108 
110  static const FeatureFlagType kFeatureClick = 0x01;
111 
118 
120  static const FeatureFlagType kFeatureLongPress = 0x04;
121 
124 
127 
134 
137 
140 
148 
154 
168 
176  typedef void (*EventHandler)(AceButton* button, uint8_t eventType,
177  uint8_t buttonState);
178 
180  ButtonConfig() = default;
181 
182  #if defined(ESP8266) || defined(ESP32)
183 
195  virtual ~ButtonConfig() = default;
196  #endif
197 
199  uint16_t getDebounceDelay() const { return mDebounceDelay; }
200 
202  uint16_t getClickDelay() const { return mClickDelay; }
203 
208  uint16_t getDoubleClickDelay() const {
209  return mDoubleClickDelay;
210  }
211 
213  uint16_t getLongPressDelay() const {
214  return mLongPressDelay;
215  }
216 
223  uint16_t getRepeatPressDelay() const {
224  return mRepeatPressDelay;
225  }
226 
230  uint16_t getRepeatPressInterval() const {
231  return mRepeatPressInterval;
232  }
233 
235  void setDebounceDelay(uint16_t debounceDelay) {
236  mDebounceDelay = debounceDelay;
237  }
238 
240  void setClickDelay(uint16_t clickDelay) {
241  mClickDelay = clickDelay;
242  }
243 
245  void setDoubleClickDelay(uint16_t doubleClickDelay) {
246  mDoubleClickDelay = doubleClickDelay;
247  }
248 
250  void setLongPressDelay(uint16_t longPressDelay) {
251  mLongPressDelay = longPressDelay;
252  }
253 
255  void setRepeatPressDelay(uint16_t repeatPressDelay) {
256  mRepeatPressDelay = repeatPressDelay;
257  }
258 
260  void setRepeatPressInterval(uint16_t repeatPressInterval) {
261  mRepeatPressInterval = repeatPressInterval;
262  }
263 
264  // The getClock() and readButton() are external dependencies that normally
265  // would be injected using separate classes, but in the interest of saving
266  // RAM in an embedded environment, we expose them in this class instead.
267 
276  virtual unsigned long getClock() { return millis(); }
277 
286  virtual int readButton(uint8_t pin) {
287  return digitalRead(pin);
288  }
289 
290  // These methods provide access to various feature flags that control the
291  // functionality of the AceButton.
292 
294  bool isFeature(FeatureFlagType features) const {
295  return mFeatureFlags & features;
296  }
297 
299  void setFeature(FeatureFlagType features) {
300  mFeatureFlags |= features;
301  }
302 
304  void clearFeature(FeatureFlagType features) {
305  mFeatureFlags &= ~features;
306  }
307 
313  void resetFeatures() {
314  // NOTE: If any additional kInternalFeatureXxx flag is added, it must be
315  // added here like this:
316  // mFeatureFlags &= (kInternalFeatureIEventHandler | kInternalFeatureXxx)
317  mFeatureFlags &= kInternalFeatureIEventHandler;
318  }
319 
320  // EventHandler
321 
331  EventHandler getEventHandler() const DEPRECATED {
332  return reinterpret_cast<EventHandler>(mEventHandler);
333  }
334 
339  void dispatchEvent(AceButton* button, uint8_t eventType,
340  uint8_t buttonState) const {
341 
342  if (! mEventHandler) return;
343 
345  IEventHandler* eventHandler =
346  reinterpret_cast<IEventHandler*>(mEventHandler);
347  eventHandler->handleEvent(button, eventType, buttonState);
348  } else {
349  EventHandler eventHandler =
350  reinterpret_cast<EventHandler>(mEventHandler);
351  eventHandler(button, eventType, buttonState);
352  }
353  }
354 
359  void setEventHandler(EventHandler eventHandler) {
360  mEventHandler = reinterpret_cast<void*>(eventHandler);
362  }
363 
368  void setIEventHandler(IEventHandler* eventHandler) {
369  mEventHandler = eventHandler;
371  }
372 
378  return &sSystemButtonConfig;
379  }
380 
381  private:
386  static ButtonConfig sSystemButtonConfig;
387 
388  // Disable copy-constructor and assignment operator
389  ButtonConfig(const ButtonConfig&) = delete;
390  ButtonConfig& operator=(const ButtonConfig&) = delete;
391 
393  void* mEventHandler = nullptr;
394 
396  FeatureFlagType mFeatureFlags = 0;
397 
398  uint16_t mDebounceDelay = kDebounceDelay;
399  uint16_t mClickDelay = kClickDelay;
400  uint16_t mDoubleClickDelay = kDoubleClickDelay;
401  uint16_t mLongPressDelay = kLongPressDelay;
402  uint16_t mRepeatPressDelay = kRepeatPressDelay;
403  uint16_t mRepeatPressInterval = kRepeatPressInterval;
404 };
405 
406 }
407 #endif
ace_button::ButtonConfig::getRepeatPressDelay
uint16_t getRepeatPressDelay() const
Milliseconds that a button needs to be Pressed down before the start of the sequence of RepeatPressed...
Definition: ButtonConfig.h:223
ace_button::ButtonConfig::getLongPressDelay
uint16_t getLongPressDelay() const
Milliseconds for a long press event.
Definition: ButtonConfig.h:213
ace_button::ButtonConfig::kFeatureSuppressClickBeforeDoubleClick
static const FeatureFlagType kFeatureSuppressClickBeforeDoubleClick
Flag to suppress kEventClicked before a kEventDoubleClicked.
Definition: ButtonConfig.h:147
ace_button::ButtonConfig::kFeatureSuppressAfterClick
static const FeatureFlagType kFeatureSuppressAfterClick
Flag to suppress kEventReleased after a kEventClicked.
Definition: ButtonConfig.h:126
ace_button::ButtonConfig::kFeatureClick
static const FeatureFlagType kFeatureClick
Flag to activate the AceButton::kEventClicked event.
Definition: ButtonConfig.h:110
ace_button::ButtonConfig::setDebounceDelay
void setDebounceDelay(uint16_t debounceDelay)
Set the debounceDelay.
Definition: ButtonConfig.h:235
ace_button::ButtonConfig::kInternalFeatureIEventHandler
static const FeatureFlagType kInternalFeatureIEventHandler
Internal flag to indicate that mEventHandler is an IEventHandler object pointer instead of an EventHa...
Definition: ButtonConfig.h:153
ace_button::ButtonConfig::setIEventHandler
void setIEventHandler(IEventHandler *eventHandler)
Install the IEventHandler object pointer.
Definition: ButtonConfig.h:368
ace_button::ButtonConfig::getClock
virtual unsigned long getClock()
Return the milliseconds of the internal clock.
Definition: ButtonConfig.h:276
ace_button::ButtonConfig::kFeatureRepeatPress
static const FeatureFlagType kFeatureRepeatPress
Flag to activate the AceButton::kEventRepeatPressed event.
Definition: ButtonConfig.h:123
ace_button::IEventHandler
Interface of the class that will handle the button event.
Definition: IEventHandler.h:39
ace_button::ButtonConfig::kDebounceDelay
static const uint16_t kDebounceDelay
Default value returned by getDebounceDelay().
Definition: ButtonConfig.h:83
ace_button::IEventHandler::handleEvent
virtual void handleEvent(AceButton *button, uint8_t eventType, uint8_t buttonState)=0
Handle the button event.
ace_button::ButtonConfig::setEventHandler
void setEventHandler(EventHandler eventHandler)
Install the EventHandler function pointer.
Definition: ButtonConfig.h:359
ace_button::ButtonConfig::setLongPressDelay
void setLongPressDelay(uint16_t longPressDelay)
Set the longPressDelay.
Definition: ButtonConfig.h:250
ace_button::ButtonConfig::dispatchEvent
void dispatchEvent(AceButton *button, uint8_t eventType, uint8_t buttonState) const
Dispatch the event to the handler.
Definition: ButtonConfig.h:339
ace_button::ButtonConfig::kRepeatPressDelay
static const uint16_t kRepeatPressDelay
Default value returned by getRepeatPressDelay().
Definition: ButtonConfig.h:95
ace_button::ButtonConfig::getDebounceDelay
uint16_t getDebounceDelay() const
Milliseconds to wait for debouncing.
Definition: ButtonConfig.h:199
ace_button::ButtonConfig::kFeatureSuppressAfterLongPress
static const FeatureFlagType kFeatureSuppressAfterLongPress
Flag to suppress kEventReleased after a kEventLongPressed.
Definition: ButtonConfig.h:136
ace_button::ButtonConfig::isFeature
bool isFeature(FeatureFlagType features) const
Check if the given features are enabled.
Definition: ButtonConfig.h:294
ace_button::AceButton
An Adjustable Compact Event-driven (ACE) Button library that debounces and dispatches button events t...
Definition: AceButton.h:50
ace_button::ButtonConfig::getDoubleClickDelay
uint16_t getDoubleClickDelay() const
Milliseconds between the first and second click to register as a double-click.
Definition: ButtonConfig.h:208
ace_button::ButtonConfig::getSystemButtonConfig
static ButtonConfig * getSystemButtonConfig()
Return a pointer to the singleton instance of the ButtonConfig which is attached to all AceButton ins...
Definition: ButtonConfig.h:377
ace_button::ButtonConfig::getClickDelay
uint16_t getClickDelay() const
Milliseconds to wait for a possible click.
Definition: ButtonConfig.h:202
ace_button::ButtonConfig::kFeatureSuppressAfterDoubleClick
static const FeatureFlagType kFeatureSuppressAfterDoubleClick
Flag to suppress kEventReleased after a kEventDoubleClicked.
Definition: ButtonConfig.h:133
ace_button::ButtonConfig
Class that defines the timing parameters and event handler of an AceButton or a group of AceButton in...
Definition: ButtonConfig.h:66
ace_button::ButtonConfig::setRepeatPressDelay
void setRepeatPressDelay(uint16_t repeatPressDelay)
Set the repeatPressDelay.
Definition: ButtonConfig.h:255
ace_button::ButtonConfig::EventHandler
void(* EventHandler)(AceButton *button, uint8_t eventType, uint8_t buttonState)
The event handler signature.
Definition: ButtonConfig.h:176
ace_button::ButtonConfig::kDoubleClickDelay
static const uint16_t kDoubleClickDelay
Default value returned by getDoubleClickDelay().
Definition: ButtonConfig.h:89
ace_button::ButtonConfig::getEventHandler
EventHandler getEventHandler() const DEPRECATED
Return the eventHandler function pointer.
Definition: ButtonConfig.h:331
ace_button::ButtonConfig::setDoubleClickDelay
void setDoubleClickDelay(uint16_t doubleClickDelay)
Set the doubleClickDelay.
Definition: ButtonConfig.h:245
ace_button::ButtonConfig::ButtonConfig
ButtonConfig()=default
Constructor.
ace_button::ButtonConfig::kLongPressDelay
static const uint16_t kLongPressDelay
Default value returned by getLongPressDelay().
Definition: ButtonConfig.h:92
ace_button::ButtonConfig::getRepeatPressInterval
uint16_t getRepeatPressInterval() const
Milliseconds between two successive RepeatPressed events.
Definition: ButtonConfig.h:230
ace_button::ButtonConfig::setClickDelay
void setClickDelay(uint16_t clickDelay)
Set the clickDelay.
Definition: ButtonConfig.h:240
ace_button::ButtonConfig::setRepeatPressInterval
void setRepeatPressInterval(uint16_t repeatPressInterval)
Set the repeatPressInterval.
Definition: ButtonConfig.h:260
ace_button::ButtonConfig::kRepeatPressInterval
static const uint16_t kRepeatPressInterval
Default value returned by getRepeatPressInterval().
Definition: ButtonConfig.h:98
ace_button::ButtonConfig::resetFeatures
void resetFeatures()
Disable all (externally visible) features.
Definition: ButtonConfig.h:313
ace_button::ButtonConfig::clearFeature
void clearFeature(FeatureFlagType features)
Disable the given features.
Definition: ButtonConfig.h:304
ace_button::ButtonConfig::kFeatureDoubleClick
static const FeatureFlagType kFeatureDoubleClick
Flag to activate the AceButton::kEventDoubleClicked event.
Definition: ButtonConfig.h:117
ace_button::ButtonConfig::kFeatureSuppressAll
static const FeatureFlagType kFeatureSuppressAll
Convenience flag to suppress all suppressions.
Definition: ButtonConfig.h:162
ace_button::ButtonConfig::setFeature
void setFeature(FeatureFlagType features)
Enable the given features.
Definition: ButtonConfig.h:299
ace_button::ButtonConfig::kClickDelay
static const uint16_t kClickDelay
Default value returned by getClickDelay().
Definition: ButtonConfig.h:86
ace_button::ButtonConfig::kFeatureLongPress
static const FeatureFlagType kFeatureLongPress
Flag to activate the AceButton::kEventLongPress event.
Definition: ButtonConfig.h:120
ace_button::ButtonConfig::kFeatureSuppressAfterRepeatPress
static const FeatureFlagType kFeatureSuppressAfterRepeatPress
Flag to suppress kEventReleased after a kEventRepeatPressed.
Definition: ButtonConfig.h:139
ace_button::ButtonConfig::FeatureFlagType
uint16_t FeatureFlagType
Type of the feature flag.
Definition: ButtonConfig.h:107
ace_button::ButtonConfig::readButton
virtual int readButton(uint8_t pin)
Return the HIGH or LOW state of the button.
Definition: ButtonConfig.h:286