52 lines
1.1 KiB
Rust
52 lines
1.1 KiB
Rust
|
use embedded_hal::digital::v2::InputPin;
|
||
|
|
||
|
pub struct Rotary<A, B> {
|
||
|
pin_a: A,
|
||
|
pin_b: B,
|
||
|
state: u8,
|
||
|
}
|
||
|
|
||
|
pub enum Direction {
|
||
|
Clockwise,
|
||
|
CounterClockwise,
|
||
|
None,
|
||
|
}
|
||
|
|
||
|
impl<A, B> Rotary<A, B>
|
||
|
where
|
||
|
A: InputPin,
|
||
|
B: InputPin,
|
||
|
{
|
||
|
pub fn new(pin_a: A, pin_b: B) -> Self {
|
||
|
Self {
|
||
|
pin_a,
|
||
|
pin_b,
|
||
|
state: 0,
|
||
|
}
|
||
|
}
|
||
|
|
||
|
pub fn update(&mut self) -> Direction {
|
||
|
let a = self.pin_a.is_low();
|
||
|
let b = self.pin_b.is_low();
|
||
|
|
||
|
let new_state = match (a, b) {
|
||
|
(Ok(true), Ok(true)) => 0b00,
|
||
|
(Ok(true), Ok(false)) => 0b01,
|
||
|
(Ok(false), Ok(true)) => 0b10,
|
||
|
(Ok(false), Ok(false)) => 0b11,
|
||
|
_ => return Direction::None,
|
||
|
};
|
||
|
|
||
|
let direction = match (self.state, new_state) {
|
||
|
(0b10, 0b11) => Direction::Clockwise,
|
||
|
(0b01, 0b00) => Direction::Clockwise,
|
||
|
(0b01, 0b11) => Direction::CounterClockwise,
|
||
|
(0b10, 0b00) => Direction::CounterClockwise,
|
||
|
_ => Direction::None,
|
||
|
};
|
||
|
|
||
|
self.state = new_state;
|
||
|
direction
|
||
|
}
|
||
|
}
|