diff --git a/doc/misc/eglot.texi b/doc/misc/eglot.texi index d501fe32d5d..c7c296c24ff 100644 --- a/doc/misc/eglot.texi +++ b/doc/misc/eglot.texi @@ -996,6 +996,18 @@ same language server. That file is still outside your project will consider it to be part of the workspace. The default is @code{nil}. +@cindex markdown renderer +@item eglot-documentation-renderer +This variable controls how Eglot renders at-point documentation +imported from the server (@pxref{Eglot Features}). By default, the +variable's value is set during startup to a markdown renderer if +available, either @code{markdown-ts-view-mode} or +@code{gfm-view-mode}. These utilities visually enhance the +documentation content through fontification and other formatting. If +you set it to @code{t}, plain text will be requested from the server +and no rendering is attempted. If the variable's value is @code{nil}, +Eglot will attempt to find a suitable renderer every time. + @item eglot-mode-map This variable is the keymap for binding Eglot-related command. It is in effect only as long as the buffer is managed by Eglot. By default, it diff --git a/etc/EGLOT-NEWS b/etc/EGLOT-NEWS index eb4040d107e..f0f595fa500 100644 --- a/etc/EGLOT-NEWS +++ b/etc/EGLOT-NEWS @@ -32,11 +32,15 @@ New key bindings: 'k' shuts down, 'r' reconnects, 'e' visits the events buffer, 'w' shows workspace configuration, and 'RET' invokes 'eglot-describe-connection'. -** Eglot uses new built-in 'markdown-ts-mode' of Emacs 31 (bug#80127) +** New LSP documentation rendering backends (bug#80127) -This means that on newer versions of Emacs the external -'markdown-mode.el' package does not need to be installed to render -Markdown content. +Eglot uses new built-in 'markdown-ts-mode' of Emacs 31, which means that +on newer versions of Emacs the external 'markdown-mode.el' package does +not need to be installed to render Markdown content. + +The variable 'eglot-documentation-renderer' replaces the now-obsolete +'eglot-prefer-plaintext'. By default, the variable selects a markdown +renderer to use throughout the session. * Changes in Eglot 1.23 (2/4/2026) diff --git a/lisp/progmodes/eglot.el b/lisp/progmodes/eglot.el index e945dfb9739..504a5e12112 100644 --- a/lisp/progmodes/eglot.el +++ b/lisp/progmodes/eglot.el @@ -149,6 +149,8 @@ 'eglot-managed-mode-hook "1.6") (define-obsolete-variable-alias 'eglot-confirm-server-initiated-edits 'eglot-confirm-server-edits "1.16") +(define-obsolete-variable-alias 'eglot-prefer-plaintext + 'eglot-documentation-renderer "1.24") (make-obsolete-variable 'eglot-events-buffer-size 'eglot-events-buffer-config "1.16") (define-obsolete-function-alias 'eglot--uri-to-path #'eglot-uri-to-path "1.16") @@ -535,10 +537,21 @@ or file operation kinds not in the alist." "If non-nil, activate Eglot in cross-referenced non-project files." :type 'boolean) -(defcustom eglot-prefer-plaintext nil - "If non-nil, always request plaintext responses to hover requests." - :type 'boolean - :package-version '(Eglot . "1.17.30")) +(defcustom eglot-documentation-renderer (cond ((eglot--builtin-mdown-p) + 'markdown-ts-view-mode) + ((fboundp 'gfm-view-mode) + 'gfm-view-mode) + (t + nil)) + "Control rendering of LSP documentation fragments. +If set to a major mode symbol `gfm-view-mode' or `markdown-ts-view-mode' +request markdown-snippets and use the corresponding Markdown renderer. +If t, always request and render plain text snippets. If set to nil, +decide dynamically." + :type '(choice (const :tag "Plain text" t) + (const :tag "Auto-detect" nil) + (function :tag "Renderer")) + :package-version '(Eglot . "1.24")) (defcustom eglot-report-progress t "If non-nil, show progress of long running LSP server work. @@ -733,7 +746,7 @@ This can be useful when using docker to run a language server.") (treesit-grammar-location 'markdown))) (defun eglot--accepted-formats () - (if (and (not eglot-prefer-plaintext) + (if (and (not (eq t eglot-documentation-renderer)) (or (fboundp 'gfm-view-mode) (eglot--builtin-mdown-p))) ["markdown" "plaintext"] ["plaintext"])) @@ -2263,12 +2276,14 @@ If MODE, force MODE to be used for fontifying MARKUP." finally return (buffer-string))) (calc2 (forced-mode) (cond - (forced-mode `(,forced-mode)) - ((eglot--builtin-mdown-p) `(,#'markdown-ts-view-mode)) - ((fboundp 'gfm-view-mode) `(,#'gfm-view-mode ,#'gfm-extract)) - (t `(#'text-mode)))) + (forced-mode forced-mode) + ((fboundp eglot-documentation-renderer) eglot-documentation-renderer) + ((eglot--builtin-mdown-p) #'markdown-ts-view-mode) + ((fboundp 'gfm-view-mode) #'gfm-view-mode) + (t #'text-mode))) (calc (s &optional (forced-mode mode) &aux (x (calc2 forced-mode))) - (setq string s render (car x) extract (or (cadr x) #'buffer-string)))) + (setq string s render x + extract (if (eq x 'gfm-view-mode) #'gfm-extract #'buffer-string)))) (cond ((stringp markup) (calc markup)) ; plain string ((setq lang (plist-get markup :language)) ; deprecated MarkedString (calc (format "```%s\n%s\n```" lang (plist-get markup :value))))