diff --git a/modules/editor/format/autoload/format.el b/modules/editor/format/autoload/format.el index fe78af107..aeed07770 100644 --- a/modules/editor/format/autoload/format.el +++ b/modules/editor/format/autoload/format.el @@ -8,6 +8,9 @@ ;;;###autoload (autoload 'apheleia--get-formatters "apheleia-formatters") +;;;###autoload +(defvar +format--region-p nil) + ;;;###autoload (defun +format-region (start end &optional callback) "Format from START to END with `apheleia'." @@ -41,22 +44,21 @@ (when (> indent 0) (indent-rigidly (point-min) (point-max) (- indent))) ;; - (apheleia-format-buffer - command - (lambda () - (with-current-buffer formatted-buffer - (when (> indent 0) - ;; restore indentation without affecting new indentation - (indent-rigidly (point-min) (point-max) - (max 0 (- indent (+format--current-indentation))))) - (set-buffer-modified-p nil)) - (with-current-buffer cur-buffer - (delete-region start end) - (goto-char start) - (save-excursion - (insert-buffer-substring-no-properties formatted-buffer) - (when callback (funcall callback))) - (kill-buffer formatted-buffer))))) + (let ((+format--region-p (cons start end))) + (apheleia-format-buffer + command + (lambda () + (with-current-buffer formatted-buffer + (when (> indent 0) + ;; restore indentation without affecting new indentation + (indent-rigidly (point-min) (point-max) + (max 0 (- indent (+format--current-indentation))))) + (set-buffer-modified-p nil)) + (with-current-buffer cur-buffer + (with-silent-modifications + (replace-region-contents start end (lambda () formatted-buffer) 5)) + (when callback (funcall callback)) + (kill-buffer formatted-buffer)))))) (when (doom-region-active-p) (setq deactivate-mark t))))) diff --git a/modules/editor/format/autoload/lsp.el b/modules/editor/format/autoload/lsp.el index ac8daeb76..c9cc5540c 100644 --- a/modules/editor/format/autoload/lsp.el +++ b/modules/editor/format/autoload/lsp.el @@ -46,40 +46,38 @@ mode unconditionally, call `+format-with-lsp-mode' instead." (cl-defun +format-lsp-buffer (&rest plist &key buffer callback &allow-other-keys) "Format the current buffer with any available lsp-mode or eglot formatter." (if-let* ((fn (with-current-buffer buffer (+format--lsp-fn))) - ((apply fn plist))) + ((apply fn (car +format--region-p) (cdr +format--region-p) + plist))) (funcall callback) (funcall callback "LSP server doesn't support formatting"))) -(cl-defun +format--with-lsp-mode (&key buffer scratch &allow-other-keys) - "Format the current buffer with any available lsp-mode formatter." +(cl-defun +format--with-lsp-mode (beg end &key buffer &allow-other-keys) + "Format the current buffer or region with any available lsp-mode formatter. + +Won't forward the buffer to chained formatters if successful." (with-current-buffer buffer (let ((edits - (cond - ((lsp-feature? "textDocument/formatting") - (lsp-request "textDocument/formatting" - (lsp--make-document-formatting-params))) - ((lsp-feature? "textDocument/rangeFormatting") - (lsp-request "textDocument/rangeFormatting" - (lsp--make-document-range-formatting-params - (point-min) (point-max)))) - (:err)))) - (unless (eq edits :err) - (unless (seq-empty-p edits) - (with-current-buffer scratch - (lsp--apply-text-edits edits 'format))) - t)))) - -(cl-defun +format--with-eglot (&key buffer scratch &allow-other-keys) - "Format the current buffer with any available eglot formatter." - (with-current-buffer scratch - (when (setq-local - eglot--cached-server - (with-current-buffer buffer - (when (or (eglot-server-capable :documentFormattingProvider) - (eglot-server-capable :documentRangeFormattingProvider)) - (eglot-current-server)))) - (let ((buffer-file-name (buffer-file-name buffer))) - (eglot-format-buffer)) + (cond ((and (null beg) (lsp-feature? "textDocument/formatting")) + (lsp-request "textDocument/formatting" + (lsp--make-document-formatting-params))) + ((lsp-feature? "textDocument/rangeFormatting") + (lsp-request "textDocument/rangeFormatting" + (lsp--make-document-range-formatting-params + (or beg (point-min)) (or end (point-max))))) + ;; try next chained formatter(s) + ((cl-return (ignore (funcall callback))))))) + (unless (seq-empty-p edits) + (lsp--apply-text-edits edits 'format)) t))) +(cl-defun +format--with-eglot (beg end &key buffer callback &allow-other-keys) + "Format the current buffer or region with any available eglot formatter. + +Won't forward the buffer to chained formatters if successful." + (with-current-buffer buffer + (or (with-demoted-errors "%s" + (always (eglot-format beg end))) + ;; try next chained formatter(s) + (ignore (funcall callback))))) + ;;; lsp.el ends here