VersaMCU/doc/02_encoder.md
2026-03-30 19:52:37 +02:00

45 lines
1.5 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Quadratur-Encoder
**Dateien:** `hal/encoder.h`, `hal/encoder.cpp`, `config/pins.h`
## Hardware
4 mechanische Quadratur-Encoder mit je 2 Phasen-Pins (A, B). Pins sind INPUT_PULLUP.
Encoder-SW-Tasten laufen **nicht** durch diesen HAL, sondern durch den Matrix-Scan (COL_0).
## Dekodierung
4-State-Lookup-Table über `(prev_state << 2) | cur_state`:
```
Zustand = (A << 1) | B → 4 Bits: 00 / 01 / 10 / 11
LUT[prev<<2 | cur] → +1 (CW), -1 (CCW), 0 (ungültig/Prellen)
```
Mechanische Encoder erzeugen 4 Flanken pro Raste → Akkumulator zählt Halbschritte.
Ein Event wird erst gefeuert wenn `|accum| >= 4` (= ein vollständiger Klick).
## ISR-Aufbau
8 ISR-Wrapper (je einer pro Pin, da `attachInterrupt` keinen Parameter unterstützt):
```cpp
static void isr_enc0_a() { handle_encoder(0); }
static void isr_enc0_b() { handle_encoder(0); }
// ... analog für Encoder 13
```
`attachInterrupt(..., CHANGE)` auf beiden Pins jedes Encoders.
`handle_encoder()``encoder_cb(enc_id, direction)``CEventQueue::push(ENC_CW / ENC_CCW)`
## ISR-Sicherheit
- `s_state[]` und `s_accum[]` sind `volatile`
- `CEventQueue::push()` ist ISR-sicher (atomare Index-Inkremente auf Single-Core-M0+, kein Heap)
- Der Callback-Pointer `s_cb` wird einmalig in `setup()` gesetzt, bevor Interrupts aktiviert werden
## Initialisierung
Initialer Zustand von A/B wird beim `encoder_init()` gelesen damit der erste Interrupt korrekt ausgewertet wird (kein "Phantom-Step" beim Einschalten).