Key Mapping Transformation Matrix

Complete transformation pipeline for every key from hardware to GUI.

Pipeline Overview

 HARDWARE     ELECTRONICS      DIGITAL        RMK/VIAL
    │              │              │              │
    ▼              ▼              ▼              ▼
Physical Key → (FiX,FoX) → (row,col) → (vrow,vcol)
   name          pins        matrix      virtual

5 Coordinate Systems:

StageNameExampleDescription
1Hardwarei1Physical key label (user perspective)
2Electronics(Fi4,Fo1)Electrical matrix (input,output pins)
3Digital(3,0)Firmware matrix scanner (row,col)
4RMK(3,0)Virtual matrix for RMK keyboard engine
5Vial"3,0"GUI display coordinates (same as RMK)

Note: RMK and Vial share the same 12×6 virtual matrix coordinates.


Physical Layout Reference (User Perspective)

         ✋ LYNXcat (Left)                      LYNXcat (Right) 🤚

          r1 m1 i1     t21 t11            t11 t21     i1 m1 r1
       p1 r2 m2 i2 i5    t22 t12        t12 t22    i5 i2 m2 r2 p1
    p4 p2 r3 m3 i3 i6  t33 t23 t13    t13 t23 t33  i6 i3 m3 r3 p2 p4
    p5 p3 r4 m4 i4 i7     t24 t14      t14 t24     i7 i4 m4 r4 p3 p5
                       t25 t15            t15 t25

  ╰── FINGER (20) ─╯╰─ THUMB (11) ─╯ ╰─ THUMB (11) ─╯╰── FINGER (20) ─╯

Key Naming Convention:

  • i = index finger, m = middle, r = ring, p = pinky
  • t = thumb
  • Numbers indicate row/position within finger group
  • i1-i4 = index column 1, i5-i7 = index column 2 (inner)

LEFT FINGER MODULE (20 Keys)

Electrical Wiring

                              ╭─────╮╭─────╮╭─────╮
                              │ r1  ││ m1  ││ i1  │                Fi4 (GPIO35)
                              ╰──┬──╯╰──┬──╯╰──┬──╯                 Row 3
                                 │      │      │
                       ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
                       │ p1  ││ r2  ││ m2  ││ i2  ││ i5  │         Fi3 (GPIO36)
                       ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯          Row 2
                          │      │      │      │      │
                ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
                │ p4  ││ p2  ││ r3  ││ m3  ││ i3  ││ i6  │         Fi2 (GPIO37)
                ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯          Row 1
                   │      │      │      │      │      │
                ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
                │ p5  ││ p3  ││ r4  ││ m4  ││ i4  ││ i7  │         Fi1 (GPIO38)
                ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯          Row 0
                   │      │      │      │      │      │
                  Fo6    Fo5    Fo4    Fo3    Fo2    Fo1
               (GPIO39)(GPIO40)(GPIO41)(GPIO42)(GPIO2)(GPIO1)
                 Col5   Col4   Col3   Col2   Col1   Col0

               pinky  pinky   ring   mid   index  index
               outer  inner                inner  outer

Complete Transformation Table

HardwareElectronicsDigitalRMK/VialNotes
Index Finger (Inner Column)
i7(Fi1, Fo1)(0, 0)(0, 0)Bottom inner
i6(Fi2, Fo1)(1, 0)(1, 0)
i5(Fi3, Fo1)(2, 0)(2, 0)
--(3, 0)(3, 0)Empty position
Index Finger (Outer Column)
i4(Fi1, Fo2)(0, 1)(0, 1)Bottom outer
i3(Fi2, Fo2)(1, 1)(1, 1)
i2(Fi3, Fo2)(2, 1)(2, 1)
i1(Fi4, Fo2)(3, 1)(3, 1)Top
Middle Finger
m4(Fi1, Fo3)(0, 2)(0, 2)Bottom
m3(Fi2, Fo3)(1, 2)(1, 2)
m2(Fi3, Fo3)(2, 2)(2, 2)
m1(Fi4, Fo3)(3, 2)(3, 2)Top
Ring Finger
r4(Fi1, Fo4)(0, 3)(0, 3)Bottom
r3(Fi2, Fo4)(1, 3)(1, 3)
r2(Fi3, Fo4)(2, 3)(2, 3)
r1(Fi4, Fo4)(3, 3)(3, 3)Top
Pinky (Inner Column)
p3(Fi1, Fo5)(0, 4)(0, 4)Bottom inner
p2(Fi2, Fo5)(1, 4)(1, 4)
p1(Fi3, Fo5)(2, 4)(2, 4)Top
--(3, 4)(3, 4)Empty position
Pinky (Outer Column)
p5(Fi1, Fo6)(0, 5)(0, 5)Bottom outer
p4(Fi2, Fo6)(1, 5)(1, 5)
--(2, 5)(2, 5)Empty position
--(3, 5)(3, 5)Empty position

