The SLIME Emacs package for Common Lisp supports cross-referencing: one can list all references pointing to a symbol, move through this list and jump to the source code of each reference.
Removing automatic reference jumps
While cross-referencing is very useful, the default configuration is frustrating: moving through the list in the Emacs buffer triggers the jump to the reference under the cursor. If you are interested in a reference in the middle of the list, you will have to move to it, opening multiple buffers you do not care about as a side effect. I finally took the time to fix it.
Key bindings for
slime-ref-mode mode are stored in the
keymap. After a quick look in
slime.el, it is easy to remove bindings for
(define-key slime-xref-mode-map (kbd "n") nil) (define-key slime-xref-mode-map [remap next-line] nil) (define-key slime-xref-mode-map (kbd "p") nil) (define-key slime-xref-mode-map [remap previous-line] nil)
If you are using
use-package, it is even simpler:
(use-package slime (:map slime-xref-mode-map (("n") ([remap next-line]) ("p") ([remap previous-line]))))
Changing the way references are used
SLIME supports two ways to jump to a reference:
space, it spawns a buffer containing the source file and close the cross-referencing buffer.
v, it spawns the source file buffer but keeps the cross-referencing buffer open and keeps it current.
This is not practical to me, so I made a change. The default action, triggered
return, now keeps the cross-referencing buffer open and switches to the
source file in the same window. This way, I can switch back to the
cross-referencing buffer with
C-x b to select another reference without
spawning buffers in other windows (I do not like having my windows hijacked by
To do that, I need a new function:
(defun g-slime-show-xref () "Display the source file of the cross-reference under the point in the same window." (interactive) (let ((location (slime-xref-location-at-point))) (slime-goto-source-location location) (with-selected-window (display-buffer-same-window (current-buffer) nil) (goto-char (point)) (g-recenter-window))))
Note the use of
g-recenter-window, a custom function to move the current
point at eye level. Feel free to use
recenter function instead.
I then bind the function to
return and remove other bindings:
(define-key slime-xref-mode-map (kbd "RET") 'g-slime-show-xref) (define-key slime-xref-mode-map (kbd "SPC") nil) (define-key slime-xref-mode-map (kbd "v") nil)
Much better now!