这次介绍编辑中关于粘贴复制的部分,不过在Emacs中称粘贴复制为Killing和Yanking,而不是通常说的Cutting和Pasting,当然差别不会太多。
一、Killing
Killing就是指删除指定的一段内容并将其放入kill 环中,kill 环和上章所介绍的标记环差不多也是一个先进先出的队列,我们还可以理解为Windows里的粘贴板。在Emacs中删除命令分为两大类,一类称为kill 命令,这种命令删除的文本会放入kill 环中,比如kill-line,kill-word命令,非常好认。kill命令相对比较安全,我们删除的内容都可以找回来。另一类删除命令称为delete 命令,就是说它们删掉的内容是不会放入kill 环中的,比如说delete-char这样子的。虽然delete 命令删除的内容不放入kill 环,但实际上这两种方式删掉的文本我们都可以用undo命令(C-/,C-_)找回来。
有些时候我们打开的文档是只读属性的不允许修改,不过我们可能会想复制点内容,但直接使用kill命令是不行的,有两个解决办法,一是使用命令M-w (kill-ring-save),这个需要首先标记好一个区域再使用,其实这个命令就是Copy命令,仅将选中内容放入kill 环而不删除。另一个办法是修改变量kill-read-only-ok 为non-nil,这样就可以直接使用kill 命令了,在使用时minibuffer中会有提示。两个办法各有所长,第一个不用改变量选择范围相对灵活,第二个快捷操作更多,大家根据需要选择。
下面分类列出delete命令和kill命令,有些在第三章已经介绍过了,这里再提一下:
C-d (delete-char),删除光标处的字符。
Backspace (delete-backward-char),删除光标前字符。
M-\ (delete-horizontal-space),删除光标处的所有空格和Tab字符。
M-SPC (just-one-space),删除光标处的所有空格和Tab字符,但留下一个。
C-x C-o (delete-blank-lines),删除光标周围的空白行,保留当前行。
M-^ (delete-indentation),将两行合为一行,删除之间的空白和缩进。参见下面两图。
使用M-^之前
使用M-^之后
这里我们可以看出delete命令基本上只能删个把字符,或者一些空白字符,干不了什么大事,也避免了意外删掉大段内容而找不会来。接着我们整理下kill 命令:
C-k (kill-line),从光标处起删除该行。
C-S-Backspace (kill-whole-line),删除整行。
C-w (kill-region),删除区域。
M-w (kill-ring-save),复制到kill 环,而不删除。
M-d (kill-word),删除光标起一个单词。
M-Backspace (backward-kill-word),删除光标前单词。
C-x Backspace (backward-kill-sentence),往前删一句。
M-k (kill-sentence),删除光标起一句。
M-z char (zap-to-char),删至字符char为止。
二、Yanking
前面讲了怎么把文本放入kill 环中,下面接着介绍如何把这些内容拿出来。这里面最常用的便是C-y (yank) 命令,也就是粘贴命令。将光标移到文本中的任何一处使用此命令便可把最近一次放入kill 环中的内容提取出来,其实除了kill 环里的,如果你在任何其它窗口程序中使用了复制命令,紧接着在Emacs里使用C-y,都可以把系统粘贴板中的内容调出。C-y在调出内容后还把使用该命令的点加入了标记环,我们可以很方便的使用C-x C-x 找到是哪个位置插入的文本。
召回的另一个命令是M-y (yank-pop),这个命令只能在刚用完C-y后使用。它的作用是用kill 环中再前一个内容替换掉刚用C-y粘贴出来的内容。简单点说,假如kill 环中有1号、2号、3号记录,使用C-y后3号记录调出,紧接着使用M-y,删掉3号记录,换成2号记录,还有M-y是可以连着多次使用的,我们再按一下1号记录就出来了。虽然这个命令可以使用前一条记录替换此条记录,但它并不会更改kill 环中记录的顺序,仅是一个指针的移动而已。另外M-y 命令可以接受参数调用,比如说C-u 2 M-y 就等价于C-y M-y。
还有一个是C-M-w (append-next-kill),这个命令只有在它下一个命令是kill 命令时才有效,作用是把下个kill 命令删掉的东西和kill 环中最后一个记录合并。
说了这么多关于kill 和yank 的内容,其实最重要的一点还是kill 环,即存放删掉东西的地方。Emacs维持的是一个全局kill 环,所有打开的buffer都可以使用。在kill 环中默认是保存前面60个删除的内容,可以使用变量kill-ring-max 来修改这个值。而kill 环中的内容是保存在kill-ring 这个变量中的,命令C-h v kill-ring 可以查看我们之前删了些什么东西。
正常情况来说,每次使用kill 命令都会在kill 环中新建一个记录来保存这次删除的东西,不过如果我们连续使用kill 命令,这一系列命令所删除的内容只会保存在一个记录中。比如我们有下面一段文本:
I have nothing◇to say. Good luck!
光标在nothing 和to之间,连续按M-d,M-Backspace,M-d,M-Backspace,文本变为:
I ◇. Good luck!
此时使用C-y会一次性将所有删除全部召回。这就说明了kill环具有一定的智能性,并不是简单的保存每次删除。不过,一旦在kill 命令中间插入了任何其它命令,包括移动光标都会使下次删除的内容在kill 环中新建立一个记录。所以我们还有C-M-w 命令强制下次删除加入上一个记录中。呃,需要注意的是M-w命令在任何时候都是新建一个记录。
三、快速复制
有的时候我们可能会想把一段内容临时保存在一个地方可供单独编辑或者以后使用,很明显kill 环不是个好地方,那新建立一个文件呢?kill 环反正也是全局的,通过它来进行复制。这个办法是不错,不过步骤稍显多了点,Emacs为了解决这种问题提供了下面几个命令:
append-to-buffer 将区域中内容加入到一个buffer中。
prepend-to-buffer 将区域中内容加入到一个buffer中,不过加入位置在该buffer的光标前。
copy-to-buffer 将区域中内容加入到一个buffer中,删除该buffer原有内容。
insert-buffer 在该位置插入指定的buffer中所有内容。
append-to-file 将区域中内容复制到一个文件中。
这些命令都只能通过M-x 来调用,而且基本都需要选中一个区域再进行操作,作用都很好理解,这里就不详细说了。
四、CUA绑定
CUA(Common User Access),Windows,Linux,Mac 都是CUA系统。CUA绑定就是说常规的C-c (copy),C-v (Paste),C-x (Cut)还是按系统定义来使用。通过M-x cua-mode 命令可以将Emacs的粘贴复制设为上述方式。这是CUA一个常见的应用方式,不过这里我不推荐大家使用这种方式,毕竟Emacs已经形成了自己的风格何必将就别人。CUA绑定还有其它很多注意的地方,改了后反而麻烦。
小结:
按键 |
命令 |
作用 |
---|---|---|
C-d |
delete-char |
删除光标处字符 |
Backspace |
delete-backward-char |
删除光标前字符 |
M-\ |
delete-horizontal-space |
删除光标处的所有空格和Tab字符 |
M-SPC |
just-one-space |
删除光标处的所有空格和Tab字符,但留下一个 |
C-x C-o |
delete-blank-lines |
删除光标周围的空白行,保留当前行 |
M-^ |
delete-indentation |
将两行合为一行,删除之间的空白和缩进 |
C-k |
kill-line |
从光标处起删除该行 |
C-S-Backspace |
kill-whole-line |
删除整行 |
C-w |
kill-region |
删除区域 |
M-w |
kill-ring-save |
复制到kill 环,而不删除 |
M-d |
kill-word |
删除光标起一个单词 |
M-Backspace |
backward-kill-word |
删除光标前单词 |
M-k | kill-sentence |
删除光标起一句 |
C-x Backspace |
backward-kill-sentence |
删除光标前删一句 |
M-z char |
zap-to-char |
删至字符char为止 |
C-y |
yank |
召回 |
M-y |
yank-pop |
召回前一个 |
C-M-w |
append-next-kill |
下一个删掉内容和上次删除合并 |
C-h v |
describe-variable |
显示变量内容 |
(none) |
append-to-buffer |
将区域中内容加入到一个buffer中 |
(none) |
prepend-to-buffer |
将区域中内容加入到一个buffer光标前 |
(none) |
copy-to-buffer |
区域中内容加入到一个buffer中,删除该buffer原有内容 |
(none) |
insert-buffer |
在该位置插入指定的buffer中所有内容 |
(none) |
append-to-file |
将区域中内容复制到一个文件中 |
(none) |
cua-mode |
启用/停用CUA绑定 |
变量 |
作用 |
---|---|
kill-read-only-ok |
是否在只读文件启用kill 命令 |
kill-ring |
kill环 |
kill-ring-max |
kill环容量 |