Visual Matrix (Firmware Perspective)

         Col0   Col1   Col2   Col3   Col4   Col5
         (Fo1)  (Fo2)  (Fo3)  (Fo4)  (Fo5)  (Fo6)
         ─────  ─────  ─────  ─────  ─────  ─────
Row 0 │   i7     i4     m4     r4     p3     p5   │ (Fi1) GPIO38 → Virt Row 0
Row 1 │   i6     i3     m3     r3     p2     p4   │ (Fi2) GPIO37 → Virt Row 1
Row 2 │   i5     i2     m2     r2     p1     --   │ (Fi3) GPIO36 → Virt Row 2
Row 3 │   --     i1     m1     r1     --     --   │ (Fi4) GPIO35 → Virt Row 3

LEFT THUMB MODULE (11 Keys)

Physical Layout (User View)

              ╭─────╮╭─────╮
              │ t21 ││ t11 │        ← Thumb range top
              ╰─────╯╰─────╯
           ╭─────╮╭─────╮
           │ t22 ││ t12 │
           ╰─────╯╰─────╯
     ╭─────╮╭─────╮╭─────╮
     │ t33 ││ t23 ││ t13 │          ← Thumb range middle
     ╰─────╯╰─────╯╰─────╯
           ╭─────╮╭─────╮
           │ t24 ││ t14 │
           ╰─────╯╰─────╯
              ╭─────╮╭─────╮
              │ t25 ││ t15 │        ← Thumb range bottom
              ╰─────╯╰─────╯
      inner column | outer column

Electrical Matrix (Firmware Scanner)

Note: Physical layout does NOT match electrical rows! The wiring pattern is non-obvious.

         Col0   Col1   Col2
         (To1)  (To2)  (To3)
         ─────  ─────  ─────
Row 0 │  t21    t33    t25  │ (Ti1) GPIO4
Row 1 │  t22    --     t24  │ (Ti2) GPIO5  ← Position (1,1) EMPTY
Row 2 │  t11    t23    t15  │ (Ti3) GPIO6
Row 3 │  t12    t13    t14  │ (Ti4) GPIO7

Key-to-Pin Wiring Reference

Physical PositionKeyElectrical (Ti, To)Digital (row, col)
Inner-leftt21(Ti1, To1)(0, 0)
Inner-rightt11(Ti3, To1)(2, 0)
2nd row-leftt22(Ti2, To1)(1, 0)
2nd row-rightt12(Ti4, To1)(3, 0)
Middle-leftt33(Ti1, To2)(0, 1)
Middle-centert23(Ti3, To2)(2, 1)
Middle-rightt13(Ti4, To2)(3, 1)
4th row-leftt24(Ti2, To3)(1, 2)
4th row-rightt14(Ti4, To3)(3, 2)
Outer-leftt25(Ti1, To3)(0, 2)
Outer-rightt15(Ti3, To3)(2, 2)

Complete Transformation Table

