Skip to content

Commit

Permalink
command-commands.lisp: use new prompt-buffer
Browse files Browse the repository at this point in the history
  • Loading branch information
jmercouris committed Feb 26, 2021
1 parent 4d746c1 commit dc309cd
Show file tree
Hide file tree
Showing 3 changed files with 70 additions and 76 deletions.
116 changes: 67 additions & 49 deletions source/command-commands.lisp
Expand Up @@ -11,31 +11,42 @@
:documentation "The hook value."))
(:accessor-name-transformer (hu.dwim.defclass-star:make-name-transformer name)))

(defmethod object-string ((hook-desc hook-description))
(name hook-desc))
(defmethod object-display ((hook-desc hook-description))
(name hook-desc))
(defmethod prompter:object-properties ((hook-description hook-description))
(list :name (name hook-description)
:value (value hook-description)))

(defmethod object-string ((handler hooks:handler))
(str:downcase (hooks:name handler)))
(defmethod object-display ((handler hooks:handler))
(str:downcase (hooks:name handler)))
(defmethod prompter:object-properties ((handler hooks:handler))
(list :name (str:downcase (hooks:name handler))))

(defun command-suggestion-filter (&optional mode-symbols)
(let* ((commands
(sort (apply #'list-commands mode-symbols) #'> :key #'access-time))
(pretty-commands (mapcar #'command-display commands)))
(lambda (minibuffer)
(fuzzy-match (input-buffer minibuffer) commands :suggestions-display pretty-commands))))
(defun get-commands (&optional (buffer (current-buffer)))
(sort (apply #'list-commands
(mapcar #'mode-name (modes buffer)))
#'> :key #'access-time))

(defmethod prompter:object-properties ((command command))
(let* ((buffer (active-buffer (current-window :no-rescan)))
(scheme-name (keymap-scheme-name buffer))
(bindings '()))
(loop for mode in (modes buffer)
for scheme-keymap = (keymap:get-keymap scheme-name (keymap-scheme mode))
when scheme-keymap
do (setf bindings (keymap:binding-keys (sym command) scheme-keymap))
when (not (null bindings))
return bindings)
(list :name (string-downcase (sym command))
:bindings (format nil "~{~a~^, ~}" bindings))))

(define-class command-source (prompter:source)
((prompter:name "Commands")
(prompter:must-match-p t)
(prompter:initial-suggestions (get-commands))))

(define-command execute-command ()
"Execute a command by name."
(unless (active-minibuffers (current-window))
(let ((command (prompt-minibuffer
:input-prompt "Execute command"
:suggestion-function (command-suggestion-filter
(mapcar #'mode-name
(modes (current-buffer))))
(let ((command (prompt
:prompt "Execute command"
:sources (make-instance 'command-source)
:hide-suggestion-count-p t)))
(setf (access-time command) (get-internal-real-time))
(run-async command))))
Expand All @@ -44,10 +55,9 @@
"Execute a command by name, also supply required, optional, and
keyword parameters."
;; TODO: prefill default-values when prompting optional/key arguments
(let* ((command (prompt-minibuffer
:input-prompt "Execute extended command"
:suggestion-function (command-suggestion-filter
(mapcar #'mode-name (modes (current-buffer))))
(let* ((command (prompt
:prompt "Execute extended command"
:sources (make-instance 'command-source)
:hide-suggestion-count-p t))
(command-symbol (sym command))
(argument-list (swank::arglist command-symbol))
Expand Down Expand Up @@ -77,7 +87,7 @@ keyword parameters."
:input-prompt (second (car argument))))))))
(setf (access-time command) (get-internal-real-time))))

(defun hook-suggestion-filter ()
(defun get-hooks ()
(flet ((list-hooks (object)
(mapcar (lambda (hook)
(make-instance 'hook-description
Expand All @@ -92,38 +102,46 @@ keyword parameters."
(let ((window-hooks (list-hooks (current-window)))
(buffer-hooks (list-hooks (current-buffer)))
(browser-hooks (list-hooks *browser*)))
(lambda (minibuffer)
(fuzzy-match (input-buffer minibuffer)
(append window-hooks
buffer-hooks
browser-hooks))))))
(append window-hooks
buffer-hooks
browser-hooks))))

(define-class hook-source (prompter:source)
((prompter:name "Hooks")
(prompter:must-match-p t)
(prompter:initial-suggestions (get-hooks))))

(defun handler-suggestion-filter (hook)
(lambda (minibuffer)
(fuzzy-match (input-buffer minibuffer)
(hooks:handlers hook))))
(define-class handler-source (prompter:source)
((prompter:name "Handlers")
(prompter:must-match-p t)
(hook :accessor hook
:initarg :hook
:documentation "The hook for which to retrieve handlers for.")
(prompter:constructor (lambda (source)
(hooks:handlers (hook source))))))

(defun disabled-handler-suggestion-filter (hook)
(lambda (minibuffer)
(fuzzy-match (input-buffer minibuffer)
(hooks:disabled-handlers hook))))
(define-class disabled-handler-source (handler-source)
((prompter:constructor (lambda (source)
(hooks:disabled-handlers (hook source))))))

(define-command disable-hook-handler ()
"Remove handler(s) from a hook."
(let* ((hook-desc (prompt-minibuffer
:input-prompt "Hook where to disable handler"
:suggestion-function (hook-suggestion-filter)))
(handler (prompt-minibuffer
:input-prompt (format nil "Disable handler from ~a" (name hook-desc))
:suggestion-function (handler-suggestion-filter (value hook-desc)))))
(let* ((hook-desc (prompt
:prompt "Hook where to disable handler"
:sources (make-instance 'hook-source)))
(handler (prompt
:prompt (format nil "Disable handler from ~a" (name hook-desc))
:sources (make-instance 'handler-source
:hook (value hook-desc)))))
(hooks:disable-hook (value hook-desc) handler)))

(define-command enable-hook-handler ()
"Remove handler(s) from a hook."
(let* ((hook-desc (prompt-minibuffer
:input-prompt "Hook where to enable handler"
:suggestion-function (hook-suggestion-filter)))
(handler (prompt-minibuffer
:input-prompt (format nil "Enable handler from ~a" (name hook-desc))
:suggestion-function (disabled-handler-suggestion-filter (value hook-desc)))))
(let* ((hook-desc (prompt
:prompt "Hook where to enable handler"
:sources (make-instance 'hook-source)))
(handler (prompt
:prompt (format nil "Enable handler from ~a" (name hook-desc))
:sources (make-instance 'disabled-handler-source
:hook (value hook-desc)))))
(hooks:enable-hook (value hook-desc) handler)))
24 changes: 0 additions & 24 deletions source/command.lisp
Expand Up @@ -252,37 +252,13 @@ extra fiddling."
(defmethod object-string ((command command))
(str:downcase (sym command)))

(defmethod object-display ((command command))
(command-display command))

(defmethod command-function ((command command))
"Return the function associated to COMMAND.
This function can be `funcall'ed."
(symbol-function (find-symbol
(string (sym command))
(pkg command))))

(defun command-display (command)
;; Use `(current-window :no-rescan)' or else the minibuffer will stutter
;; because of the FFI calls.
(let* ((buffer (active-buffer (current-window :no-rescan)))
(scheme-name (keymap-scheme-name buffer))
(bindings '()))
(loop for mode in (modes buffer)
for scheme-keymap = (keymap:get-keymap scheme-name (keymap-scheme mode))
when scheme-keymap
do (setf bindings (keymap:binding-keys (sym command) scheme-keymap))
when (not (null bindings))
return bindings)
(format nil "~a~a~a"
(str:downcase (sym command))
(if bindings
(format nil " (~{~a~^, ~})" bindings)
"")
(match (object-string (pkg command))
((or "" "nyxt" "nyxt-user") "")
(a (format nil " [~a]" a))))))

(declaim (ftype (function (function) (or null command)) function-command))
(defun function-command (function)
"Return the command associated to FUNCTION, if any."
Expand Down
6 changes: 3 additions & 3 deletions source/help.lisp
Expand Up @@ -158,9 +158,9 @@ For generic functions, describe all the methods."
"Inspect a command and show it in a help buffer.
A command is a special kind of function that can be called with
`execute-command' and can be bound to a key."
(let ((input (prompt-minibuffer
:input-prompt "Describe command"
:suggestion-function (command-suggestion-filter))))
(let ((input (prompt
:prompt "Describe command"
:sources (make-instance 'command-source))))
(describe-command* input)))

(defun describe-slot* (slot class &key mention-class-p) ; TODO: Adapt HTML sections / lists to describe-slot and describe-class.
Expand Down

0 comments on commit dc309cd

Please sign in to comment.