emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Feature request : Tab-completion for 'shell-comand'


From: TSUCHIYA Masatoshi
Subject: Re: Feature request : Tab-completion for 'shell-comand'
Date: Sun, 09 Mar 2008 23:01:56 +0900
User-agent: Gnus/5.110007 (No Gnus v0.7) Emacs/22.1 (gnu/linux)

Dear Emacs core developers,

>> On Thu, 06 Mar 2008 12:04:36 +0200
>> address@hidden (Juri Linkov) said as follows:

>> This code is insufficient, because the output of `message' function
>> which is called from tab-completion functions will bury the current
>> completing status in minibuffer.

>Yes, these messages overwrite the minibuffer, but instead of temporarily
>redefining the function `message' as in shell-command.el, it would be
>better to fix comint.el and shell.el to not display completion messages
>when the minibuffer is active.  These files already contain places where
>this check is done this way:

> (unless (window-minibuffer-p (selected-window))
>   (message "Completing file name..."))

I think that such change will not work well based on two reasons.
The first reason is that we will have to install the above change into
all completion functions including functions added by users if you hope
that this change works consistently.  Such great change must be very
very difficult.  The second reason is that several completion functions
will require a minibuffer to display their completing status.

My solution employed in shell-command.el resolves these two problems.
The first problem is resolved by re-defining `message' function.
Re-definition of `message' function enables all tab-completion functions
to call `message' function without ill effects.  And more, the second
problem is also resolved by this re-defined `message' function which
uses a single minibuffer as two separated areas.  The re-defined
`message' function uses the left half of minibuffer to display a regular
prompt and uses the right half to display a completing status.

This trick is realized by the following code.  You can see that the
re-defined `message' function concatenates a regular prompt and a
completing status, and displays both of them.

(defun shell-command-read-minibuffer
  (format-string current-directory &optional initial-contents
                 user-keymap read hist)
  "Read a command string in the minibuffer, with completion."
  (let ((keymap (make-sparse-keymap))
        (prompt (shell-command-make-prompt-string
                 format-string current-directory)))
    (set-keymap-parent keymap (or user-keymap minibuffer-local-map))
    (define-key keymap "\t"
      (lambda ()
        (interactive)
        (let ((orig-function (symbol-function 'message)))
          (unwind-protect
              (progn
                (defun message (string &rest arguments)
                  (let* ((s1 (concat prompt
                                     (buffer-substring
                                      (shell-command/minibuffer-prompt-end)
                                      (point-max))))
                         (s2 (apply (function format) string arguments))
                         (w (- (window-width)
                               (string-width s1)
                               (string-width s2)
                               1)))
                    (funcall orig-function
                             (if (>= w 0)
                                 (concat s1 (make-string w ?\ ) s2)
                               s2))
                    (if (sit-for 0.3) (funcall orig-function s1))
                    s2))
                (require 'shell)
                (require 'comint)
                (run-hook-with-args-until-success
                 'shell-command-complete-functions))
            (fset 'message orig-function)))))
    (read-from-minibuffer prompt initial-contents keymap read hist)))

I hope that you will try http://namazu.org/~tsuchiya/elisp/shell-command.el
before further discussion.

>> And more, the customize hook like `shell-command-complete-functions'
>> will be necessary, in order to enable users to customize tab-completion
>> functions.

>I agree that this user option `shell-command-complete-functions' is
>necessary for users to customize, and I think its default value should
>be the same as the default value of `shell-dynamic-complete-functions'.

>Also I see that shell-command.el changes the shell-command prompt.
>I think this is a separate feature that is better to implement as
>a minor mode that uses `minibuffer-setup-hook' to add shell-command
>specific information to the created prompt.  Please see a mode like
>minibuffer-electric-default-mode or file-name-shadow-mode for the ideas
>how this could be implemented.

I think that it is not a good idea to separate the tab-completion
feature and the feature to display a current directory in a prompt.
Users must know where they call commands with tab-completion, because
almost all actions of tab-completion functions depend on the current
directory.

I already signed a disclaimer for Gnus.  So, the simplest way is to
merge necessary code of shell-command.el into simple.el and grep.el
after I will sign a disclaimer for Emacs itself, isn't it?

Regards,

-- 
TSUCHIYA Masatoshi




reply via email to

[Prev in Thread] Current Thread [Next in Thread]