HardwareElectronicsDigitalVirtualCalculationNotes
t21(Ti1, To1)(0, 0)(4, 0)vrow=4+(0/2), vcol=(0%2)*3+0Top inner
t33(Ti1, To2)(0, 1)(4, 1)vrow=4+(0/2), vcol=(0%2)*3+1
t25(Ti1, To3)(0, 2)(4, 2)vrow=4+(0/2), vcol=(0%2)*3+2Bottom outer
t22(Ti2, To1)(1, 0)(4, 3)vrow=4+(1/2), vcol=(1%2)*3+0
----(1, 1)(4, 4)--EMPTY
t24(Ti2, To3)(1, 2)(4, 5)vrow=4+(1/2), vcol=(1%2)*3+2
t11(Ti3, To1)(2, 0)(5, 0)vrow=4+(2/2), vcol=(2%2)*3+0Top inner
t23(Ti3, To2)(2, 1)(5, 1)vrow=4+(2/2), vcol=(2%2)*3+1
t15(Ti3, To3)(2, 2)(5, 2)vrow=4+(2/2), vcol=(2%2)*3+2Bottom outer
t12(Ti4, To1)(3, 0)(5, 3)vrow=4+(3/2), vcol=(3%2)*3+0
t13(Ti4, To2)(3, 1)(5, 4)vrow=4+(3/2), vcol=(3%2)*3+1
t14(Ti4, To3)(3, 2)(5, 5)vrow=4+(3/2), vcol=(3%2)*3+2Bottom

Thumb Compaction Visualization

Physical 4×3 Matrix:              Virtual 2×6 Matrix (Rows 4-5):

  Col0  Col1  Col2                 Col0  Col1  Col2  Col3  Col4  Col5
  ────  ────  ────                 ────  ────  ────  ────  ────  ────
R0│ t21   t33   t25 │──────┐    R4│ t21   t33   t25   t22   --    t24 │
R1│ t22   --    t24 │──────┘       └─────────────────┴─────────────┘
R2│ t11   t23   t15 │──────┐    R5│ t11   t23   t15   t12   t13   t14 │
R3│ t12   t13   t14 │──────┘       └─────────────────┴─────────────┘

Formula: vrow = 4 + (phys_row / 2)
         vcol = (phys_row % 2) * 3 + phys_col

RIGHT FINGER MODULE (20 Keys)

Electrical Wiring (Mirrored from Left)

               ╭─────╮╭─────╮╭─────╮
               │ i1  ││ m1  ││ r1  │                               Fi4 (GPIO35)
               ╰──┬──╯╰──┬──╯╰──┬──╯                                Row 3
                  │      │      │
        ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
        │ i5  ││ i2  ││ m2  ││ r2  ││ p1  │                        Fi3 (GPIO36)
        ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯                         Row 2
           │      │      │      │      │
        ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
        │ i6  ││ i3  ││ m3  ││ r3  ││ p2  ││ p4  │                 Fi2 (GPIO37)
        ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯                  Row 1
           │      │      │      │      │      │
        ╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮╭─────╮
        │ i7  ││ i4  ││ m4  ││ r4  ││ p3  ││ p5  │                 Fi1 (GPIO38)
        ╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯╰──┬──╯                  Row 0
           │      │      │      │      │      │
          Fo1    Fo2    Fo3    Fo4    Fo5    Fo6
       (GPIO1)(GPIO2)(GPIO42)(GPIO41)(GPIO40)(GPIO39)
         Col0   Col1   Col2   Col3   Col4   Col5

        index  index   mid    ring   pinky  pinky
        outer  inner                 inner  outer

Complete Transformation Table

HardwareElectronicsDigitalRMK/VialNotes
Index Finger (Outer Column)
i7(Fi1, Fo1)(0, 0)(6, 0)Bottom outer
i6(Fi2, Fo1)(1, 0)(7, 0)
i5(Fi3, Fo1)(2, 0)(8, 0)
--(3, 0)(9, 0)Empty position
Index Finger (Inner Column)
i4(Fi1, Fo2)(0, 1)(6, 1)Bottom inner
i3(Fi2, Fo2)(1, 1)(7, 1)
i2(Fi3, Fo2)(2, 1)(8, 1)
i1(Fi4, Fo2)(3, 1)(9, 1)Top
Middle Finger
m4(Fi1, Fo3)(0, 2)(6, 2)Bottom
m3(Fi2, Fo3)(1, 2)(7, 2)
m2(Fi3, Fo3)(2, 2)(8, 2)
m1(Fi4, Fo3)(3, 2)(9, 2)Top
Ring Finger
r4(Fi1, Fo4)(0, 3)(6, 3)Bottom
r3(Fi2, Fo4)(1, 3)(7, 3)
r2(Fi3, Fo4)(2, 3)(8, 3)
r1(Fi4, Fo4)(3, 3)(9, 3)Top
Pinky (Inner Column)
p3(Fi1, Fo5)(0, 4)(6, 4)Bottom inner
p2(Fi2, Fo5)(1, 4)(7, 4)
p1(Fi3, Fo5)(2, 4)(8, 4)Top
--(3, 4)(9, 4)Empty position
Pinky (Outer Column)
p5(Fi1, Fo6)(0, 5)(6, 5)Bottom outer
p4(Fi2, Fo6)(1, 5)(7, 5)
--(2, 5)(8, 5)Empty position
--(3, 5)(9, 5)Empty position

