From c564e25fb24c3279a39c82e9ffa6df630e240770 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o=20T=C3=A1vora?= Date: Tue, 27 Nov 2018 12:42:56 +0000 Subject: [PATCH] Fix #52: Use entire line as xref summary when available After an original implementation by Michael Livshin. Also close #127. * eglot.el (eglot--xref-make): Rework. (xref-backend-definitions, xref-backend-references) (xref-backend-apropos): Simplify call to `eglot--xref-make'. --- eglot.el | 37 +++++++++++++++++++++++++++---------- 1 file changed, 27 insertions(+), 10 deletions(-) diff --git a/eglot.el b/eglot.el index 4996f5b6..45d97f06 100644 --- a/eglot.el +++ b/eglot.el @@ -1478,13 +1478,30 @@ DUMMY is ignored." (advice-add 'xref-find-definitions :after #'eglot--xref-reset-known-symbols) (advice-add 'xref-find-references :after #'eglot--xref-reset-known-symbols) -(defun eglot--xref-make (name uri position) - "Like `xref-make' but with LSP's NAME, URI and POSITION." - (cl-destructuring-bind (&key line character) position - (xref-make name (xref-make-file-location - (eglot--uri-to-path uri) - ;; F!@(#*&#$)CKING OFF-BY-ONE again - (1+ line) character)))) +(defun eglot--xref-make (name uri range) + "Like `xref-make' but with LSP's NAME, URI and RANGE. +Try to visit the target file for a richer summary line." + (pcase-let* + ((`(,beg . ,end) (eglot--range-region range)) + (file (eglot--uri-to-path uri)) + (visiting (find-buffer-visiting file)) + (collect (lambda () + (eglot--widening + (pcase-let* ((`(,beg . ,end) (eglot--range-region range)) + (bol (progn (goto-char beg) (point-at-bol))) + (substring (buffer-substring bol (point-at-eol)))) + (add-face-text-property (- beg bol) (- end bol) 'highlight + t substring) + (list substring (1+ (current-line)) (current-column)))))) + (`(,summary ,line ,column) + (cond + (visiting (with-current-buffer visiting (funcall collect))) + ((file-readable-p file) (with-temp-buffer (insert-file-contents file) + (funcall collect))) + (t ;; fall back to the "dumb strategy" + (let ((start (cl-getf range :start))) + (list name (1+ (cl-getf start :line)) (cl-getf start :character))))))) + (xref-make summary (xref-make-file-location file line column)))) (defun eglot--sort-xrefs (xrefs) (sort xrefs @@ -1537,7 +1554,7 @@ DUMMY is ignored." (if (vectorp definitions) definitions (vector definitions))))) (eglot--sort-xrefs (mapcar (jsonrpc-lambda (&key uri range) - (eglot--xref-make identifier uri (plist-get range :start))) + (eglot--xref-make identifier uri range)) locations)))) (cl-defmethod xref-backend-references ((_backend (eql eglot)) identifier) @@ -1552,7 +1569,7 @@ DUMMY is ignored." (eglot--sort-xrefs (mapcar (jsonrpc-lambda (&key uri range) - (eglot--xref-make identifier uri (plist-get range :start))) + (eglot--xref-make identifier uri range)) (jsonrpc-request (eglot--current-server-or-lose) :textDocument/references (append @@ -1566,7 +1583,7 @@ DUMMY is ignored." (mapcar (jsonrpc-lambda (&key name location &allow-other-keys) (cl-destructuring-bind (&key uri range) location - (eglot--xref-make name uri (plist-get range :start)))) + (eglot--xref-make name uri range))) (jsonrpc-request (eglot--current-server-or-lose) :workspace/symbol `(:query ,pattern))))))