eval-after-load проти режиму гачка


75

Чи існує різниця між встановленням речей для режиму з використанням eval-after-loadта використанням гачка режиму?

Я бачив якийсь код, де define-keyвикористовується всередині основного режиму, і якийсь інший код, define-keyякий використовується у eval-after-loadформі.


Оновлення:

Для кращого розуміння, ось приклад використання гачків після завантаження та режиму з орг-режимом. Код може працювати до (load "org") або (require 'org)або (package-initialize).

;; The following two lines of code set some org-mode options.
;; Usually, these can be outside (eval-after-load ...) and work.
;; In cases that doesn't work, try using setq-default or set-variable
;; and putting them in (eval-after-load ...), if the
;; doc for the variables don't say what to do.
;; Or use Customize interface.
(setq org-hide-leading-stars t)
(setq org-return-follows-link t)

;; "org" because C-h f org-mode RET says that org-mode is defined in org.el
(eval-after-load "org"
  '(progn
     ;; Establishing your own keybindings for org-mode.
     ;; Variable org-mode-map is available only after org.el or org.elc is loaded.
     (define-key org-mode-map (kbd "<C-M-return>") 'org-insert-heading-respect-content)
     (define-key org-mode-map (kbd "<M-right>") nil) ; erasing a keybinding.
     (define-key org-mode-map (kbd "<M-left>") nil) ; erasing a keybinding.

     (defun my-org-mode-hook ()
       ;; The following two lines of code is run from the mode hook.
       ;; These are for buffer-specific things.
       ;; In this setup, you want to enable flyspell-mode
       ;; and run org-reveal for every org buffer.
       (flyspell-mode 1)
       (org-reveal))
     (add-hook 'org-mode-hook 'my-org-mode-hook)))

6
+1 за «орг» , тому що Ch е орг-режимі RET каже , що орг-режим визначається в org.el . Я боровся з тим, eval-after-loadщоб насправді оцінити nxml-mode, і ця підказка спрацювала!
Зак Янг

Відповіді:


107

Загорнутий код eval-after-loadбуде виконаний лише один раз, тому він зазвичай використовується для одноразового налаштування, такого як встановлення загальних значень і поведінки за замовчуванням. Прикладом може бути налаштування розкладки клавіш за замовчуванням для певного режиму. У eval-after-loadкоді немає поняття "поточний буфер".

Гачки режиму виконуються один раз для кожного буфера, в якому режим увімкнений, тому вони використовуються для конфігурації для кожного буфера. Тому переключення режимів запускаються пізніше, ніж eval-after-loadкод; це дозволяє їм здійснювати дії на основі такої інформації, як, чи ввімкнено інші режими в поточному буфері.


1
На замітку (виправте мене, якщо я помиляюся): emacs-lisp-mode та lisp-mode, здається, завантажуються до того, як користувацькі сценарії eval-after-load будуть виконані. Тож у такому випадку, можливо, справді доведеться використовувати замість нього гачок режиму.
balu

1
Так: eval-after-loadблок завжди eval«d після відповідної бібліотеки loadред. Але зауважте, що код завжди буде виконуватися до того, як будуть викликані будь-які функції у відповідній бібліотеці. Отже, якщо ви (eval-after-load 'lisp-mode ...), тоді ...код у цьому блоці буде запущений до виклику lisp-modeфункції in lisp-mode.el.
sanityinc

1
Що after-loadсаме робить ? Чи є різниця eval-after-load?
balu

6
Це просто локальна обгортка макросів для eval-after-load, щоб уникнути необхідності цитувати форму, передану eval-after-load. тобто замість (eval-after-load 'foo '(progn (foo) (bar)))я можу писати (after-load 'foo (foo) (bar)).
sanityinc

2
@balu: emacs-lisp-modeі lisp-modeскидаються з emacs і ніколи не завантажуються.
sds
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.