Visual Matrix (Firmware Perspective)

         Col0   Col1   Col2   Col3   Col4   Col5
         (Fo1)  (Fo2)  (Fo3)  (Fo4)  (Fo5)  (Fo6)
         ─────  ─────  ─────  ─────  ─────  ─────
Row 0 │   i7     i4     m4     r4     p3     p5   │ (Fi1) GPIO38 → Virt Row 6
Row 1 │   i6     i3     m3     r3     p2     p4   │ (Fi2) GPIO37 → Virt Row 7
Row 2 │   i5     i2     m2     r2     p1     --   │ (Fi3) GPIO36 → Virt Row 8
Row 3 │   --     i1     m1     r1     --     --   │ (Fi4) GPIO35 → Virt Row 9

RIGHT THUMB MODULE (11 Keys)

Physical Layout (User View - Mirrored from Left)

              ╭─────╮╭─────╮
              │ t11 ││ t21 │        ← Thumb range top
              ╰─────╯╰─────╯
           ╭─────╮╭─────╮
           │ t12 ││ t22 │
           ╰─────╯╰─────╯
     ╭─────╮╭─────╮╭─────╮
     │ t13 ││ t23 ││ t33 │          ← Thumb range middle
     ╰─────╯╰─────╯╰─────╯
           ╭─────╮╭─────╮
           │ t14 ││ t24 │
           ╰─────╯╰─────╯
              ╭─────╮╭─────╮
              │ t15 ││ t25 │        ← Thumb range bottom
              ╰─────╯╰─────╯
      outer column | inner column

Electrical Matrix (Same Mapping as Left)

Note: Physical layout is mirrored, but electrical matrix mapping is identical to left thumb.

         Col0   Col1   Col2
         (To1)  (To2)  (To3)
         ─────  ─────  ─────
Row 0 │  t21    t33    t25  │ (Ti1) GPIO4
Row 1 │  t22    --     t24  │ (Ti2) GPIO5  ← Position (1,1) EMPTY
Row 2 │  t11    t23    t15  │ (Ti3) GPIO6
Row 3 │  t12    t13    t14  │ (Ti4) GPIO7

Key-to-Pin Wiring Reference

Physical PositionKeyElectrical (Ti, To)Digital (row, col)
Inner-leftt11(Ti3, To1)(2, 0)
Inner-rightt21(Ti1, To1)(0, 0)
2nd row-leftt12(Ti4, To1)(3, 0)
2nd row-rightt22(Ti2, To1)(1, 0)
Middle-leftt13(Ti4, To2)(3, 1)
Middle-centert23(Ti3, To2)(2, 1)
Middle-rightt33(Ti1, To2)(0, 1)
4th row-leftt14(Ti4, To3)(3, 2)
4th row-rightt24(Ti2, To3)(1, 2)
Outer-leftt15(Ti3, To3)(2, 2)
Outer-rightt25(Ti1, To3)(0, 2)

Complete Transformation Table

