自作キーボードっておもしろい!

自作したキーボードについて

総当りマトリクスとRGB matrix

総当りマトリクスを使用して設計した場合に、キーバックライトとしてRGB matrixを適用する際のメモです。


注:筆者はプログラムについては素人です。どうしてこうなるのか、という点はよく分かっていません。


Ergomixsta kite-Eは総当りマトリクスを使用して設計しました。

キーマトリクスとLEDはこのようになっています。

QMKのdocumentには総当りマトリクスについての説明がありません。
もちろん、RGB matrixのページにも総当りマトリクスについては触れられていません。
docs.qmk.fm

課題は以下の2点です。
1.総当りマトリクスに対応するようにLEDのpositionをどのように設定するのか?
2.Ergomixsta kite-Eにはキーバックライトではないインジケーター用LEDがあるが、その扱いはどうするのか?

QMK firmwareの#difine layoutは以下のようになっています。

#define LAYOUT( \
    K12,   K13,   K14,   K15,   K16,   K17,                           K18,   K19,   K110,  K62,   K63,              K64,   K65,   K67,   K68,   K69,   K610, \
    K21,   K23,   K24,   K25,   K26,   K27,                           K28,   K29,   K210,  K61,   K73,              K74,   K75,   K76,   K78,   K79,   K710, \
    K31,   K32,   K34,   K35,   K36,   K37,                           K38,   K39,   K310,  K72,                        K84,   K85,   K86,   K87,   K89,   K810, \
    K41,   K42,   K43,   K45,   K46,   K47,   K48,                 K59,   K510,  K81,   K71,              K93,   K94,   K95,   K96,   K97,   K98,   K910, \
    K51,   K52,   K53,   K54,   K56,             K49,   K410,     K101, K102,  K82,   K83,   K91,    K92,             K105, K106, K107, K108, K109, \
	                                                       K57,   K58,                                 K103,   K104, \
    KE1L,  KE1R,                                                                                                                                                                    KE2L,  KE2R  \
) \
{ \
    { KC_NO, K12,   K13,   K14,   K15,   K16,   K17,   K18,   K19,   K110,  KC_NO, }, \
    { K21,   KC_NO, K23,   K24,   K25,   K26,   K27,   K28,   K29,   K210,  KC_NO, }, \
    { K31,   K32,   KC_NO, K34,   K35,   K36,   K37,   K38,   K39,   K310,  KC_NO, }, \
    { K41,   K42,   K43,   KC_NO, K45,   K46,   K47,   K48,   K49,   K410,  KC_NO, }, \
    { K51,   K52,   K53,   K54,   KC_NO, K56,   K57,   K58,   K59,   K510,  KC_NO, }, \
    { K61,   K62,   K63,   K64,   K65,   KC_NO, K67,   K68,   K69,   K610,  KC_NO, }, \
    { K71,   K72,   K73,   K74,   K75,   K76,   KC_NO, K78,   K79,   K710,  KC_NO, }, \
    { K81,   K82,   K83,   K84,   K85,   K86,   K87,   KC_NO, K89,   K810,  KC_NO, }, \
    { K91,   K92,   K93,   K94,   K95,   K96,   K97,   K98,   KC_NO, K910,  KC_NO, }, \
    { K101,  K102,  K103,  K104,  K105,  K106,  K107,  K108,  K109,  KC_NO, KC_NO, }, \
    { KE1L,  KE1R,  KE2L,  KE2R,  KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO }, \
}

KE1L, KE1R, KE2L, KE2R はロータリーエンコーダーを回した際の入力にあたります。

実際のLEDのは位置は以下のようになっています。

まず、keymap.cで上記のキーマトリクスのキーの位置に、LEDの回路の順番に1番から番号を振って当てはめていきます。このときインジケーター用のLEDは無視します。ですので、K17が1、K16が2、・・・K109が88になります。

    { NO_LED, 6,   5,   4,   3,   2,   1,   50,   51,   52,  NO_LED, }, 
    { 7,   NO_LED, 8,   9,   10,   11,   12,   49,   48,   47,  NO_LED, }, 
    { 18,   17,   NO_LED, 16,   15,   14,   13,   42,   43,   44,  NO_LED, }, 
    { 19,   20,   21,   NO_LED, 22,   23,   24,   25,   27,   26,  NO_LED, }, 
    { 31,   30,   29,   28,   NO_LED, NO_LED,   32,   33,   41,   40,  NO_LED, }, 
    { 46,   53,   54,   55,   56,   NO_LED, 57,   58,   59,   60,  NO_LED, }, 
    { 38,   45,   67,   66,   65,   64,   NO_LED, 63,   62,   61,  NO_LED, }, 
    { 39,   36,   37,   68,   69,   70,   71,   NO_LED, 72,   73,  NO_LED, }, 
    { 82,   81,   80,   79,   78,   77,   76,   75,   NO_LED, 74,  NO_LED, }, 
    { 34,  35,  83,  84,  NO_LED,  85,  86,  87,  88,  NO_LED, NO_LED, }, 
    { NO_LED,  NO_LED,  NO_LED,  NO_LED,  NO_LED, NO_LED, NO_LED, NO_LED, NO_LED, NO_LED, NO_LED }

