按键查找(Key lookup)是从指定键盘映射中查找按键序列绑定的过程。 绑定的执行或使用不属于按键查找的范畴。
按键查找仅使用按键序列中每个事件的事件类型;
事件的其余部分会被忽略。实际上,用于按键查找的按键序列可以仅通过其类型(一个符号)
来指定鼠标事件,而非完整的事件(一个列表)。See 输入事件。
这样的按键序列不足以让 command-execute 运行,
但足以用于按键查找或重新绑定。
当按键序列包含多个事件时,按键查找会按顺序处理事件: 先找到第一个事件的绑定,且该绑定必须是键盘映射; 然后在该键盘映射中查找第二个事件的绑定,依此类推, 直到按键序列中的所有事件处理完毕。 (为最后一个事件查找到的绑定可以是键盘映射,也可以不是。) 因此,按键查找过程是基于在键盘映射中查找单个事件这一更简单的过程定义的。 具体行为取决于该键盘映射中与事件关联的对象类型。
我们使用术语 keymap entry 来描述在键盘映射中查找事件类型所得到的值。
(这不包括菜单项的键盘映射元素中的项字符串和其他附加元素,
因为 keymap-lookup 及其他按键查找函数不会在返回值中包含这些内容。)
虽然任意 Lisp 对象都可以作为键盘映射项存入键盘映射,
但并非所有对象对按键查找都有意义。
以下是有意义的键盘映射项类型表:
nil ¶nil 表示查找过程中已使用的事件构成了未定义按键。
当键盘映射完全未提及某事件类型且无默认绑定时,
等价于该事件类型的绑定为 nil。
至此在查找过程中使用的事件构成了一个完整的键, 而 command 是该键的绑定。See 什么是函数?。
该数组(可以是字符串或向量)是一个键盘宏。至此在查找过程中使用的事件 构成了一个完整的键,而该数组是该键的绑定。更多信息参见 键盘宏。
至此在查找过程中使用的事件构成了一个前缀键。按键序列的下一个 事件将在 keymap 中进行查找。
列表的含义取决于其包含的内容:
keymap,那么该列表
是一个按键映射表,并会被当作按键映射表处理(见上文)。
lambda,那么该列表是一个
lambda 表达式。它会被认定为一个函数,并按函数方式处理(见上文)。
为了能作为按键绑定正常执行,
该函数必须是一个命令—即它必须包含 interactive
规范说明。See 定义命令。
symbol 的函数定义会被用来替代 symbol 本身。如果该函数定义同样是一个符号, 则此过程会重复进行,次数不限。 最终这一过程应指向一个属于按键映射表、命令 或键盘宏的对象。
需要注意的是,按键映射表和键盘宏(字符串及向量)并非
有效的函数,因此若一个符号的函数定义是按键映射表、字符串或向量,
则该符号作为函数是无效的。但作为
按键绑定,它是有效的。如果该定义是一个键盘宏,
那么该符号也可作为 command-execute 的有效参数
(see 交互式调用)。
符号 undefined 值得特别说明:它表示将该键视为未定义状态。
严格来说,该键是已定义的,其绑定的命令就是 undefined;
但该命令的行为与未定义键的默认行为一致:
它会响铃(通过调用 ding 函数),但不会触发错误信号。
undefined 用于局部按键映射表中,以覆盖全局按键
绑定并使该键在局部变为未定义状态。若将局部绑定设为
nil 则无法实现此效果,因为 nil 不会覆盖全局绑定。
如果找到任何其他类型的对象,至此在查找过程中使用的事件 构成了一个完整的键,该对象即为该键的绑定,但 此绑定无法作为命令执行。
简而言之,按键映射表条目可以是按键映射表、命令、键盘宏、
指向上述任一类型的符号,或 nil。