Skip to content

Commit 115e216

Browse files
committed
Rename AssociatedItems to AssocItems
Signed-off-by: Rustin-Liu <rustin.liu@gmail.com>
1 parent 39eee17 commit 115e216

File tree

1 file changed

+125
-0
lines changed

1 file changed

+125
-0
lines changed

test.rs

+125
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
#![allow(missing_docs)]
2+
3+
use embedded_hal::digital::v2::{InputPin, OutputPin};
4+
use generic_array::{ArrayLength, GenericArray};
5+
use heapless::Vec;
6+
7+
pub trait HeterogenousArray {
8+
type Len;
9+
}
10+
11+
/// Macro to implement a iterator on trait objects from a tuple struct.
12+
#[macro_export]
13+
macro_rules! impl_heterogenous_array {
14+
($s:ident, $t:ty, $len:tt, [$($idx:tt),+]) => {
15+
impl<'a> IntoIterator for &'a $s {
16+
type Item = &'a $t;
17+
type IntoIter = generic_array::GenericArrayIter<&'a $t, $len>;
18+
fn into_iter(self) -> Self::IntoIter {
19+
self.as_array().into_iter()
20+
}
21+
}
22+
impl<'a> IntoIterator for &'a mut $s {
23+
type Item = &'a mut $t;
24+
type IntoIter = generic_array::GenericArrayIter<&'a mut $t, $len>;
25+
fn into_iter(self) -> Self::IntoIter {
26+
self.as_mut_array().into_iter()
27+
}
28+
}
29+
impl $crate::matrix::HeterogenousArray for $s {
30+
type Len = $len;
31+
}
32+
impl $s {
33+
pub fn as_array(&self) -> generic_array::GenericArray<&$t, $len> {
34+
generic_array::arr![&$t; $( &self.$idx as &$t, )+]
35+
}
36+
pub fn as_mut_array(&mut self) -> generic_array::GenericArray<&mut $t, $len> {
37+
generic_array::arr![&mut $t; $( &mut self.$idx as &mut $t, )+]
38+
}
39+
}
40+
}
41+
}
42+
43+
pub struct Matrix<C, R> {
44+
cols: C,
45+
rows: R,
46+
}
47+
48+
impl<C, R> Matrix<C, R> {
49+
pub fn new<E>(cols: C, rows: R) -> Result<Self, E>
50+
where
51+
for<'a> &'a mut R: IntoIterator<Item = &'a mut dyn OutputPin<Error = E>>,
52+
{
53+
let mut res = Self { cols, rows };
54+
res.clear()?;
55+
Ok(res)
56+
}
57+
pub fn clear<'a, E: 'a>(&'a mut self) -> Result<(), E>
58+
where
59+
&'a mut R: IntoIterator<Item = &'a mut dyn OutputPin<Error = E>>,
60+
{
61+
for r in self.rows.into_iter() {
62+
r.set_high()?;
63+
}
64+
Ok(())
65+
}
66+
pub fn get<'a, E: 'a>(&'a mut self) -> Result<PressedKeys<R::Len, C::Len>, E>
67+
where
68+
&'a mut R: IntoIterator<Item = &'a mut dyn OutputPin<Error = E>>,
69+
R: HeterogenousArray,
70+
R::Len: ArrayLength<GenericArray<bool, C::Len>>,
71+
&'a C: IntoIterator<Item = &'a dyn InputPin<Error = E>>,
72+
C: HeterogenousArray,
73+
C::Len: ArrayLength<bool>,
74+
{
75+
let cols = &self.cols;
76+
self.rows
77+
.into_iter()
78+
.map(|r| {
79+
r.set_low()?;
80+
let col = cols
81+
.into_iter()
82+
.map(|c| c.is_low())
83+
.collect::<Result<Vec<_, C::Len>, E>>()?
84+
.into_iter()
85+
.collect();
86+
r.set_high()?;
87+
Ok(col)
88+
})
89+
.collect::<Result<Vec<_, R::Len>, E>>()
90+
.map(|res| PressedKeys(res.into_iter().collect()))
91+
}
92+
}
93+
94+
#[derive(Default, PartialEq, Eq)]
95+
pub struct PressedKeys<U, V>(pub GenericArray<GenericArray<bool, V>, U>)
96+
where
97+
V: ArrayLength<bool>,
98+
U: ArrayLength<GenericArray<bool, V>>;
99+
100+
impl<U, V> PressedKeys<U, V>
101+
where
102+
V: ArrayLength<bool>,
103+
U: ArrayLength<GenericArray<bool, V>>,
104+
{
105+
pub fn iter_pressed<'a>(&'a self) -> impl Iterator<Item = (usize, usize)> + Clone + 'a {
106+
self.0.iter().enumerate().flat_map(|(i, r)| {
107+
r.iter()
108+
.enumerate()
109+
.filter_map(move |(j, &b)| if b { Some((i, j)) } else { None })
110+
})
111+
}
112+
}
113+
114+
impl<'a, U, V> IntoIterator for &'a PressedKeys<U, V>
115+
where
116+
V: ArrayLength<bool>,
117+
U: ArrayLength<GenericArray<bool, V>>,
118+
U: ArrayLength<&'a GenericArray<bool, V>>,
119+
{
120+
type IntoIter = core::slice::Iter<'a, GenericArray<bool, V>>;
121+
type Item = &'a GenericArray<bool, V>;
122+
fn into_iter(self) -> Self::IntoIter {
123+
self.0.iter()
124+
}
125+
}

0 commit comments

Comments
 (0)