次に、LEDの順番に沿って、物理的な位置を割り当てていきます。
QMK firmwareのdocumentによると、左上が{0, 0}になりますので、K12つまり、LEDの6が{0, 0}になります。
このときにインジケーター用LEDの位置も指定しました(これが必要かどうかは確認していません)。インジケーター用LEDは回路上では最初にあたりますので、最初に指定しているものがインジケーター用になります。

  {72, 0},	 {60, 0},	 {48, 0},   {36, 0},   {24, 0},   {12, 0},	{0, 0},  // LEDのインジケーター用、1-6
  {0, 13},   {12, 13},  {24, 13},  {36, 13},  {48, 13}, {60, 13},  // LEDの7-12
  {60, 26},  {48, 26},  {36, 26},  {24, 26},  {12, 26}, {0, 39}, 
  {0, 39},   {12, 39},  {24, 39},  {36, 39},  {48, 39}, {60, 39},  {72, 39},
  {84, 52},  {72, 52},  {36, 52},  {24, 39},  {12, 39}, {0, 39},   {72, 64},  {84, 64},
  {95, 52},  {106, 52}, {117, 52}, {128, 52},
  {128, 39}, {117, 39}, {106, 39}, {95, 39},
  {95, 26},  {106, 26}, {117, 26}, {128, 26},
  {128, 13}, {117, 13}, {106, 13}, {95, 13},  
  {95, 0},   {106, 0},  {117, 0},  {128, 0},  {140, 0},
  {164, 0},  {176, 0},  {188, 0},  {200, 0},  {212, 0},  {224, 0},
  {224, 13}, {212, 13}, {200, 13}, {188, 13}, {176, 13}, {164, 13}, {140, 13},
  {164, 26}, {176, 26}, {188, 26}, {200, 26}, {212, 26}, {224, 13},
  {224, 39}, {212, 39}, {200, 39}, {188, 39}, {176, 39}, {164, 39}, {152, 39},
  {152, 52}, {140, 52}, {140, 64}, {152, 64}, {188, 52}, {200, 52}, {212, 52}, {224, 52}

最後にFlag処理を、LEDの順番に沿って行います。
(このFlag処理についてはいまいち理解していません。インジケーター用は2でいいの?)

  2,  // インジケーター用
  4, 4, 4, 4, 4, 4,   // LEDの1-6
  4, 4, 4, 4, 4, 4,   // LEDの7-12
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4,
  4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4,
  4, 4, 4, 4, 

まとめると

led_config_t g_led_config = { {
  // Key Matrix to LED Index
    { NO_LED, 6,   5,   4,   3,   2,   1,   50,   51,   52,  NO_LED, }, 
    { 7,   NO_LED, 8,   9,   10,   11,   12,   49,   48,   47,  NO_LED, }, 
    { 18,   17,   NO_LED, 16,   15,   14,   13,   42,   43,   44,  NO_LED, }, 
    { 19,   20,   21,   NO_LED, 22,   23,   24,   25,   27,   26,  NO_LED, }, 
    { 31,   30,   29,   28,   NO_LED, NO_LED,   32,   33,   41,   40,  NO_LED, }, 
    { 46,   53,   54,   55,   56,   NO_LED, 57,   58,   59,   60,  NO_LED, }, 
    { 38,   45,   67,   66,   65,   64,   NO_LED, 63,   62,   61,  NO_LED, }, 
    { 39,   36,   37,   68,   69,   70,   71,   NO_LED, 72,   73,  NO_LED, }, 
    { 82,   81,   80,   79,   78,   77,   76,   75,   NO_LED, 74,  NO_LED, }, 
    { 34,  35,  83,  84,  NO_LED,  85,  86,  87,  88,  NO_LED, NO_LED, }, 
    { NO_LED,  NO_LED,  NO_LED,  NO_LED,  NO_LED, NO_LED, NO_LED, NO_LED, NO_LED, NO_LED, NO_LED }
}, {
  // LED Index to Physical Position
  {72, 0},	 {60, 0},	 {48, 0},   {36, 0},   {24, 0},   {12, 0},	{0, 0}, 
  {0, 13},   {12, 13},  {24, 13},  {36, 13},  {48, 13}, {60, 13},
  {60, 26},  {48, 26},  {36, 26},  {24, 26},  {12, 26}, {0, 39}, 
  {0, 39},   {12, 39},  {24, 39},  {36, 39},  {48, 39}, {60, 39},  {72, 39},
  {84, 52},  {72, 52},  {36, 52},  {24, 39},  {12, 39}, {0, 39},   {72, 64},  {84, 64},
  {95, 52},  {106, 52}, {117, 52}, {128, 52},
  {128, 39}, {117, 39}, {106, 39}, {95, 39},
  {95, 26},  {106, 26}, {117, 26}, {128, 26},
  {128, 13}, {117, 13}, {106, 13}, {95, 13},  
  {95, 0},   {106, 0},  {117, 0},  {128, 0},  {140, 0},
  {164, 0},  {176, 0},  {188, 0},  {200, 0},  {212, 0},  {224, 0},
  {224, 13}, {212, 13}, {200, 13}, {188, 13}, {176, 13}, {164, 13}, {140, 13},
  {164, 26}, {176, 26}, {188, 26}, {200, 26}, {212, 26}, {224, 13},
  {224, 39}, {212, 39}, {200, 39}, {188, 39}, {176, 39}, {164, 39}, {152, 39},
  {152, 52}, {140, 52}, {140, 64}, {152, 64}, {188, 52}, {200, 52}, {212, 52}, {224, 52}
  }, {
  // LED Index to Flag
  2,
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4, 
  4, 4, 4, 4,
  4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4, 4, 4, 4, 
  4, 4, 4, 4,
  4, 4, 4, 4, 
  } 
};

これで、結果的にキー配列とLEDの位置を一致させることが出来ました。

何かの参考になればと、思います。

改善点などを教えていただければ助かります。
ちゃんと理解していないため、質問にはたぶん答えられません。