端末(ターミナル), 仮想端末にて、(F1キー等)特殊なキーと各修飾キーと連携(Ctrl+Alt+F1等)した場合のキーバインド設定方法を紹介
#経緯
開発環境作成にて、tmuxに上記のようなキーを使用してショートカットの作成をしようとしたところ、参考サイトがなかなか見つけれず、思った以上に苦労したので備忘録も兼ねて記載。あわせて、zsh, vimの設定方法も調べたのでついでに記載
#環境
名前 | バージョン | |
---|---|---|
OS | OS X El Capitan | 10.11.5 |
端末 | iTerm2 | 3.0.4 |
シェル | zsh | 5.2 |
仮想端末 | tmux | 2.2 |
端末エミュレータ | xterm-256color | - |
補足
端末エミュレータに関しては以下コマンド実行により確認
$ echo $TERM
#設定手順概要
- バインド対象キーが(利用端末にて)有効であるかを確認
- 有効であれば次手順へ
- 無効な場合はバインド対象キーのEscシーケンスを確認
- 端末設定にてバインド対象キーを追加し、Escシーケンスを設定する
- 対象ソフトウェアの設定方法に合わせ、バインドキーを設定
#設定手順詳細
##対象キーが有効であるかの確認
- 端末(iTerm2)の設定画面を表示
- 設定画面から「Profiles > Keys」を選択し、「Key Mappings」を表示
- 「Key Combination」の列を確認し、対象キーがあるかを確認
##バインド対象キーの追加し、利用可能にする
上記より、バインド対象キーがない場合の手順
- (上記手順で表示した)「Key Mappings」の下にある「+」をクリック
- 「Keyboard Shortcut」にてバインド対象のキーをクリック
- 「Action:」にて、「Send Escape Sequence」を選択
- 該当項目に「Escシーケンス」のEscを除去した文字列を入力
※例えば 「Ctrl + F1」の場合は「[1;5P」と入力
###Escシーケンス記載手順
以下ルールに従い記載
- 下記の「特殊キーのEscシーケンス一覧」より修飾キーなしの場合のEscシーケンスを確認
- 確認したEscシーケンスに修飾キーの番号を付与した文字列で記載
※\Eはエスケープ(Esc)を表している
####特殊キーのEscシーケンス一覧
キー | Escシーケンス | キー | Escシーケンス |
---|---|---|---|
F1 | \EOP | PageUp | \E[6~ |
F2 | \EOQ | PageDown | \E[5~ |
F3 | \EOR | Home | \EOH |
F4 | \EOS | End | \EOF |
F5 | \E[15~ | Up | \EOA |
F6 | \E[17~ | Down | \EOB |
F7 | \E[18~ | Right | \EOC |
F8 | \E[19~ | Left | \EOD |
F9 | \E[20~ | ||
F10 | \E[21~ | ||
F11 | \E[23~ | ||
F12 | \E[24~ |
####修飾キーの番号付与方法に関して
下記を参考に対象の修飾キーの番号を付与したEscシーケンスを記載
#####修飾キーの番号
Shift:2
Alt:3
Shift+Alt:4
Ctrl:5
Shift+Ctrl:6
Alt+Ctrl:7
Shift+Alt+Ctrl:8
#####修飾キーの番号付与ルール
-
OX
のときは[1;(番号)X
-
[(数値)~
のときは[(数値);(番号)~
例)Shiftの場合
Shift + キー | Escシーケンス | Shift + キー | Escシーケンス |
---|---|---|---|
Shift + F1 | \E[1;2P | Shift + PageUp | \E[6;2~ |
Shift + F2 | \E[1;2Q | Shift + PageDown | \E[5;2~ |
Shift + F3 | \E[1;2R | Shift + Home | \E[1;2H |
Shift + F4 | \E[1;2S | Shift + End | \E[1;2F |
Shift + F5 | \E[15;2~ | Shift + Up | \E[1;2A |
Shift + F6 | \E[17;2~ | Shift + Down | \E[1;2B |
Shift + F7 | \E[18;2~ | Shift + Right | \E[1;2C |
Shift + F8 | \E[19;2~ | Shift + Left | \E[1;2D |
Shift + F9 | \E[20;2~ | ||
Shift + F10 | \E[21;2~ | ||
Shift + F11 | \E[23;2~ | ||
Shift + F12 | \E[24;2~ |
###参考サイト
terminfo for xterm
termcapとterminfo
###注意事項
- 上記手順にてiTerm2にバインドキーを設定した場合、「Action:」項目の表示はEsc文字は「^[」になります(e.g
^[[1;5P
等) - iTerm2にて、Altキーを使用する場合は「Left option(⌥) key acts as」「Right option(⌥) key acts as」を「+Esc」に設定する必要があります
※iTerm2の設定画面から「Profiles > Keys」を選択した際の画面下部のラジオボタンで変更
##tmuxに設定する
設定ファイル(.tmux.conf)に下記を記載。これでxtermのキーシーケンス使用可となる
set -g xterm-keys on
設定ルールに従い、キーバインドの定義を記載
例)
# ウィンドウ操作の再定義
unbind n; bind -n F2 next-window
unbind p; bind -n S-F2 previous-window
unbind w; bind -n M-F2 choose-window
unbind c; bind -n C-S-F2 new-window
「S-」がShift,「C-」がCtrl,「M-」がAltを表す
###参考
man tmux
の「KEY BINDINGS」項目
##vimに設定する
###手順概要
- vimにて各特殊キーの「<>表記」とEscシーケンスの定義を確認(
set termcap
)
- 確認したEscシーケンスの定義が環境と異なっている場合は再定義を実施(e.g.
:set <xF1>=^[[1;*P
) - 設定ファイルにキーバインド設定を記載(e.g.
map <C-M-S-F2> :echo 'CMS F2 mapped'<CR>
)
###手順詳細
####Escシーケンスの定義確認
vimのコマンドラインからset termcap
を実行し、「--- Terminal keys ---」の項目を確認
「--- Terminal keys ---」で表示する内容
- [t_xx(termcapエントリ)] [<>表記] [Escシーケンス]で表示
- Escシーケンスの
*
は<C-M-S-...>等の修飾キーを使用した時、修飾キーの番号が入ることを示す - デフォルトでは<>表記の<x○○>(<xF1>等)は<○○>(<F1>等)をマッピングする
※<○○>を定義をした場合はマッピングしない
※私の環境では以下のように表示
--- Terminal keys ---
t_#2 <S-Home> ^[[1;2H t_k2 <F2> ^[[12;*~ t_kr <Right> ^[O*C
t_#4 <S-Left> ^[[1;2D t_k3 <F3> ^[[13;*~ t_ku <Up> ^[O*A
t_%1 <Help> ^[[28;*~ t_k4 <F4> ^[[14;*~ <Mouse> ^[[M
t_%i <S-Right> ^[[1;2C t_k5 <F5> ^[[15;*~ <xF1> ^[O*P
t_&8 <Undo> ^[[26;*~ t_k6 <F6> ^[[17;*~ <xF2> ^[O*Q
t_*7 <S-End> ^[[1;2F t_k7 <F7> ^[[18;*~ <xF3> ^[O*R
t_@7 <End> ^[[1;*F t_k8 <F8> ^[[19;*~ <xF4> ^[O*S
t_F1 <F11> ^[[23;*~ t_k9 <F9> ^[[20;*~ <xEnd> ^[O*F
t_F2 <F12> ^[[24;*~ t_k; <F10> ^[[21;*~ <zEnd> ^[[8;*~
t_K1 <kHome> ^[[1;*~ t_kB <S-Tab> ^[[Z <xHome> ^[O*H
t_K4 <kEnd> ^[[4;*~ t_kD <Del> ^[[3~ <zHome> ^[[7;*~
t_K6 <kPlus> ^[O*k t_kI <Insert> ^[[2;*~ <xUp> ^[[1;*A
t_K7 <kMinus> ^[O*m t_kN <PageDown> ^[[6;*~ <xDown> ^[[1;*B
t_K8 <kDivide> ^[O*o t_kP <PageUp> ^[[5;*~ <xLeft> ^[[1;*D
t_K9 <kMultiply> ^[O*j t_kb <BS> ^? <xRight> ^[[1;*C
t_KA <kEnter> ^[O*M t_kd <Down> ^[O*B <kDel> ^[[3;*~
t_KB <kPoint> ^[O*n t_kh <Home> ^[[1;*H
t_k1 <F1> ^[[11;*~ t_kl <Left> ^[O*D
^[
はEscを表しており、「^ + [」でないことに注意
####再定義とバインドの設定
確認したEscシーケンス定義が環境と異なっている場合は:set [<>表記]=[Escシーケンス]
で再定義する
※同じである場合は再定義不要
例)F1の場合
:set <xF1>=^[[1;*P
:set <F1>=^[OP
map <S-F1> [Shift+F1押下時のアクション記載]
map <C-F1> [Ctrl+F1押下時のアクション記載]
map <M-F1> [Alt+F1押下時のアクション記載]
map <C-S-F1> [Ctrl+Shift+F1押下時のアクション記載]
- <xF1>は
^[O*P
となっているため、^[[1;*P
で(修飾キーを使用した場合の文字列で)再定義 - この定義により、<F1>が
^[[1;P
となってしまうので、あわせて再定義
※^[
はvimのINSERTモードにて、「 Ctrl+v 押下」->「 Esc 押下 」で記載 - mapの設定ルールに従い、キーバインドを定義
###参考
サイト:term-Vim日本語ドキュメント
※もしくはvimにて、以下を実行
##zshに設定する
設定ルールに従い記載。Escシーケンスはvimの以下機能を利用
- 非数字文字を文字通りに入力
INSERTモードにて、 Ctrl+v を押下し、対象のキーを押下
例)
# hook関数precmd実行
__call_precmds() {
type precmd > /dev/null 2>&1 && precmd
for __pre_func in $precmd_functions; do $__pre_func; done
}
#shift+upで親ディレクトリへ
#shift+downで戻る
__cd_up() { builtin pushd ..; echo; __call_precmds; zle reset-prompt }
__cd_undo() { builtin popd; echo; __call_precmds; zle reset-prompt }
zle -N __cd_up; bindkey '^[[1;2A' __cd_up
zle -N __cd_undo; bindkey '^[[1;2B' __cd_undo
###注意
※修飾キーの連携とは無関係だが、zshの設定ではまった部分があったためメモ
参考サイト:terminfo for xtermにある以下記載より
「Up」「Down」「Right」「Left」「Home」「End」
のEscシーケンスは上記の 特殊キーのEscシーケンス一覧
と異なるので設定に使用する場合は注意が必要(修飾キー利用時は同じ)
# To see the difference between normal/application modes, consider this example:
# + In normal (non-application) mode, the terminal transmits a down-arrow
# as \E[C, which happens to echo as a down-arrow.
# + In application mode the terminal transmits \EOC, which echoes as C.
# That is because the \EO is the SS3 control, which says to use the
# character from the G3 character set for the next cell.
#
####異なる特殊キーのEscシーケンス一覧
キー | Escシーケンス |
---|---|
Home | \E[H |
End | \E[F |
Up | \E[A |
Down | \E[B |
Right | \E[C |
Left | \E[D |