Skip to content
Snippets Groups Projects
Commit 406be08f authored by Stephen D's avatar Stephen D
Browse files

keyboard driver

parent b3c546ae
No related branches found
No related tags found
No related merge requests found
use core::convert::Infallible;
use core::{convert::Infallible, fmt::Display};
use embedded_hal::{
blocking::delay::{DelayMs, DelayUs},
digital::v2::{InputPin, OutputPin},
};
use rp2040_hal::Timer;
use rtt_target::rprintln;
use rtt_target::{rprint, rprintln};
const NONE: char = '\0';
const CALL_END: char = '\x01';
const L_SHIFT: char = '\x02';
const R_SHIFT: char = '\x03';
const ALT: char = '\x04';
const SYM: char = '\x05';
const BACK: char = '\x06';
const MENU: char = '\x07';
const BACKSPACE: char = '\x08';
const CALL_START: char = '\x09';
const TOUCHPAD_BUTTON: char = '\x0B';
const ENTER: char = '\n';
const KEYMAP: [[char; 8]; 6] = [
[CALL_END, ENTER, 'b', 'y', 'n', 'j', 'u', 'h'],
[NONE, BACKSPACE, '$', 'i', 'm', 'k', 'o', 'l'],
[NONE, 'p', 'x', 'd', 'z', L_SHIFT, 'e', 's'],
[NONE, R_SHIFT, 'v', 't', 'c', 'f', 'r', 'g'],
[NONE, 'a', ALT, SYM, ' ', '0', 'q', 'w'],
[
NONE,
NONE,
BACK,
MENU,
NONE,
CALL_START,
NONE,
TOUCHPAD_BUTTON,
],
];
enum KeyCode {
CallStart,
Menu,
Touchpad,
Back,
CallEnd,
Backspace,
Enter,
LeftShift,
RightShift,
Alt,
Sym,
Char(char),
}
impl KeyCode {
fn from_keyboard(c: char, alt: bool, shift: bool) -> Self {
match (alt, shift, c) {
(_, _, CALL_END) => KeyCode::CallEnd,
(_, _, L_SHIFT) => KeyCode::LeftShift,
(_, _, R_SHIFT) => KeyCode::RightShift,
(_, _, ALT) => KeyCode::Alt,
(_, _, SYM) => KeyCode::Sym,
(_, _, BACK) => KeyCode::Back,
(_, _, MENU) => KeyCode::Menu,
(_, _, BACKSPACE) => KeyCode::Backspace,
(_, _, CALL_START) => KeyCode::CallStart,
(_, _, TOUCHPAD_BUTTON) => KeyCode::Touchpad,
(_, _, ENTER) => KeyCode::Enter,
(false, false, _) => KeyCode::Char(c),
(true, _, _) => KeyCode::Char(altify(c)),
(false, true, _) => KeyCode::Char(c.to_ascii_uppercase()),
}
}
}
impl Display for KeyCode {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
match self {
KeyCode::CallEnd => write!(f, "<CALLEND>"),
KeyCode::Backspace => write!(f, "<BACKSPACE>"),
KeyCode::Enter => write!(f, "\n"),
KeyCode::CallStart => write!(f, "<CALLSTART>"),
KeyCode::Menu => write!(f, "<MENU>"),
KeyCode::Touchpad => write!(f, "<TOUCHPAD>"),
KeyCode::Back => write!(f, "<BACK>"),
KeyCode::LeftShift => write!(f, "<LEFTSHIFT>"),
KeyCode::RightShift => write!(f, "<RIGHTSHIFT>"),
KeyCode::Alt => write!(f, "<ALT>"),
KeyCode::Sym => write!(f, "<SYM>"),
KeyCode::Char(c) => write!(f, "{c}"),
}
}
}
pub struct Keyboard<
// col
......@@ -24,6 +109,7 @@ pub struct Keyboard<
row_clk: RCLK,
row_ser: RSER,
row_ld: RLD,
last_state: u64,
}
impl<
......@@ -54,11 +140,13 @@ impl<
row_clk,
row_ser,
row_ld,
last_state: 0,
}
}
pub fn read_state(&mut self) -> u64 {
let mut out = 0;
let mut state = 0;
for x in 0..6 {
// +2 gets us to QF (col 6)
......@@ -66,15 +154,37 @@ impl<
self.timer.delay_ms(1);
out |= u64::from(read_rows(
let y = read_rows(
&mut self.timer,
&mut self.row_clk,
&mut self.row_ser,
&mut self.row_ld,
)) << (x * 8);
);
state |= u64::from(y) << (x * 8);
}
let delta = (!self.last_state) & state;
for x in 0..6 {
for y in 0..8 {
if delta & (1 << (x * 8 + y)) > 0 {
let key = KEYMAP[usize::try_from(x).unwrap()][usize::try_from(y).unwrap()];
if key != NONE {
let keycode = KeyCode::from_keyboard(
key,
is_alt_pressed(state),
is_shift_pressed(state),
);
rprint!("{}", keycode);
} else {
rprint!("\n({}, {})", x, y);
}
}
}
}
out
self.last_state = state;
state
}
// 1s in val are low
......@@ -122,3 +232,46 @@ fn read_rows<
out
}
fn is_alt_pressed(state: u64) -> bool {
(state & (1 << (4 * 8 + 2))) > 0
}
fn is_shift_pressed(state: u64) -> bool {
let left = (state & (1 << (2 * 8 + 5))) > 0;
let right = (state & (1 << (3 * 8 + 1))) > 0;
left || right
}
fn altify(c: char) -> char {
match c {
'q' => '#',
'w' => '1',
'e' => '2',
'r' => '3',
't' => '(',
'y' => ')',
'u' => '_',
'i' => '-',
'o' => '+',
'p' => '@',
'a' => '*',
's' => '4',
'd' => '5',
'f' => '6',
'g' => '/',
'h' => ':',
'j' => ';',
'k' => ',',
'l' => '"',
'z' => '7',
'x' => '8',
'c' => '9',
'v' => '?',
'b' => '!',
'n' => ',',
'm' => '.',
_ => c,
}
}
......@@ -277,7 +277,6 @@ mod app {
let state = keyboard.read_state();
if state > 0 {
rprintln!("{:x}", state);
write!(&mut buf, "KB: {state:x}\r\n").unwrap();
//serial.write(&buf.as_bytes());
keyboard_bl.set_duty(max_duty);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment