tools/lookup: Support implementations lookup handlers

This commit is contained in:
Seong Yong-ju 2020-05-12 00:43:16 +09:00
parent 1529dcaaf5
commit 13134726dc
3 changed files with 35 additions and 4 deletions

View file

@ -15,6 +15,9 @@ properties:
:definition FN :definition FN
Run when jumping to a symbol's definition. Used by `+lookup/definition'. Run when jumping to a symbol's definition. Used by `+lookup/definition'.
:implementations FN
Run when looking for implementations of a symbol in the current project. Used
by `+lookup/implementations'.
:references FN :references FN
Run when looking for usage references of a symbol in the current project. Used Run when looking for usage references of a symbol in the current project. Used
by `+lookup/references'. by `+lookup/references'.
@ -46,8 +49,8 @@ change the current buffer or window or return non-nil when it succeeds.
If it doesn't change the current buffer, or it returns nil, the lookup module If it doesn't change the current buffer, or it returns nil, the lookup module
will fall back to the next handler in `+lookup-definition-functions', will fall back to the next handler in `+lookup-definition-functions',
`+lookup-references-functions', `+lookup-file-functions' or `+lookup-implementations-functions', `+lookup-references-functions',
`+lookup-documentation-functions'. `+lookup-file-functions' or `+lookup-documentation-functions'.
Consecutive `set-lookup-handlers!' calls will overwrite previously defined Consecutive `set-lookup-handlers!' calls will overwrite previously defined
handlers for MODES. If used on minor modes, they are stacked onto handlers handlers for MODES. If used on minor modes, they are stacked onto handlers
@ -57,7 +60,7 @@ This can be passed nil as its second argument to unset handlers for MODES. e.g.
(set-lookup-handlers! 'python-mode nil) (set-lookup-handlers! 'python-mode nil)
\(fn MODES &key DEFINITION REFERENCES DOCUMENTATION FILE XREF-BACKEND ASYNC)" \(fn MODES &key DEFINITION IMPLEMENTATIONS REFERENCES DOCUMENTATION FILE XREF-BACKEND ASYNC)"
(declare (indent defun)) (declare (indent defun))
(dolist (mode (doom-enlist modes)) (dolist (mode (doom-enlist modes))
(let ((hook (intern (format "%s-hook" mode))) (let ((hook (intern (format "%s-hook" mode)))
@ -69,15 +72,17 @@ This can be passed nil as its second argument to unset handlers for MODES. e.g.
(fset (fset
fn fn
(lambda () (lambda ()
(cl-destructuring-bind (&key definition references documentation file xref-backend async) (cl-destructuring-bind (&key definition implementations references documentation file xref-backend async)
plist plist
(cl-mapc #'+lookup--set-handler (cl-mapc #'+lookup--set-handler
(list definition (list definition
implementations
references references
documentation documentation
file file
xref-backend) xref-backend)
(list '+lookup-definition-functions (list '+lookup-definition-functions
'+lookup-implementations-functions
'+lookup-references-functions '+lookup-references-functions
'+lookup-documentation-functions '+lookup-documentation-functions
'+lookup-file-functions '+lookup-file-functions
@ -133,6 +138,7 @@ This can be passed nil as its second argument to unset handlers for MODES. e.g.
(let* ((origin (point-marker)) (let* ((origin (point-marker))
(handlers (handlers
(plist-get (list :definition '+lookup-definition-functions (plist-get (list :definition '+lookup-definition-functions
:implementations '+lookup-implementations-functions
:references '+lookup-references-functions :references '+lookup-references-functions
:documentation '+lookup-documentation-functions :documentation '+lookup-documentation-functions
:file '+lookup-file-functions) :file '+lookup-file-functions)
@ -241,6 +247,18 @@ evil-mode is active."
((+lookup--jump-to :definition identifier nil arg)) ((+lookup--jump-to :definition identifier nil arg))
((error "Couldn't find the definition of %S" identifier)))) ((error "Couldn't find the definition of %S" identifier))))
;;;###autoload
(defun +lookup/implementations (identifier &optional arg)
"Jump to the implementations of IDENTIFIER (defaults to the symbol at point).
Each function in `+lookup-implementations-functions' is tried until one changes
the point or current buffer."
(interactive (list (doom-thing-at-point-or-region)
current-prefix-arg))
(cond ((null identifier) (user-error "Nothing under point"))
((+lookup--jump-to :implementations identifier nil arg))
((error "Couldn't find the implementations of %S" identifier))))
;;;###autoload ;;;###autoload
(defun +lookup/references (identifier &optional arg) (defun +lookup/references (identifier &optional arg)
"Show a list of usages of IDENTIFIER (defaults to the symbol at point) "Show a list of usages of IDENTIFIER (defaults to the symbol at point)

View file

@ -3,6 +3,8 @@
;; "What am I looking at?" This module helps you answer this question. ;; "What am I looking at?" This module helps you answer this question.
;; ;;
;; + `+lookup/definition': a jump-to-definition that should 'just work' ;; + `+lookup/definition': a jump-to-definition that should 'just work'
;; + `+lookup/implementations': find a symbol's implementations in the current
;; project
;; + `+lookup/references': find a symbol's references in the current project ;; + `+lookup/references': find a symbol's references in the current project
;; + `+lookup/file': open the file referenced at point ;; + `+lookup/file': open the file referenced at point
;; + `+lookup/online'; look up a symbol on online resources ;; + `+lookup/online'; look up a symbol on online resources
@ -52,6 +54,15 @@ If the argument is interactive (satisfies `commandp'), it is called with
argument: the identifier at point. See `set-lookup-handlers!' about adding to argument: the identifier at point. See `set-lookup-handlers!' about adding to
this list.") this list.")
(defvar +lookup-implementations-functions ()
"Function for `+lookup/implementations' to try. Stops at the first function to
return non-nil or change the current window/point.
If the argument is interactive (satisfies `commandp'), it is called with
`call-interactively' (with no arguments). Otherwise, it is called with one
argument: the identifier at point. See `set-lookup-handlers!' about adding to
this list.")
(defvar +lookup-references-functions (defvar +lookup-references-functions
'(+lookup-xref-references-backend-fn '(+lookup-xref-references-backend-fn
+lookup-project-search-backend-fn) +lookup-project-search-backend-fn)

View file

@ -54,6 +54,7 @@ working on that project after closing the last buffer.")
(set-lookup-handlers! 'lsp-mode :async t (set-lookup-handlers! 'lsp-mode :async t
:documentation #'lsp-describe-thing-at-point :documentation #'lsp-describe-thing-at-point
:definition #'lsp-find-definition :definition #'lsp-find-definition
:implementations #'lsp-find-implementation
:references #'lsp-find-references) :references #'lsp-find-references)
;; TODO Lazy load these. They don't need to be loaded all at once unless the ;; TODO Lazy load these. They don't need to be loaded all at once unless the
@ -189,6 +190,7 @@ auto-killed (which is a potentially expensive process)."
(when (featurep! +peek) (when (featurep! +peek)
(set-lookup-handlers! 'lsp-ui-mode :async t (set-lookup-handlers! 'lsp-ui-mode :async t
:definition 'lsp-ui-peek-find-definitions :definition 'lsp-ui-peek-find-definitions
:implementations 'lsp-ui-peek-find-implementation
:references 'lsp-ui-peek-find-references))) :references 'lsp-ui-peek-find-references)))