Skip to content

Commit

Permalink
lsp-rust: add semantic token modifiers
Browse files Browse the repository at this point in the history
This is more of a proof-of-concept than anything else.

It works for the "mutable" modifier, adding an underline. This matches
what the VsCode client does, but clashes with the lsp-mode default for
read vs write highlighted variables.

The "reference" modifier has the bold attribute set.

The rest have a no-operation face assigned, but need to be there to
get the font caluclation numbers right, and to be customized by users.
  • Loading branch information
alanz committed Oct 6, 2022
1 parent ab659a3 commit eeafcdb
Show file tree
Hide file tree
Showing 2 changed files with 156 additions and 0 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.org
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
* Add ~lsp-sorbet-as-add-on~ variable to allow running the Sorbet server as an add-on alongside Solargraph or others
* Add [[https://github.com/nikeee/dot-language-server][dot-language-server]] (/a.k.a./ Graphviz) support.
* Add [[https://github.com/FractalBoy/perl-language-server][PLS]] support (additional sever for Perl).
* Add some support for rust-analyzer semantic token modifiers. Highlights mutable and reference variables.
** Release 8.0.0
* Add ~lsp-clients-angular-node-get-prefix-command~ to get the Angular server from another location which is still has ~/lib/node_modules~ in it.
* Set ~lsp-clients-angular-language-server-command~ after the first connection to speed up subsequent connections.
Expand Down
155 changes: 155 additions & 0 deletions clients/lsp-rust.el
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
(require 'lsp-mode)
(require 'ht)
(require 'dash)
(require 'lsp-semantic-tokens)

(defgroup lsp-rust nil
"LSP support for Rust, using Rust Language Server or rust-analyzer."
Expand Down Expand Up @@ -926,6 +927,37 @@ or JSON objects in `rust-project.json` format."
(lsp-defun lsp-rust--analyzer-debug-lens ((&Command :arguments? [args]))
(lsp-rust-analyzer-debug args))

(defun lsp-rust-analyzer--semantic-modifiers ()
"Mapping between rust-analyzer keywords and fonts to apply.
The keywords are sent in the initialize response, in the semantic
tokens legend."
'(
("documentation" . lsp-rust-analyzer-documentation-modifier-face)
("declaration" . lsp-rust-analyzer-declaration-modifier-face)
("definition" . lsp-rust-analyzer-definition-modifier-face)
("static" . lsp-rust-analyzer-static-modifier-face)
("abstract" . lsp-rust-analyzer-abstract-modifier-face)
("deprecated" . lsp-rust-analyzer-deprecated-modifier-face)
("readonly" . lsp-rust-analyzer-readonly-modifier-face)
("default_library" . lsp-rust-analyzer-default-library-modifier-face)
("async" . lsp-rust-analyzer-async-modifier-face)
("attribute" . lsp-rust-analyzer-attribute-modifier-face)
("callable" . lsp-rust-analyzer-callable-modifier-face)
("constant" . lsp-rust-analyzer-constant-modifier-face)
("consuming" . lsp-rust-analyzer-consuming-modifier-face)
("control_flow" . lsp-rust-analyzer-control-flow-modifier-face)
("crate_root" . lsp-rust-analyzer-crate-root-modifier-face)
("injected" . lsp-rust-analyzer-injected-modifier-face)
("intra_doc_link" . lsp-rust-analyzer-intra-doc-link-modifier-face)
("library" . lsp-rust-analyzer-library-modifier-face)
("mutable" . lsp-rust-analyzer-mutable-modifier-face)
("public" . lsp-rust-analyzer-public-modifier-face)
("reference" . lsp-rust-analyzer-reference-modifier-face)
("trait" . lsp-rust-analyzer-trait-modifier-face)
("unsafe" . lsp-rust-analyzer-unsafe-modifier-face)
))


(lsp-register-client
(make-lsp-client
:new-connection (lsp-stdio-connection
Expand All @@ -947,6 +979,10 @@ or JSON objects in `rust-project.json` format."
(when lsp-rust-analyzer-server-display-inlay-hints
(lsp-rust-analyzer-inlay-hints-mode)))
:ignore-messages nil

:semantic-tokens-faces-overrides `(:discard-default-modifiers t
:modifiers
,(lsp-rust-analyzer--semantic-modifiers))
:server-id 'rust-analyzer
:custom-capabilities `((experimental . ((snippetTextEdit . ,(and lsp-enable-snippet (featurep 'yasnippet))))))
:download-server-fn (lambda (_client callback error-callback _update?)
Expand Down Expand Up @@ -1290,6 +1326,125 @@ https://github.com/rust-analyzer/rust-analyzer/blob/master/docs/dev/lsp-extensio
(interactive)
(lsp-rust-analyzer-move-item "Down"))


;; Semantic tokens

;; Modifier faces
(defface lsp-rust-analyzer-documentation-modifier-face
'((t nil))
"The face modification to use for documentation items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-declaration-modifier-face
'((t nil))
"The face modification to use for declaration items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-definition-modifier-face
'((t nil))
"The face modification to use for definition items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-static-modifier-face
'((t nil))
"The face modification to use for static items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-abstract-modifier-face
'((t nil))
"The face modification to use for abstract items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-deprecated-modifier-face
'((t nil))
"The face modification to use for deprecated items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-readonly-modifier-face
'((t nil))
"The face modification to use for readonly items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-default-library-modifier-face
'((t nil))
"The face modification to use for default-library items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-async-modifier-face
'((t nil))
"The face modification to use for async items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-attribute-modifier-face
'((t nil))
"The face modification to use for attribute items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-callable-modifier-face
'((t nil))
"The face modification to use for callable items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-constant-modifier-face
'((t nil))
"The face modification to use for constant items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-consuming-modifier-face
'((t nil))
"The face modification to use for consuming items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-control-flow-modifier-face
'((t nil))
"The face modification to use for control-flow items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-crate-root-modifier-face
'((t nil))
"The face modification to use for crate-root items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-injected-modifier-face
'((t nil))
"The face modification to use for injected items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-intra-doc-link-modifier-face
'((t nil))
"The face modification to use for intra-doc-link items.")
:group 'lsp-rust-analyzer

(defface lsp-rust-analyzer-library-modifier-face
'((t nil))
"The face modification to use for library items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-mutable-modifier-face
'((t :underline t))
"The face modification to use for mutable items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-public-modifier-face
'((t nil))
"The face modification to use for public items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-reference-modifier-face
'((t :bold t))
"The face modification to use for reference items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-trait-modifier-face
'((t nil))
"The face modification to use for trait items."
:group 'lsp-rust-analyzer)

(defface lsp-rust-analyzer-unsafe-modifier-face
'((t nil))
"The face modification to use for unsafe items."
:group 'lsp-rust-analyzer)

(lsp-consistency-check lsp-rust)

(provide 'lsp-rust)
Expand Down

0 comments on commit eeafcdb

Please sign in to comment.