yank
在学习了current-kill
之后,yank
函数的代码几乎变得很简单。
yank
函数不直接使用kill-ring-yank-pointer
变量。它调用insert-for-yank
,而insert-for-yank
又调用current-kill
,后者设置了kill-ring-yank-pointer
变量。
代码如下:
(defun yank (&optional arg) "重新插入(\"粘贴\")最近一次删除的文本段。 更准确地说,重新插入最近一次删除或粘贴的文本段。将光标放在末尾,并在开头设置标记。 使用 \\[universal-argument] 作为参数时,效果相同,但将光标放在开头(标记放在末尾)。 带有参数N时,重新插入第N个最近删除的文本段。 当此命令将删除的文本插入缓冲区时,将遵循`yank-excluded-properties'和`yank-handler',如`insert-for-yank-1'的文档字符串所述,请参见。 还可以参考命令`yank-pop'(\\[yank-pop])."
(interactive "*P") (setq yank-window-start (window-start)) ;; 如果没有完全执行,使last-command指示随后的命令。 (setq this-command t) (push-mark (point))
(insert-for-yank (current-kill (cond ((listp arg) 0) ((eq arg '-) -2) (t (1- arg))))) (if (consp arg) ;; 这类似于exchange-point-and-mark,但不激活标记。 ;; 尽管命令循环会因为插入文本而取消激活标记,但避免激活更清晰。 (goto-char (prog1 (mark t) (set-marker (mark-marker) (point) (current-buffer)))))
;; 如果完全执行,使this-command指示。 (if (eq this-command t) (setq this-command 'yank)) nil)
关键表达式是insert-for-yank
,它插入由current-kill
返回的字符串,但从中删除了一些文本属性。
然而,在到达该表达式之前,函数将yank-window-start
的值设置为(window-start)
表达式返回的位置,即显示当前开始的位置。yank
函数还设置了this-command
并推送了标记。
在它插入适当的元素之后,如果可选参数是CONS而不是数字或为空,它将光标放在插入的文本的开头,并在其末尾设置标记。
(prog1
函数类似于progn
,但返回其第一个参数的值,而不是其最后一个参数的值。其第一个参数被强制为整数返回缓冲区的标记。可以通过将光标置于此缓冲区中的这些函数上,然后键入C-h f(describe-function
)并随后键入RET来查看这些函数的文档;默认为函数。)
函数成功时的最后部分说明了要做什么。