Encoder
drivers
drivers/Encoder.h
driver
stable
stable
Driver: Encoder Lecture d'un encodeur rotatif quadrature (2 voies A/B) par interruptions, avec suivi de position, de vitesse et de sens de rotation. Fonctionnalités : /
Méthodes publiques
| Méthode | Description | Paramètres | Retour |
|---|---|---|---|
|
Encoder()
Encoder(uint8_t pinA, uint8_t pinB, bool usePullup = true);
|
Construit l'objet encodeur (ne configure pas encore les broches). / | pinA: Broche de la voie A de l'encodeur pinB: Broche de la voie B de l'encodeur usePullup: Active les résistances de tirage internes (défaut: true) / |
|
|
Encoder()
Encoder();
|
|||
|
begin()
begin();
|
Configure les broches et attache les interruptions. d'instance (registre statique) sont déjà utilisés / | truetrue si l'initialisation réussit, false si les 2 emplacements d'instance (registre statique) sont déjà utilisés / |
|
|
end()
end();
|
Détache les interruptions et libère l'emplacement d'instance. / | ||
|
getCount()
getCount() const;
|
|||
|
getTurns()
getTurns() const;
|
|||
|
getAngle()
getAngle() const;
|
|||
|
getRadians()
getRadians() const;
|
|||
|
getNormalized()
getNormalized() const;
|
|||
|
getDirection()
getDirection() const;
|
|||
|
getSpeed()
getSpeed() const;
|
|||
|
getRPM()
getRPM() const;
|
|||
|
setCPR()
setCPR(uint16_t cpr) {
|
Définit le nombre de transitions par tour (Counts Per Revolution). / | cpr: Résolution de l'encodeur (dépend du modèle physique) / | |
|
setDebounce()
setDebounce(bool enable, uint32_t debounceUs = 1000) {
|
Active/désactive l'anti-rebond logiciel sur les transitions. / | enable: Active l'anti-rebond si true debounceUs: Durée minimale entre 2 transitions valides, en µs (défaut: 1000) / |
|
|
setReverse()
setReverse(bool reverse) {
|
Inverse le sens logique de comptage (utile si le câblage A/B est inversé). / | reverse: true pour inverser le sens / | |
|
reset()
reset();
|
Remet le comptage de position à zéro. / | ||
|
setPosition()
setPosition(int32_t newCount);
|
Force la position courante à une valeur donnée. / | newCount: Nouvelle valeur de comptage / | |
|
hasMoved()
hasMoved() const;
|
Indique si l'encodeur a bougé depuis le dernier appel. / | truetrue si un mouvement a été détecté / |
|
|
waitForMovement()
waitForMovement(uint32_t timeoutMs = 0);
|
Bloque jusqu'à détection d'un mouvement, ou expiration d'un délai. / | timeoutMs: Délai d'attente maximal en ms (0 = attente infinie) | truetrue si un mouvement a été détecté avant expiration du délai / |
|
printDebugInfo()
printDebugInfo(Stream& stream = Serial) const;
|
Affiche l'état complet de l'encodeur (position, vitesse, sens...) sur un flux série. / | stream: Flux de sortie utilisé (défaut: Serial) / | |
|
_handleA()
_handleA();
|
|||
|
_handleB()
_handleB();
|
Méthodes privées
_process(uint8_t currState);;
_updateSpeed();;
Variables membres
uint8_t _instanceCount;
bool _usePullup;
bool _reverse;
uint16_t _cpr;
int32_t _count;
int32_t _lastCount;
Direction _direction;
float _speed;
uint32_t _lastSpeedTime;
int32_t _lastSpeedCount;
bool _debounceEnabled;
uint32_t _debounceUs;
uint32_t _lastIsrTime;
uint8_t _lastState;
bool _initialized;
uint8_t _isrIndex;
Code source
#pragma once
#include <Arduino.h>
namespace crepp::drivers {
/*
* =========================
* Driver: Encoder
* -------------------------
* Lecture d'un encodeur rotatif quadrature (2 voies A/B) par interruptions,
* avec suivi de position, de vitesse et de sens de rotation.
*
* @badge driver
* @badge stable
*
* Fonctionnalités :
* - Comptage incrémental de position (avec table de Gray pour un décodage fiable)
* - Calcul de la vitesse et du régime (RPM) à partir du comptage
* - Anti-rebond configurable, inversion de sens, remise à zéro
* - Jusqu'à 2 instances simultanées (limite matérielle des ISR globales)
* =========================
*/
class Encoder {
public:
/**
* @brief Sens de rotation détecté par l'encodeur.
*/
enum class Direction {
NONE = 0, ///< Pas de mouvement détecté
CLOCKWISE = 1, ///< Rotation dans le sens horaire
COUNTER_CLOCKWISE = -1 ///< Rotation dans le sens anti-horaire
};
/**
* @brief Construit l'objet encodeur (ne configure pas encore les broches).
* @param pinA Broche de la voie A de l'encodeur
* @param pinB Broche de la voie B de l'encodeur
* @param usePullup Active les résistances de tirage internes (défaut: true)
*/
Encoder(uint8_t pinA, uint8_t pinB, bool usePullup = true);
~Encoder();
/**
* @brief Configure les broches et attache les interruptions.
* @return true si l'initialisation réussit, false si les 2 emplacements
* d'instance (registre statique) sont déjà utilisés
*/
bool begin();
/**
* @brief Détache les interruptions et libère l'emplacement d'instance.
*/
void end();
// Getters position
/// Comptage brut de transitions depuis le dernier reset()
int32_t getCount() const;
/// Nombre de tours complets effectués (déduit du CPR configuré)
int32_t getTurns() const;
/// Angle courant en degrés (0-360), déduit du CPR configuré
float getAngle() const;
/// Angle courant en radians, déduit du CPR configuré
float getRadians() const;
/// Position normalisée entre 0.0 et 1.0 sur un tour
float getNormalized() const;
// Getters mouvement
/// Sens de rotation détecté au dernier changement d'état
Direction getDirection() const;
/// Vitesse angulaire courante (unité dépendante du CPR configuré)
float getSpeed() const;
/// Régime de rotation courant, en tours par minute
float getRPM() const;
// Configuration
/**
* @brief Définit le nombre de transitions par tour (Counts Per Revolution).
* @param cpr Résolution de l'encodeur (dépend du modèle physique)
*/
void setCPR(uint16_t cpr) { _cpr = cpr; }
/**
* @brief Active/désactive l'anti-rebond logiciel sur les transitions.
* @param enable Active l'anti-rebond si true
* @param debounceUs Durée minimale entre 2 transitions valides, en µs (défaut: 1000)
*/
void setDebounce(bool enable, uint32_t debounceUs = 1000) { _debounceEnabled = enable; _debounceUs = debounceUs; }
/**
* @brief Inverse le sens logique de comptage (utile si le câblage A/B est inversé).
* @param reverse true pour inverser le sens
*/
void setReverse(bool reverse) { _reverse = reverse; }
// Contrôle
/**
* @brief Remet le comptage de position à zéro.
*/
void reset();
/**
* @brief Force la position courante à une valeur donnée.
* @param newCount Nouvelle valeur de comptage
*/
void setPosition(int32_t newCount);
// Utilitaires
/**
* @brief Indique si l'encodeur a bougé depuis le dernier appel.
* @return true si un mouvement a été détecté
*/
bool hasMoved() const;
/**
* @brief Bloque jusqu'à détection d'un mouvement, ou expiration d'un délai.
* @param timeoutMs Délai d'attente maximal en ms (0 = attente infinie)
* @return true si un mouvement a été détecté avant expiration du délai
*/
bool waitForMovement(uint32_t timeoutMs = 0);
/**
* @brief Affiche l'état complet de l'encodeur (position, vitesse, sens...) sur un flux série.
* @param stream Flux de sortie utilisé (défaut: Serial)
*/
void printDebugInfo(Stream& stream = Serial) const;
/// @internal Appelée par l'ISR globale de la voie A — ne pas appeler directement
void _handleA();
/// @internal Appelée par l'ISR globale de la voie B — ne pas appeler directement
void _handleB();
/// @internal Registre statique des instances actives (2 encodeurs max, limite ISR)
static Encoder* _instances[2];
/// @internal Nombre d'instances actuellement enregistrées
static uint8_t _instanceCount;
private:
uint8_t _pinA, _pinB;
bool _usePullup;
bool _reverse;
uint16_t _cpr;
volatile int32_t _count;
mutable volatile int32_t _lastCount;
volatile Direction _direction;
volatile float _speed;
volatile uint32_t _lastSpeedTime;
volatile int32_t _lastSpeedCount;
bool _debounceEnabled;
uint32_t _debounceUs;
volatile uint32_t _lastIsrTime;
volatile uint8_t _lastState;
volatile bool _initialized;
uint8_t _isrIndex; ///< Slot ISR attribué à begin() (0 ou 1), 0xFF si non attribué
/// Traite un changement d'état brut (2 bits AB) et met à jour comptage/sens
void _process(uint8_t currState);
/// Recalcule la vitesse à partir de l'évolution du comptage dans le temps
void _updateSpeed();
static const int8_t GRAY_TABLE[16]; ///< Table de décodage de Gray pour les 4 transitions valides
};
} // namespace crepp::drivers