From 18faa0ba32c9ce751c16960b2a39b3880b523272 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 2 Apr 2022 02:19:54 +0200 Subject: Suggestive patch for simplified completion NOTE: The patch is largely untested. Modifications: - Update readme.org - Remove geiser-company - Move Company extensions to geiser-completion Omissions: - geiser-company--inhibit-autodoc has been removed. Eldoc handling should be implemented in the frontend, not in the backend. See for example: https://github.com/minad/corfu/blob/04fbfce3d7e9c125a7fd22a34455a508247a522b/corfu.el#L1212 - The quickhelp-string action and geiser-company--docstring have been removed. company-quickhelp can use `:company-doc-buffer` instead with minimal overhead. See: https://github.com/company-mode/company-quickhelp/blob/3ca2708b4e5190205aca01d65fe1b391963a53f9/company-quickhelp.el#L138 - The automatic Company setup has been removed. Personally I am not a fan of such auto configuration. It is better if completion is configured consistently in the user configuration. You may want to restore the auto configuration for backward compatibility. It depends on your backward compatibility story. I am fine with rare breaking changes from time to time. - There is a cyclic dependency between geiser-edit/geiser-doc and geiser-completion, which should be untangled. --- elisp/geiser-company.el | 148 --------------------------------------------- elisp/geiser-completion.el | 32 +++++++++- elisp/geiser-mode.el | 7 --- elisp/geiser-reload.el | 1 - elisp/geiser-repl.el | 6 -- readme.org | 11 ++-- 6 files changed, 37 insertions(+), 168 deletions(-) delete mode 100644 elisp/geiser-company.el diff --git a/elisp/geiser-company.el b/elisp/geiser-company.el deleted file mode 100644 index adc3654..0000000 --- a/elisp/geiser-company.el +++ /dev/null @@ -1,148 +0,0 @@ -;;; geiser-company.el -- integration with company-mode - -;; Copyright (C) 2009, 2010, 2011, 2012, 2013, 2014, 2016 Jose Antonio Ortega Ruiz - -;; This program is free software; you can redistribute it and/or -;; modify it under the terms of the Modified BSD License. You should -;; have received a copy of the license along with this program. If -;; not, see . - -;; Start date: Mon Aug 24, 2009 12:44 - - -;;; Code: - -(require 'geiser-autodoc) -(require 'geiser-completion) -(require 'geiser-edit) -(require 'geiser-base) -(require 'geiser-doc) - -(eval-when-compile (require 'cl-lib)) - - -;;; Helpers: - -(defvar-local geiser-company--enabled-flag nil) - -(defvar-local geiser-company--autodoc-flag nil) - -(defvar-local geiser-company--completions nil) - -(defun geiser-company--candidates (prefix) - (and (equal prefix (car geiser-company--completions)) - (cdr geiser-company--completions))) - -(defun geiser-company--doc (id) - (ignore-errors - (when (not (geiser-autodoc--inhibit)) - (let ((help (geiser-autodoc--autodoc `((,id 0)) nil))) - (and help (substring-no-properties help)))))) - -(defun geiser-company--doc-buffer (id) - (let* ((impl geiser-impl--implementation) - (module (geiser-eval--get-module)) - (symbol (make-symbol id)) - (ds (geiser-doc--get-docstring symbol module))) - (if (or (not ds) (not (listp ds))) - (progn - (message "No documentation available for '%s'" symbol) - nil) - (with-current-buffer (get-buffer-create "*company-documentation*") - (geiser-doc--render-docstring ds symbol module impl) - (current-buffer))))) - -(defun geiser-company--docstring (id) - (let* ((module (geiser-eval--get-module)) - (symbol (make-symbol id)) - (ds (geiser-doc--get-docstring symbol module))) - (and ds - (listp ds) - (concat (geiser-autodoc--str* (cdr (assoc "signature" ds))) - "\n\n" - (cdr (assoc "docstring" ds)))))) - -(defun geiser-company--location (id) - (ignore-errors - (when (not (geiser-autodoc--inhibit)) - (let ((id (make-symbol id))) - (condition-case nil - (geiser-edit-module id 'noselect) - (error (geiser-edit-symbol id 'noselect))))))) - -(defun geiser-company--prefix-at-point () - (ignore-errors - (when (and (not (geiser-autodoc--inhibit)) geiser-company--enabled-flag) - (if (nth 8 (syntax-ppss)) 'stop - (let* ((prefix (and (looking-at-p "\\_>") - (geiser-completion--prefix nil))) - (cmps1 (and prefix - (geiser-completion--complete prefix nil))) - (cmps2 (and prefix - (geiser-completion--complete prefix t))) - (mprefix (and (not cmps1) (not cmps2) - (geiser-completion--prefix t))) - (cmps3 (and mprefix (geiser-completion--complete mprefix t))) - (cmps (or cmps3 (append cmps1 cmps2))) - (prefix (or mprefix prefix))) - (setq geiser-company--completions (cons prefix cmps)) - prefix))))) - - -;;; Activation - -(defun geiser-company--setup (enable) - (setq geiser-company--enabled-flag enable) - (when (fboundp 'geiser-company--setup-company) - (geiser-company--setup-company enable))) - -(defun geiser-company--inhibit-autodoc (ignored) - (when (setq geiser-company--autodoc-flag geiser-autodoc-mode) - (geiser-autodoc-mode -1))) - -(defun geiser-company--restore-autodoc (&optional ignored) - (when geiser-company--autodoc-flag - (geiser-autodoc-mode 1))) - - -;;; Company activation - -(declare-function company-begin-backend "ext:company") -(declare-function company-cancel "ext:company") -(declare-function company-mode "ext:company") -(defvar company-backends) -(defvar company-active-map) -(eval-after-load "company" - '(progn - (defun geiser-company-backend (command &optional arg &rest ignored) - "A `company-mode' completion back-end for `geiser-mode'." - (interactive (list 'interactive)) - (cl-case command - ('interactive (company-begin-backend 'geiser-company-backend)) - ('prefix (geiser-company--prefix-at-point)) - ('candidates (geiser-company--candidates arg)) - ('meta (geiser-company--doc arg)) - ('doc-buffer (geiser-company--doc-buffer arg)) - ('quickhelp-string (geiser-company--docstring arg)) - ('location (geiser-company--location arg)) - ('sorted t))) - (defun geiser-company--setup-company (enable) - (when enable - (set (make-local-variable 'company-backends) - (add-to-list 'company-backends 'geiser-company-backend))) - (company-mode (if enable 1 -1))) - (add-hook 'company-completion-finished-hook - 'geiser-company--restore-autodoc) - (add-hook 'company-completion-cancelled-hook - 'geiser-company--restore-autodoc) - (add-hook 'company-completion-started-hook - 'geiser-company--inhibit-autodoc) - (define-key company-active-map (kbd "M-`") - (lambda () - (interactive) - (company-cancel) - (call-interactively 'geiser-completion--complete-module))))) - - - -(provide 'geiser-company) diff --git a/elisp/geiser-completion.el b/elisp/geiser-completion.el index 9943030..7696ec5 100644 --- a/elisp/geiser-completion.el +++ b/elisp/geiser-completion.el @@ -17,6 +17,8 @@ (require 'geiser-log) (require 'geiser-syntax) (require 'geiser-base) +;; (require 'geiser-edit) TODO untangle cyclic dependency +;; (require 'geiser-doc) TODO untangle cyclic dependency (require 'comint) (require 'minibuffer) @@ -132,6 +134,30 @@ we're looking for a module name.") (point))) (scan-error pos))))) +(defun geiser-completion--company-docsig (id) + (ignore-errors + (when (not (geiser-autodoc--inhibit)) + (let ((help (geiser-autodoc--autodoc `((,id 0))))) + (and help (substring-no-properties help)))))) + +(defun geiser-completion--company-doc-buffer (id) + (let* ((impl geiser-impl--implementation) + (module (geiser-eval--get-module)) + (symbol (make-symbol id)) + (ds (geiser-doc--get-docstring symbol module))) + (when (consp ds) + (with-current-buffer (get-buffer-create "*company-documentation*") + (geiser-doc--render-docstring ds symbol module impl) + (current-buffer))))) + +(defun geiser-completion--company-location (id) + (ignore-errors + (when (not (geiser-autodoc--inhibit)) + (let ((id (make-symbol id))) + (condition-case nil + (geiser-edit-module id 'noselect) + (error (geiser-edit-symbol id 'noselect))))))) + (defun geiser-completion--thing-at-point (module &optional predicate) (with-syntax-table scheme-mode-syntax-table (let* ((beg (geiser-completion--symbol-begin module)) @@ -142,7 +168,11 @@ we're looking for a module name.") (match-string 1 prefix) prefix))) (cmps (and prefix (geiser-completion--complete prefix module)))) - (and cmps (list beg end cmps))))) + (when cmps + (list beg end cmps + :company-docsig #'geiser-completion--company-docsig + :company-doc-buffer #'geiser-completion--company-doc-buffer + :company-location #'geiser-completion--company-location))))) (defun geiser-completion--for-symbol (&optional predicate) (geiser-completion--thing-at-point nil predicate)) diff --git a/elisp/geiser-mode.el b/elisp/geiser-mode.el index a7f49a1..2354bf2 100644 --- a/elisp/geiser-mode.el +++ b/elisp/geiser-mode.el @@ -17,7 +17,6 @@ (require 'geiser-doc) (require 'geiser-compile) (require 'geiser-completion) -(require 'geiser-company) (require 'geiser-xref) (require 'geiser-edit) (require 'geiser-autodoc) @@ -53,11 +52,6 @@ active when `geiser-mode' is activated in a buffer." :group 'geiser-autodoc :type 'boolean) -(geiser-custom--defcustom geiser-mode-company-p t - "Whether to use company-mode for completion, if available." - :group 'geiser-mode - :type 'boolean) - (geiser-custom--defcustom geiser-mode-smart-tab-p nil "Whether `geiser-smart-tab-mode' gets enabled by default in Scheme buffers." :group 'geiser-mode @@ -391,7 +385,6 @@ interacting with the Geiser REPL is at your disposal. (when geiser-mode (geiser-impl--set-buffer-implementation nil t)) (setq geiser-autodoc-mode-string "/A") (setq geiser-smart-tab-mode-string "/T") - (geiser-company--setup (and geiser-mode geiser-mode-company-p)) (geiser-completion--setup geiser-mode) (when geiser-mode-autodoc-p (geiser-autodoc-mode (if geiser-mode 1 -1))) diff --git a/elisp/geiser-reload.el b/elisp/geiser-reload.el index 3e9352e..e6bea24 100644 --- a/elisp/geiser-reload.el +++ b/elisp/geiser-reload.el @@ -29,7 +29,6 @@ geiser-xref geiser-compile geiser-debug - geiser-company geiser-edit geiser-completion geiser-autodoc diff --git a/elisp/geiser-repl.el b/elisp/geiser-repl.el index b66e000..e9567b3 100644 --- a/elisp/geiser-repl.el +++ b/elisp/geiser-repl.el @@ -10,7 +10,6 @@ ;;; Code: -(require 'geiser-company) (require 'geiser-doc) (require 'geiser-autodoc) (require 'geiser-edit) @@ -106,10 +105,6 @@ change that." "Whether to enable `geiser-autodoc-mode' in the REPL by default." :type 'boolean) -(geiser-custom--defcustom geiser-repl-company-p t - "Whether to use company-mode for completion, if available." - :type 'boolean) - (geiser-custom--defcustom geiser-repl-read-only-prompt-p t "Whether the REPL's prompt should be read-only." :type 'boolean) @@ -560,7 +555,6 @@ will be set up using `geiser-connect-local' when a REPL is started.") (geiser-repl--connection-setup impl address prompt-rx deb-prompt-rx)) (geiser-repl--startup impl address) (geiser-repl--autodoc-mode 1) - (geiser-company--setup geiser-repl-company-p) (geiser-repl--set-up-load-path) (add-hook 'comint-output-filter-functions 'geiser-repl--output-filter diff --git a/readme.org b/readme.org index 480c299..22632f1 100644 --- a/readme.org +++ b/readme.org @@ -99,16 +99,17 @@ To start a REPL, run =M-x geiser=. -** Completion with company-mode +** Completion at point Geiser offers identifier and module name completion, bound to =M-TAB= and =M-`= respectively. Only names visible in the current module are offered. - While that is cool and all, things are even better: if you have - [[http://company-mode.github.io/][company mode]] installed, Geiser's completion will use it. Just - require company-mode and, from then on, any new scheme buffer or - REPL will use it. + While that is cool and all, things are even better: if you have [[http://company-mode.github.io/][Company]] or + [[https://github.com/minad/corfu][Corfu]] installed, Geiser's completion will integrate with it. Just enable + global-company-mode/corfu-global-mode and, from then on, any new scheme + buffer or REPL will use it. Alternatively you can activate company-mode or + corfu-mode individually only in some buffers. ** Macro expansion with macrostep-geiser -- cgit v1.2.3