emacs-devel
[Top][All Lists]
Advanced

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

Re: Control help- and Info-mode buffers from other buffers


From: Arthur Miller
Subject: Re: Control help- and Info-mode buffers from other buffers
Date: Sun, 04 Jun 2023 16:04:39 +0200
User-agent: Gnus/5.13 (Gnus v5.13)

Juri Linkov <juri@linkov.net> writes:

>> The interactive form has to be the very first form in a function body, which
>> makes it impossible to just wrap the entire function  into
>> with-selected-window. In this case I save selected-window in global var
>> (Info-jump) and select that window back at the very end of the function. It 
>> is
>> the same effect as if being wrapped into with-selected-window, but 
>> unfortunately
>> it uses a global variable. I don't know how to do it otherwise, if there is a
>> better way, pleae let me know, I would like to learn how to do it in a better
>> way if there is one.
>
> Another way is to add a new argument WINDOW to all commands.
> Then the interactive form could send the window value to the body.

Sorry I wasn't answered to your last few mails; I am just busy and would to get
this done and over. Yeah I would myself pretty much like to have that pedal to
modify all commands like a piano player; but I am really bad with it, I forgett 
the
pedal all the time when I play. But I would gladly start a business and sell
Emacs pedals if you are interested!

If you think of the bit of code I sent in as test-command; I would like to get
that *effect*, not necessary to really paste in all that code in each and every
command. Could it be possibly to create a function, that is called by each
commands and that arranges to execute the command in correct context
(other-window or user selected window)? I mean like you suggested, some sort of
parameter, keyword etc? If you think of your idea, which seemed more flexible to
me, but to achieve that effect, and if that would in some easy to user macro a
lá define-minor-mode or use-package style.

> But when an interactive selection of a window by the user is not involved,
> then you can just call the same function like 'other-window-for-scrolling'
> twice: in the interactive form and in the body it should return the same.
>
>> I have both in my WM and in Emacs that focus should follow mouse. Now what
>> happens is that, despite the function jumpiing to correct Emacs window on
>> another frame, due to cursor being in old frame, all input goes to the old
>> frame, so at least this particular function does not work with multiple
>> frames. According to the docs for select-window, both frame to which the 
>> window
>> belongs, and the buffer displaying are made selected/current, so it is 
>> probably
>> my WM spooking. I will try to test with some other WM and to boot into 
>> Windows
>> and test there, but on systems where focus follows the mouse, I guess there 
>> is
>> nothing to do? I suppose the same issue will happen with few other functions
>> that prompt user for the input via minibuffer. It works well when Info 
>> window is
>> on the same frame of course.
>
> 'other-frame' explicitly calls 'select-frame-set-input-focus' at the end.
I have just found a solution that will display menu in users selected frame, so
all good :-).

#+begin_src emacs-lisp
(interactive
   (let (;; If point is within a menu item, use that item as the default
         (default nil)
         (p (point))
         beg
         (case-fold-search t)
         (mouse-autoselect-window nil)
         (info-window (get-buffer-window "*info*" t)))
     (unless (window-live-p info-window)
       (user-error "There is no visible Info buffer."))
     (with-current-buffer (window-buffer info-window)
       (save-excursion
         (goto-char (point-min))
         (if (not (search-forward "\n* menu:" nil t))
             (user-error "No menu in this node"))
         (setq beg (point))
         (and (< (point) p)
              (save-excursion
                (goto-char p)
                (end-of-line)
                (if (re-search-backward (concat "\n\\* +\\("
                                                Info-menu-entry-name-re
                                                "\\):")
                                        beg t)
                    (setq default (match-string-no-properties 1))))))
       (let ((item nil))
         (while (null item)
           (setq item (let ((completion-ignore-case t)
                            (Info-complete-menu-buffer (current-buffer)))
                        (completing-read (format-prompt "Menu item" default)
                                         #'Info-complete-menu-item nil t nil nil
                                         default))))
         (list item current-prefix-arg))))
   Info-mode)
#+end_src

As I got the idea yesterday while writing about it; It is possible to just work
in info-buffer, there is no need to also switch to window. The above interacitve
form is from Info-menu; and now I get the prompt displayed in the selected frame
not one with the *info* buffer and I can remove the ugly global var I used for
"the communication" too :).

>> I do have another question too: what is a good strategy if there are 
>> multiple info
>> windows open? Prompt user to select with a completing read, or just leave 
>> as-is,
>> i.e. return the first info window?
>
> I think a good default would be to use the most recently used window.

Isn't that what would Emacs does per automatic, I mean what get-buffer or
get-buffer-window chooses?



reply via email to

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