rog-aura: bringup the per-key LED stuff again

This commit is contained in:
Luke D. Jones
2022-08-24 22:01:13 +12:00
parent f3876100ae
commit 0ef524a94b
10 changed files with 490 additions and 82 deletions

View File

@@ -1,10 +1,11 @@
use serde::{Deserialize, Serialize};
#[derive(Debug, PartialEq, Copy, Clone, Serialize, Deserialize)]
#[derive(Debug, Default, PartialEq, Copy, Clone, Serialize, Deserialize)]
pub enum Key {
VolUp,
VolDown,
MicMute,
#[default]
Rog,
Fan,
Esc,
@@ -151,6 +152,13 @@ pub enum Key {
RowEndSpacer,
}
impl Key {
pub fn is_placeholder(&self) -> bool {
let shape = KeyShape::from(self);
shape.is_blank() || shape.is_spacer()
}
}
/// Types of shapes of LED on keyboards. The shape is used for visual representations
///
/// A post fix of Spacer *must be ignored by per-key effects

View File

@@ -49,6 +49,10 @@ impl KeyLayout {
pub fn rows(&self) -> Iter<KeyRow> {
self.rows.iter()
}
pub fn rows_ref(&self) -> &[KeyRow] {
&self.rows
}
}
#[derive(Debug, Deserialize, Serialize, Clone)]
@@ -66,6 +70,10 @@ impl KeyRow {
self.row.iter()
}
pub fn row_ref(&self) -> &[Key] {
&self.row
}
pub fn height(&self) -> f32 {
self.height
}

View File

@@ -0,0 +1,168 @@
#[allow(clippy::upper_case_acronyms)]
pub struct GX502Layout(Vec<[Key; 17]>);
impl KeyLayout for GX502Layout {
fn get_rows(&self) -> &Vec<[Key; 17]> {
&self.0
}
}
impl Default for GX502Layout {
fn default() -> Self {
GX502Layout(vec![
[
Key::NormalSpacer,
Key::FuncSpacer,
Key::VolDown,
Key::VolUp,
Key::MicMute,
Key::Rog,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
],
[
Key::Esc,
Key::NormalBlank,
Key::F1,
Key::F2,
Key::F3,
Key::F4,
Key::NormalBlank, // not sure which key to put here
Key::F5,
Key::F6,
Key::F7,
Key::F8,
Key::NormalBlank,
Key::F9,
Key::F10,
Key::F11,
Key::F12,
Key::Del,
],
[
Key::Tilde,
Key::N1,
Key::N2,
Key::N3,
Key::N4,
Key::N5,
Key::N6,
Key::N7,
Key::N8,
Key::N9,
Key::N0,
Key::Hyphen,
Key::Equals,
Key::BkSpc3_1,
Key::BkSpc3_2,
Key::BkSpc3_3,
Key::Home,
],
[
Key::Tab,
Key::Q,
Key::W,
Key::E,
Key::R,
Key::T,
Key::Y,
Key::U,
Key::I,
Key::O,
Key::P,
Key::LBracket,
Key::RBracket,
Key::BackSlash,
Key::BackSlash,
Key::BackSlash,
Key::PgUp,
],
[
Key::Caps,
Key::A,
Key::S,
Key::D,
Key::F,
Key::G,
Key::H,
Key::J,
Key::K,
Key::L,
Key::SemiColon,
Key::Quote,
Key::Quote,
Key::Return3_1,
Key::Return3_2,
Key::Return3_3,
Key::PgDn,
],
[
Key::LShift,
Key::LShift,
Key::Z,
Key::X,
Key::C,
Key::V,
Key::B,
Key::N,
Key::M,
Key::Comma,
Key::Period,
Key::FwdSlash,
Key::FwdSlash,
Key::Rshift3_1,
Key::Rshift3_2,
Key::Rshift3_3,
Key::End,
],
[
Key::LCtrl,
Key::LFn,
Key::Meta,
Key::LAlt,
Key::Space5_1,
Key::Space5_2,
Key::Space5_3,
Key::Space5_4,
Key::Space5_5,
Key::RAlt,
Key::PrtSc,
Key::RCtrl,
Key::RCtrl,
Key::Left,
Key::Up,
Key::Right,
Key::RFn,
],
[
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::NormalBlank,
Key::Left,
Key::Down,
Key::Right,
Key::NormalBlank,
],
])
}
}

View File

@@ -1,4 +1,10 @@
use crate::keys::Key;
use serde_derive::{Deserialize, Serialize};
#[cfg(feature = "dbus")]
use zvariant::Type;
/// Represents the per-key raw USB packets
pub type PerKeyRaw = Vec<Vec<u8>>;
/// A `KeyColourArray` contains all data to change the full set of keyboard
/// key colours individually.
@@ -7,16 +13,19 @@ use crate::keys::Key;
/// to the keyboard EC. One row controls one group of keys, these keys are not
/// necessarily all on the same row of the keyboard, with some splitting between
/// two rows.
#[derive(Clone)]
pub struct KeyColourArray([[u8; 64]; 11]);
#[cfg_attr(feature = "dbus", derive(Type))]
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct KeyColourArray(PerKeyRaw);
impl Default for KeyColourArray {
fn default() -> Self {
Self::new()
}
}
impl KeyColourArray {
pub fn new() -> Self {
let mut set = [[0u8; 64]; 11];
let mut set = vec![vec![0u8; 64]; 11];
for (count, row) in set.iter_mut().enumerate() {
row[0] = 0x5d; // Report ID
row[1] = 0xbc; // Mode = custom??, 0xb3 is builtin
@@ -211,15 +220,31 @@ impl KeyColourArray {
Key::Fan | Key::Space | Key::BkSpc => return None,
};
Some(&mut self.0[row][col..2])
Some(&mut self.0[row][col..=col + 2])
}
#[inline]
pub fn get(&self) -> &[[u8; 64]; 11] {
pub fn get(&self) -> PerKeyRaw {
self.0.clone()
}
#[inline]
pub fn get_ref(&self) -> &PerKeyRaw {
&self.0
}
#[inline]
pub fn get_mut(&mut self) -> &mut PerKeyRaw {
&mut self.0
}
}
pub trait KeyLayout {
fn get_rows(&self) -> &Vec<[Key; 17]>;
}
impl From<KeyColourArray> for PerKeyRaw {
fn from(k: KeyColourArray) -> Self {
k.0
}
}

View File

@@ -1,17 +1,43 @@
use serde_derive::{Deserialize, Serialize};
use crate::error::Error;
use crate::{keys::Key, Colour, KeyColourArray, PerKeyRaw, Speed};
/// All the possible AniMe actions that can be used. The enum is intended to be
/// used in a array allowing the user to cycle through a series of actions.
#[derive(Debug, Deserialize, Serialize)]
pub enum ActionData {
Static,
#[derive(Debug, Default, Deserialize, Serialize)]
pub struct PerKey {
pub key: Key,
pub action: ActionData,
/// The end resulting colour after stepping through effect
#[serde(skip)]
colour: Colour,
}
#[derive(Debug, Deserialize, Serialize)]
pub enum ActionData {
Static(Colour),
Breathe {
/// The starting colour
colour1: Colour,
/// The secondary starting colour
colour2: Colour,
/// The speed at which to cycle between the colours
speed: Speed,
/// Temporary data to help keep state
#[serde(skip)]
colour1_actual: Colour,
/// Temporary data to help keep state
#[serde(skip)]
colour2_actual: Colour,
},
}
impl Default for ActionData {
fn default() -> Self {
Self::Static(Colour::default())
}
}
/// An optimised precomputed set of actions that the user can cycle through
#[derive(Debug, Deserialize, Serialize, Default)]
pub struct Sequences(Vec<ActionData>);
pub struct Sequences(Vec<PerKey>);
impl Sequences {
#[inline]
@@ -19,51 +45,76 @@ impl Sequences {
Self(Vec::new())
}
/// Use a base `AnimeAction` to generate the precomputed data and insert in to
/// the run buffer
#[inline]
pub fn insert(&mut self, _index: usize) -> Result<(), Error> {
Ok(())
pub fn push(&mut self, action: PerKey) {
self.0.push(action);
}
#[inline]
pub fn insert(&mut self, index: usize, action: PerKey) {
self.0.insert(index, action);
}
/// Remove an item at this position from the run buffer. If the `index` supplied
/// is not in range then `None` is returned, otherwise the `ActionData` at that location
/// is yeeted and returned.
#[inline]
pub fn remove_item(&mut self, index: usize) -> Option<ActionData> {
pub fn remove_item(&mut self, index: usize) -> Option<PerKey> {
if index < self.0.len() {
return Some(self.0.remove(index));
}
None
}
pub fn iter(&self) -> ActionIterator {
ActionIterator {
actions: self,
next_idx: 0,
pub fn next_state(&mut self) {
for effect in self.0.iter_mut() {
match effect.action {
ActionData::Static(c) => effect.colour = c,
ActionData::Breathe {
colour1,
colour2,
speed,
colour1_actual,
colour2_actual,
} => {
effect.colour = colour1;
}
}
}
}
pub fn create_packets(&self) -> PerKeyRaw {
let mut keys = KeyColourArray::new();
for effect in self.0.iter() {
if let Some(rgb) = keys.rgb_for_key(effect.key) {
rgb[0] = effect.colour.0;
rgb[1] = effect.colour.1;
rgb[2] = effect.colour.2;
}
}
keys.into()
}
}
/// Iteractor helper for iterating over all the actions in `Sequences`
pub struct ActionIterator<'a> {
actions: &'a Sequences,
next_idx: usize,
}
#[cfg(test)]
mod tests {
use crate::{keys::Key, Colour, PerKey, Sequences};
impl<'a> Iterator for ActionIterator<'a> {
type Item = &'a ActionData;
#[test]
fn single_key_next_state_then_create() {
let mut seq = Sequences::new();
seq.0.push(PerKey {
key: Key::F,
action: crate::ActionData::Static(Colour(255, 127, 0)),
colour: Default::default(),
});
#[inline]
fn next(&mut self) -> Option<&'a ActionData> {
if self.next_idx == self.actions.0.len() {
self.next_idx = 0;
return None;
}
seq.next_state();
let packets = seq.create_packets();
let current = self.next_idx;
self.next_idx += 1;
Some(&self.actions.0[current])
assert_eq!(packets[0][0], 0x5d);
assert_eq!(packets[5][33], 255);
assert_eq!(packets[5][34], 127);
assert_eq!(packets[5][35], 0);
}
}