help-gnu-emacs
[Top][All Lists]
Advanced

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

Re: Understanding after-make-frame-functions


From: Kaushal Modi
Subject: Re: Understanding after-make-frame-functions
Date: Tue, 17 May 2016 16:15:39 +0000

On Mon, May 16, 2016 at 11:44 PM Eli Zaretskii <eliz@gnu.org> wrote:

> There's nothing specific to daemon here, it is all just side effect of
> how and when frames are created by Emacs.  In particular, the daemon
> creates frames when emacsclient connects to it, and doesn't have any
> displayable frames before that.
>
> In general, _any_ call to make-frame will always run
> after-make-frame-functions, you can clearly see that in the code.
>

Thanks. But I think that this side effect should be documented. I used the
below test snippet in 3 different invocations of emacs:

(1) emacs &
(2) emacsclient -c -a '' &
(3) emacs -nw

=====
(defvar my-index 1
  "Index that increments after each hook is called.")
(dolist (hook '(before-init-hook
                after-init-hook
                emacs-startup-hook
                window-setup-hook
                before-make-frame-hook
                after-make-frame-functions
                after-setting-font-hook))
  (add-hook hook
            `(lambda (&optional frame)
               (when frame
                 (select-frame frame))
               (message "[%d] Running `%s' .."
                        my-index (symbol-name (quote ,hook)))
               (message "[%d]  Symbola: %S"
                        my-index (find-font (font-spec :name "Symbola")))
               (setq my-index (1+ my-index))) :append))
=====

In the "emacs &" invocation, I got:

[1] Running ‘after-init-hook’ ..
[1]  Symbola: #<font-entity xft unknown Symbola nil iso10646-1 normal
normal semi-condensed 0 nil nil 0 ((:font-entity
"/home/kmodi/.fonts/Symbola.ttf" . 0) (:name . "Symbola"))>
For information about GNU Emacs and the GNU system, type C-h C-a.
[2] Running ‘emacs-startup-hook’ ..
[2]  Symbola: #<font-entity xft unknown Symbola nil iso10646-1 normal
normal semi-condensed 0 nil nil 0 ((:font-entity
"/home/kmodi/.fonts/Symbola.ttf" . 0) (:name . "Symbola"))>
[3] Running ‘window-setup-hook’ ..
[3]  Symbola: #<font-entity xft unknown Symbola nil iso10646-1 normal
normal semi-condensed 0 nil nil 0 ((:font-entity
"/home/kmodi/.fonts/Symbola.ttf" . 0) (:name . "Symbola"))>

In the "emacsclient -c -a '' &" invocation, I got:

[1] Running ‘after-init-hook’ ..
[1]  Symbola: nil
Starting Emacs daemon.
Restarting server
[2] Running ‘emacs-startup-hook’ ..
[2]  Symbola: nil
[3] Running ‘window-setup-hook’ ..
[3]  Symbola: nil
[4] Running ‘before-make-frame-hook’ ..
[4]  Symbola: nil
[5] Running ‘after-make-frame-functions’ ..
[5]  Symbola: #<font-entity xft unknown Symbola nil iso10646-1 normal
normal semi-condensed 0 nil nil 0 ((:font-entity
"/home/kmodi/.fonts/Symbola.ttf" . 0) (:name . "Symbola"))>
When done with this frame, type C-x 5 0

In the "emacs -nw" invocation, I got:

[1] Running ‘after-init-hook’ ..
[1]  Symbola: nil
For information about GNU Emacs and the GNU system, type C-h C-a.
[2] Running ‘emacs-startup-hook’ ..
[2]  Symbola: nil
[3] Running ‘window-setup-hook’ ..
[3]  Symbola: nil

So in conclusion, it looks like however the user customizes the
before-make-frame-hook and after-make-frame-functions, those would be
ineffective when running non-daemon emacs and emacs -nw. It is obvious that
frames are not being created for emacs -nw and so those hooks are not
called. But it is not evident that the init.el/.emacs is called after frame
generation when running emacs& and so those frame hook customizations serve
no purpose in that case.


> > (2) Is window-setup-hook supposed to run only in non-daemon emacs?
>
> No, of course not.  It is supposed to be used by any customizations
> that need to hook into stuff that Emacs does early on during its
> startup (see startup.el), which you cannot do later.
>

Thanks. I now understand that. Just that I cannot use window-setup-hook for
my font check when running emacsclient because the frame/fonts haven't been
loaded yet (as we also see in the above experiment:

[3] Running ‘window-setup-hook’ ..
[3]  Symbola: nil
...
[5] Running ‘after-make-frame-functions’ ..
[5]  Symbola: #<font-entity xft unknown Symbola ...


> > (3) What would be a more concise manner to do stuff like linum
> activation,
> > find-font call, etc. correctly in both emacs and emacsclient?
>
> I don't understand the question.  Emacs daemon can be started with a
> non-empty ~/.emacs, so why is this an issue?  IOW, what's wrong with
> the answer "as you usually do with customizations"?
>

With the help of the above experiment, I think I now better understand
which hooks to use and if I need to use those:

I now have the below in my init:

=====
(defun modi/symbola-font-check (&optional frame)
  (require 'setup-symbola))
(if (daemonp)
    (progn
      ;; The below `select-frame' call is mandatory for the `find-font'
      ;; to work correctly when using emacs daemon or emacsclient (learned
      ;; through experimentation).
      (add-hook 'after-make-frame-functions #'select-frame :append)
      ;; Need to delay font check till the fonts are actually available,
which
      ;; does not happen until the point when `after-make-frame-functions'
hook
      ;; is run (only for emacsclient launches).
      (add-hook 'after-make-frame-functions #'modi/symbola-font-check))
  ;; For non-daemon, regular emacs launches, the frame/fonts are loaded
*before*
  ;; the emacs config is read. So in that case there is no need to add the
font
  ;; check function to any specific hook.
  (modi/symbola-font-check))
=====

There's something else too which is undocumented and I learned through
experimentation; that I need to add select-frame to
after-make-frame-functions first for the find-font to work as intended
(else it always returns nil). Would adding that to that hook be a good
default?

At the end of this, let me know if you too think that the
after-make-frame-functions needs more clarification in the documentation,
and I will file a bug report for that.

Thanks for going through my email in detail.

Kaushal
-- 

-- 
Kaushal Modi


reply via email to

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