AI Chat GPT Stable Diffusion イベントレポ インディーゲーム キースイッチ デスク周り 推し活 水族館
Category:
最近、『D-macropad』という小型キーボードを設計しました。
動作はprk firmware。
上部の独立したキー部分には、それぞれRGB-LEDを載せています。
このLEDを、レイヤーの切り替え状態がわかるインジケータのように使いたいと思ったのですが、方法がわからず少々難儀しました。prk firmwareでLEDの色・発光パターンを制御する例は公式ドキュメントがあったのですが、レイヤーごとにカラーを変更する例は、ざっと調べても見つけられなかったんですよね。
今回、手探りで『レイヤー切り替えトグルボタン』と、『レイヤーごとにLEDの色を変える処理』を実装したので、自分の備忘録も兼ねて紹介します。
prk firmwareは、QMKをはじめとした他のファームウェア同様にraise, lowerなどのレイヤー機能が使えます。
ただし、Githubで紹介されているレイヤー指定キーコード(:default, :raise等)は原則長押し時のリアクションになるようです。
では、《切替えキーを押したら指定レイヤーに移動し、再度切替えキーを押せば解除》のような挙動をさせるためにどうしたかというと、キーコード定義とif else文による条件式を組み合わせました。
kbd.define_mode_key :RAISE, [ toggle_raise , nil, 200, nil]
kbd.define_mode_key :LOWER, [ toggle_lower , nil, 200, nil]
toggle_raise = Proc.new {
if kbd.layer == :default
kbd.lock_layer :raise
else
kbd.unlock_layer
end
}
toggle_lower = Proc.new {
if kbd.layer == :default
kbd.lock_layer :lower
else
kbd.unlock_layer
end
}
まず、kbd.define_mode_keyでレイヤー切り替え用のキーコードを定義します。
# (1) (2) (3) (4)
kbd.define_mode_key :RAISE, [ toggle_raise , nil, 200, nil]
(1)-(4)はそれぞれ以下の通り(Github参照)。
(1) 単押し時のキー [proc, キーコード]
(2) 長押し時のキー [proc, キーコード, レイヤー]
(3) リリース時間の閾値:この時間内にキーを離すと(1)の処理が走る
(4) 再押下時間の閾値:3状態で、この時間内に再度キーを押すと(1)のままになる
(1), (2)にはいずれも、procを使った処理を入れることができます。
toggle_raise をprocで定義し、《defaultレイヤー時に単押しするとレイヤーをraiseにロック、default以外の時はロックを解除》するようにします。lowerのレイヤーも同様です。
toggle_raise = Proc.new {
if kbd.layer == :default
kbd.lock_layer :raise
else
kbd.unlock_layer
end
}
これでレイヤー切り替えのトグルボタンが実装できました。
キー押下時にレイヤーを変更・固定する方法としては、《デフォルトレイヤーを都度切替える》手段もあります。
以下のようなデフォルトレイヤー変更キー(RAISE, LOWER, DEFAULT)を各レイヤーに配置し、擬似的なトグルキーのように挙動させるパターンです。
kbd.add_layer :default %i[ RAISE LOWER ]
kbd.add_layer :raise, %i[ DEFAULT LOWER ]
kbd.add_layer :lower, %i[ RAISE DEFAULT ]
kbd.define_mode_key :RAISE, [ Proc.new { kbd.default_layer = :raise }, nil, 200, nil]
kbd.define_mode_key :LOWER, [ Proc.new { kbd.default_layer = :lower }, nil, 200, nil]
kbd.define_mode_key :DEFAULT, [ Proc.new { kbd.default_layer = :default }, nil, 200, nil]
3レイヤーの切り替えでは力技感があるのと、キーコードの割り振りが煩雑になるので、今回こちらの方法は採用しませんでした。
レイヤーを頻繁に切り替えない場合や、使用デバイスに合わせてレイヤー構成を変えたい場合は、こちらの方が適しているかもしれません。
続いて、prk firmwareで《今いるレイヤーに応じてLEDの色を変える》処理を追加しました。
rgb = RGB.new(
14, # ピン番号
0, # アンダーグローピクセル数
2, # バックライトピクセル数
false # 24ビットデータを送信するか
)
rgb.effect = :static
rgb.speed = 31 # エフェクト速度: 1-31
rgb.hue = 100 # 色相: 0-100
rgb.saturation = 80 # 彩度: 0-100
rgb.value = 10 # 明度: 1-31
kbd.append rgb
kbd.before_report do
case kbd.layer
when :default
rgb.hue = 50 # 空色
when :raise
rgb.hue = 15 # 黄色
when :lower
rgb.hue = 80 # 紫色
end
基本のRGB LED設定と発光パターンを指定した後、レイヤー毎にRGBの色を変更する処理を加えています。
kbd.before_report do
case kbd.layer
when :default
rgb.hue = 50 # 空色
when :raise
rgb.hue = 15 # 黄色
when :lower
rgb.hue = 80 # 紫色
end
kbd.before_report ブロックで《現在どのレイヤーにいるか》を監視し、レイヤーに応じて rgb.hue の値(色相)を変更します。
LEDの色味はHSV(hue, saturation, value)の値で決まります。
HSVからRGBの変換は、以下のようなツールを使用すると便利です。
saturation (彩度)の値が低いと色相の変化を感じにくいので、saturation は100とか、極端な値の方がいいかもしれません。個人的には再度ビカビカより、少し白っぽい色味が好きなので数値を落としてあります。
今回は色相だけ変更していますが、effectやvalue(明度)の変更と組み合わせても面白そうです。
コメント