Next: Key Binding Commands, Previous: Remapping Commands, Up: Keymaps [Contents][Index]
read-key-sequence
関数がキーシーケンス(Key Sequence Inputを参照)を読み取るときは、特定のイベントシーケンスを他のものに変換(translate)するために、変換キーマップ(translation
keymaps)を使用します。input-decode-map
、local-function-key-map
、key-translation-map
(優先順)は変換キーマップです。
変換キーマップは、他のキーマップと同じ構造をもちますが、使われ方は異なります。変換キーマップは、キーシーケンスを読み取るときに、コンプリートキーシーケンスにたいするバインディングではなく、キーシーケンスに行う変換を指定します。キーシーケンスが読み取られると、それらのキーシーケンスは変換キーマップにたいしてチェックされます。ある変換キーマップがkをベクターvに“バインド”する場合、キーシーケンス内のどこかにサブシーケンスとしてkが出現すると、それはvないのでイベントに置き換えられます。
たとえば、キーパッドキーPF1が押下されたとき、VT100端末はESC O
Pを送信します。そのような端末では、Emacsはそのイベントシーケンスを単一イベントpf1
に変換しなければなりません。これは、input-decode-map
内でESC
O Pを[pf1]
に“バインド”することにより行われます。したがって、その端末上でC-c
PF1をタイプしたとき、端末は文字シーケンスC-c ESC O
Pを発行し、read-key-sequence
がそれをC-c PF1に変換してベクター[?\C-c
pf1]
としてリターンします。
変換キーマップは、(keyboard-coding-system
で指定された入力コーディングシステムを通じて)Emacsがキーボード入力をデコードした直後だけ効果をもちます。Terminal I/O Encodingを参照してください。
この変数は、通常の文字端末上のファンクションキーから送信された文字シーケンスを記述するキーマップを保持する。
input-decode-map
の値は、通常はその端末のTerminfoかTermcapのエントリーに応じて、自動的にセットアップされるが、Lispの端末仕様ファイルの助けが必要なときもある。Emacsには、多くの一般的な端末の端末仕様ファイルが同梱されている。これらのファイルの主な目的は、TermcapやTerminfoから推定できないエントリーをinput-decode-map
内に作成することである。Terminal-Specificを参照のこと。
この変数は、input-decode-map
と同じようにキーマップを保持するが、通常優先される解釈候補(alternative
interpretation)に変換されるべきキーシーケンスを記述するキーマップを保持する。このキーマップはinput-decode-map
の後、key-translation-map
の前に適用される。
local-function-key-map
内のエントリーは、マイナーモード、ローカルキーマップ、グローバルキーマップによるバインディングと衝突する場合は無視される。つまり、元のキーシーケンスが他にバインディングをもたない場合だけ、リマッピングが適用される。
local-function-key-map
がfunction-key-map
を継承するが、function-key-map
を直接使用すべきではない。
この変数は、入力イベントを他のイベントに変換するために、input-decode-map
と同じように使用される、別のキーマップを保持する。input-decode-map
との違いは、local-function-key-map
の前ではなく、後に機能する点である。このキーマップは、local-function-key-map
による変換結果を受け取る。
input-decode-map
と同様、ただしlocal-function-key-map
とは異なり、このキーマップは入力キーシーケンスが通常のバインディングをもつかどうかかに関わらず適用される。しかし、このキーマップによりキーバインディングがオーバーライドされても、key-translation-map
では実際のキーバインディングが効果をもち得ることに注意されたい。確かに、実際のキーバインディングはlocal-function-key-map
をオーバーライドし、したがってkey-translation-map
が受け取るキーシーケンスは変更されるだろう。明確にするためには、このような類の状況は避けたほうがよい。
key-translation-map
は、通常はself-insert-command
にバインディングされるような通常文字を含めて、ユーザーがある文字を他の文字にマップすることを意図している。
キーシーケンスのかわりにキーの“変換”として関数を使用することにより、シンプルなエイリアスより多くのことにinput-decode-map
、local-function-key-map
、key-translation-map
を使用できます。その場合、この関数はそのキーの変換を計算するために呼び出されます。
キー変換関数は、引数を1つ受け取ります。この引数はread-key-sequence
内で指定されるプロンプトです。キーシーケンスがエディターコマンドループに読み取られる場合は、nil
です。ほとんどの場合、プロンプト値は無視できます。
関数が自身で入力を読み取る場合、その関数は後続のイベントを変更する効果をもつことができます。たとえば、以下はC-c hをハイパー文字に後続する文字とするために定義する方法の例です:
(defun hyperify (prompt) (let ((e (read-event))) (vector (if (numberp e) (logior (lsh 1 24) e) (if (memq 'hyper (event-modifiers e)) e (add-event-modifier "H-" e)))))) (defun add-event-modifier (string e) (let ((symbol (if (symbolp e) e (car e)))) (setq symbol (intern (concat string (symbol-name symbol)))) (if (symbolp e) symbol (cons symbol (cdr e))))) (define-key local-function-key-map "\C-ch" 'hyperify)
そのキーシーケンスがコマンドにバインドされたとき、またはさらにイベントを追加してもコマンドにバインドされるシーケンスにすることができないとEmacsが判断したときに、キーシーケンスの終わりが検出されます。
これは、元のキーシーケンスがバインディングをもつかどうかに関わらず、input-decode-map
およびkey-translation-map
を適用するとき、そのようなバインディングが変換の開始を妨げることを意味します。たとえば、前述のVT100の例に戻って、グローバルマップにC-c
ESCを追加してみましょう。すると、ユーザーがC-c PF1をタイプしたとき、EmacsはC-c
ESC O PをC-c PF1に変換するのに失敗するでしょう。これは、EmacsがC-x
ESCの直後に読み取りを停止して、O Pは読み取られずに残るからです。この場合、ユーザーが実際にC-c
ESCをタイプした場合、ユーザーが実際にESCを押下したのか、あるいはPF1を押下したのか判断するために、Emacsが待つべきではないのです。
この理由により、キーシーケンスの終わりがキー変換のプレフィクスであるようなキーシーケンスをコマンドにバインドするのは、避けたほうがよいでしょう。そのような問題を起こす主なサフィックス、およびプレフィクスはESC、M-O(実際はESC O)、M-[(実際はESC [)です。