HardwareElectronicsDigitalVirtualCalculationNotes
t21(Ti1, To1)(0, 0)(10, 0)vrow=10+(0/2), vcol=(0%2)*3+0Top inner
t33(Ti1, To2)(0, 1)(10, 1)vrow=10+(0/2), vcol=(0%2)*3+1
t25(Ti1, To3)(0, 2)(10, 2)vrow=10+(0/2), vcol=(0%2)*3+2Bottom outer
t22(Ti2, To1)(1, 0)(10, 3)vrow=10+(1/2), vcol=(1%2)*3+0
----(1, 1)(10, 4)--EMPTY
t24(Ti2, To3)(1, 2)(10, 5)vrow=10+(1/2), vcol=(1%2)*3+2
t11(Ti3, To1)(2, 0)(11, 0)vrow=10+(2/2), vcol=(2%2)*3+0Top inner
t23(Ti3, To2)(2, 1)(11, 1)vrow=10+(2/2), vcol=(2%2)*3+1
t15(Ti3, To3)(2, 2)(11, 2)vrow=10+(2/2), vcol=(2%2)*3+2Bottom outer
t12(Ti4, To1)(3, 0)(11, 3)vrow=10+(3/2), vcol=(3%2)*3+0
t13(Ti4, To2)(3, 1)(11, 4)vrow=10+(3/2), vcol=(3%2)*3+1
t14(Ti4, To3)(3, 2)(11, 5)vrow=10+(3/2), vcol=(3%2)*3+2Bottom

Thumb Compaction Visualization

Physical 4×3 Matrix:              Virtual 2×6 Matrix (Rows 10-11):

  Col0  Col1  Col2                 Col0  Col1  Col2  Col3  Col4  Col5
  ────  ────  ────                 ────  ────  ────  ────  ────  ────
R0│ t21   t33   t25 │──────┐   R10│ t21   t33   t25   t22   --    t24 │
R1│ t22   --    t24 │──────┘       └─────────────────┴─────────────┘
R2│ t11   t23   t15 │──────┐   R11│ t11   t23   t15   t12   t13   t14 │
R3│ t12   t13   t14 │──────┘       └─────────────────┴─────────────┘

Formula: vrow = 10 + (phys_row / 2)
         vcol = (phys_row % 2) * 3 + phys_col

COMPLETE VIRTUAL MATRIX (12×6 = 72 Keys)

This is what RMK and Vial see:

        Col0   Col1   Col2   Col3   Col4   Col5
        ─────  ─────  ─────  ─────  ─────  ─────
Row 0 │  Li7    Li4    Lm4    Lr4    Lp3    Lp5  │  LeftCat Finger
Row 1 │  Li6    Li3    Lm3    Lr3    Lp2    Lp4  │
Row 2 │  Li5    Li2    Lm2    Lr2    Lp1    --   │
Row 3 │  --     Li1    Lm1    Lr1    --     --   │
        ═════════════════════════════════════════
Row 4 │  Lt21   Lt33   Lt25   Lt22   --     Lt24 │  LeftCat Thumb
Row 5 │  Lt11   Lt23   Lt15   Lt12   Lt13   Lt14 │
        ═════════════════════════════════════════
Row 6 │  Ri7    Ri4    Rm4    Rr4    Rp3    Rp5  │  RightCat Finger
Row 7 │  Ri6    Ri3    Rm3    Rr3    Rp2    Rp4  │
Row 8 │  Ri5    Ri2    Rm2    Rr2    Rp1    --   │
Row 9 │  --     Ri1    Rm1    Rr1    --     --   │
        ═════════════════════════════════════════
Row10 │  Rt21   Rt33   Rt25   Rt22   --     Rt24 │  RightCat Thumb
Row11 │  Rt11   Rt23   Rt15   Rt12   Rt13   Rt14 │

Empty Positions (4 per side = 8 total):

  • Left Finger: (3,0), (3,4), (3,5), (2,5)
  • Left Thumb: (4,4)
  • Right Finger: (9,0), (9,4), (9,5), (8,5)
  • Right Thumb: (10,4)

GPIO Pin Reference

Finger Module (Both Sides - Identical Wiring)

SignalGPIODirectionFunction
Fi1GPIO38InputRow 0 (bottom physical row)
Fi2GPIO37InputRow 1
Fi3GPIO36InputRow 2
Fi4GPIO35InputRow 3 (top physical row)
Fo1GPIO1OutputCol 0 (index outer)
Fo2GPIO2OutputCol 1 (index inner)
Fo3GPIO42OutputCol 2 (middle)
Fo4GPIO41OutputCol 3 (ring)
Fo5GPIO40OutputCol 4 (pinky inner)
Fo6GPIO39OutputCol 5 (pinky outer)

Thumb Module (Both Sides - Identical Wiring)

