2025-05-27 19:10:56 -07:00
|
|
|
#pragma once
|
|
|
|
|
|
|
|
|
|
#include <Arduino.h>
|
|
|
|
|
#include <functional>
|
|
|
|
|
|
|
|
|
|
// Button timing configuration
|
|
|
|
|
#define BUTTON_DEBOUNCE_TIME_MS 50 // Debounce time in ms
|
2025-05-28 16:45:41 -07:00
|
|
|
#define BUTTON_CLICK_TIMEOUT_MS 500 // Max time between clicks for multi-click
|
2025-05-30 20:32:49 -07:00
|
|
|
#define BUTTON_LONG_PRESS_TIME_MS 3000 // Time to trigger long press (3 seconds)
|
2025-05-27 19:10:56 -07:00
|
|
|
#define BUTTON_READ_INTERVAL_MS 10 // How often to read the button
|
|
|
|
|
|
|
|
|
|
class Button {
|
|
|
|
|
public:
|
|
|
|
|
enum EventType {
|
|
|
|
|
NONE,
|
|
|
|
|
SHORT_PRESS,
|
|
|
|
|
DOUBLE_PRESS,
|
|
|
|
|
TRIPLE_PRESS,
|
2025-06-18 11:52:16 +02:00
|
|
|
QUADRUPLE_PRESS,
|
2025-05-27 19:10:56 -07:00
|
|
|
LONG_PRESS,
|
|
|
|
|
ANY_PRESS
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
using EventCallback = std::function<void()>;
|
|
|
|
|
|
|
|
|
|
Button(uint8_t pin, bool activeState = LOW);
|
|
|
|
|
Button(uint8_t pin, bool activeState, bool isAnalog, uint16_t analogThreshold = 20);
|
|
|
|
|
|
|
|
|
|
void begin();
|
|
|
|
|
void update();
|
|
|
|
|
|
|
|
|
|
// Set callbacks for different events
|
|
|
|
|
void onShortPress(EventCallback callback) { _onShortPress = callback; }
|
|
|
|
|
void onDoublePress(EventCallback callback) { _onDoublePress = callback; }
|
|
|
|
|
void onTriplePress(EventCallback callback) { _onTriplePress = callback; }
|
2025-06-18 11:52:16 +02:00
|
|
|
void onQuadruplePress(EventCallback callback) { _onQuadruplePress = callback; }
|
2025-05-27 19:10:56 -07:00
|
|
|
void onLongPress(EventCallback callback) { _onLongPress = callback; }
|
2025-05-30 20:32:49 -07:00
|
|
|
void onAnyPress(EventCallback callback) { _onAnyPress = callback; }
|
2025-05-27 19:10:56 -07:00
|
|
|
|
|
|
|
|
// State getters
|
2025-05-30 22:14:37 -07:00
|
|
|
bool isPressed() const { return _currentState; }
|
2025-05-27 19:10:56 -07:00
|
|
|
EventType getLastEvent() const { return _lastEvent; }
|
|
|
|
|
|
|
|
|
|
private:
|
|
|
|
|
enum State {
|
|
|
|
|
IDLE,
|
|
|
|
|
PRESSED,
|
|
|
|
|
RELEASED,
|
|
|
|
|
WAITING_FOR_MULTI_CLICK
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
uint8_t _pin;
|
|
|
|
|
bool _activeState;
|
|
|
|
|
bool _isAnalog;
|
|
|
|
|
uint16_t _analogThreshold;
|
|
|
|
|
|
|
|
|
|
State _state = IDLE;
|
|
|
|
|
bool _currentState;
|
|
|
|
|
bool _lastState;
|
|
|
|
|
|
|
|
|
|
uint32_t _stateChangeTime = 0;
|
|
|
|
|
uint32_t _pressTime = 0;
|
|
|
|
|
uint32_t _releaseTime = 0;
|
|
|
|
|
uint32_t _lastReadTime = 0;
|
|
|
|
|
|
|
|
|
|
uint8_t _clickCount = 0;
|
|
|
|
|
EventType _lastEvent = NONE;
|
|
|
|
|
|
|
|
|
|
// Callbacks
|
|
|
|
|
EventCallback _onShortPress = nullptr;
|
|
|
|
|
EventCallback _onDoublePress = nullptr;
|
|
|
|
|
EventCallback _onTriplePress = nullptr;
|
2025-06-18 11:52:16 +02:00
|
|
|
EventCallback _onQuadruplePress = nullptr;
|
2025-05-27 19:10:56 -07:00
|
|
|
EventCallback _onLongPress = nullptr;
|
|
|
|
|
EventCallback _onAnyPress = nullptr;
|
|
|
|
|
|
|
|
|
|
bool readButton();
|
|
|
|
|
void handleStateChange();
|
|
|
|
|
void triggerEvent(EventType event);
|
|
|
|
|
};
|