SignalGPIODirectionFunction
Ti1GPIO4InputRow 0
Ti2GPIO5InputRow 1
Ti3GPIO6InputRow 2
Ti4GPIO7InputRow 3
To1GPIO18OutputCol 0
To2GPIO8OutputCol 1
To3GPIO3OutputCol 2

Transformation Formulas (Code Reference)

Source: firmware/common/src/key_index.rs

Finger Module (Direct Mapping)

// LeftCat Finger: physical = virtual (rows 0-3)
(DeviceRole::LeftCat, ModuleSlot::Finger) => (phys_row, phys_col)

// RightCat Finger: offset by 6 rows (rows 6-9)
(DeviceRole::RightCat, ModuleSlot::Finger) => (6 + phys_row, phys_col)

Thumb Module (4×3 → 2×6 Compaction)

// LeftCat Thumb: compact to rows 4-5
(DeviceRole::LeftCat, ModuleSlot::Thumb) => {
    let virt_row = 4 + (phys_row / 2);      // 0,1→4; 2,3→5
    let virt_col = (phys_row % 2) * 3 + phys_col;
    (virt_row, virt_col)
}

// RightCat Thumb: compact to rows 10-11
(DeviceRole::RightCat, ModuleSlot::Thumb) => {
    let virt_row = 10 + (phys_row / 2);     // 0,1→10; 2,3→11
    let virt_col = (phys_row % 2) * 3 + phys_col;
    (virt_row, virt_col)
}

Example: Tracing Key Li2 Through Pipeline

STAGE 1: HARDWARE
   User presses key labeled "i2" on left finger module
   Physical position: index finger, second row from top

STAGE 2: ELECTRONICS
   Switch connects Fi3 (row input) to Fo2 (col output)
   Signal path: GPIO36 (Fi3) ← switch → GPIO2 (Fo2)

STAGE 3: DIGITAL (Matrix Scanner)
   MatrixDriver scans:
     cols[1].set_low()          // Fo2 = GPIO2
     rows[2].is_low() == true   // Fi3 = GPIO36 detects LOW
   Result: (row=2, col=1)

STAGE 4: INPUT ACTION (Event Generation)
   EventGenerator creates:
     InputAction::KeyPress { row: 2, col: 1 }
   FrameHeader adds routing:
     sender: DeviceRole::LeftCat
     module_slot: ModuleSlot::Finger
     sequence_id: 42

STAGE 5: ESP-NOW (Wireless)
   Frame serialized via postcard
   Broadcast to tower (~0.5ms latency)

STAGE 6: VIRTUAL MATRIX (Tower)
   physical_to_virtual(LeftCat, Finger, 2, 1):
     → Direct mapping for Finger
     → Virtual (2, 1)

STAGE 7: RMK/VIAL
   RMK receives Event::KeyPress(row=2, col=1)
   Keymap lookup: KEYMAP[layer][2][1] → KeyAction
   Vial displays key at position "2,1" with label "Li2"
   USB HID report generated → Host

Debugging Quick Reference

Wrong Key in Vial

SymptomCheckFix
Wrong positionFirmware logs: verify KeyPress(row, col)Hardware wiring issue
Wrong labelvial.json label at positionUpdate vial.json label
Key doesn't registerSequence tracking logsCheck ESP-NOW reception

Vial Position → Physical Key Lookup

Given Vial position (vrow, vcol):

IF vrow < 4:  Left Finger
   physical = (vrow, vcol)
   key = see Left Finger table above

IF vrow 4-5:  Left Thumb
   phys_row = (vrow - 4) * 2 + (vcol >= 3 ? 1 : 0)
   phys_col = vcol % 3
   key = see Left Thumb table above

IF vrow 6-9:  Right Finger
   physical = (vrow - 6, vcol)
   key = see Right Finger table above

IF vrow 10-11: Right Thumb
   phys_row = (vrow - 10) * 2 + (vcol >= 3 ? 1 : 0)
   phys_col = vcol % 3
   key = see Right Thumb table above

Key Files

FilePurpose
firmware/common/src/key_index.rsTransformation functions
firmware/cat/src/config.rsGPIO pin definitions
firmware/tower/src/virtual_matrix.rsRMK InputDevice bridge
firmware/tower/vial.jsonVial layout definition
firmware/tower/src/config.rsVirtual matrix dimensions