The Stack Overflow podcast is back! Listen to an interview with our new CEO.

Hot answers tagged

57

The new advice system has the following advantages: add-function: This is brand new functionality that simply was not part of defadvice. It is a kind of hybrid between add-hook and defadvice. In the future, expect more foo-function variables (modified via add-function) and less foo-functions (modified via add-hook). This functionality was the main ...


22

All information you need is included in C-h f add-function which describes the underlying mechanism of advice-add. The new advice system basically acts like replacing the current definition of a function by the function described in the table in C-h f add-function, depending on your choice of the WHERE argument, only cleaner for the sake of tracking what ...


16

Alternatively, use a local hook: (add-hook 'c++-mode-hook (lambda () (add-hook 'before-save-hook MY-HOOK-FUNC nil 'local))) This adds MY-HOOK-FUNC to the buffer-local before-save-hook of each C++ Mode buffer, or any buffer in a mode derived of C++ Mode. I find this more elegant that explicitly checking major-mode, and it has the advantage that ...


15

Couldn't you use (cl-)letf while referencing the original function yourself? Something like this: ;; Original function (defun my-fun (arg) (message "my-fun (%s)" arg)) ;; Standard call (my-fun "arg") ;; => my-fun (arg) ;; Temporary overriding (more or less like an around advice) (let ((orig-fun (symbol-function 'my-fun))) (letf (((symbol-function '...


14

You can use directory-local variables to make Emacs' source files read-only by default. (See also C-hig (emacs) Directory Variables RET). Create a file called .dir-locals.el at the root of the directory tree you wish to protect, with the following contents: ((nil . ((eval . (view-mode 1))))) Edit: Michał Politowski points out in the comments that enabling ...


12

One fairly common way of restricting the action of a hook to a particular major mode is to check the value of major-mode. For example, this hook prints a message before saving buffers using c++-mode: (defun my-c++-mode-before-save-hook () (when (eq major-mode 'c++-mode) (message "It's never too early to start saving (C++ code)!"))) (add-hook 'before-...


11

Of course it is possible inclusive the interactive specification. We are dealing here with elisp! (Lisp is the language where the most important constructs are lists. Callable forms are just lists. So you can construct them after your liking.) Application: You want to add some functionality to some functions automagically. The extended functions should be ...


11

I had to solve a very similar problem in nadvice.el, so here is a solution (which uses some of the code from nadvice.el): (defun wrapper (&rest args) (interactive (advice-eval-interactive-spec (cadr (interactive-form #'wrappee)))) (apply #'wrappee args)) Compared to the other solutions posted so far, this one has the advantage of ...


11

There's advice-mapc, which let's one iterate over all advices of some function, applying a given function to each. With it, it's easy to remove all advices: (advice-mapc (lambda (adv prop) (advice-remove 'executable-find adv)) 'executable-find) This could be extended to remove only advices which don't have a name property by looking in the second (...


9

One of the clear benefits of advice being normal functions is that you can visit a definition with find-function. At present, when viewing the help for a (new-style) advised function, it provides a link to the help for the advice function, and from there a link to the source (as usual for function help). The old system provided the advice docstring inline, ...


8

From the file header: ;;; Commentary: ;; This package lets you add behavior (which we call "piece of advice") to ;; existing functions, like the old `advice.el' package, but with much fewer ;; bells and whistles. As I read it, the primary goal is to be simpler than the old advice system, not to have more capabilities. Reading the docs, it seems that ...


7

The defadvice macro is almost obsolete, having been replaced by an improved system that uses advice-add, advice-remove, etc, which allows you to turn advice on and off, among other things. See the manual for details. If you are stuck on an older version of Emacs without the improved system, you can deactivate advice on a function with (ad-deactivate ...


7

Customize the variable help-window-select: "Non-nil means select help window for viewing. Choices are: never (nil) Select help window only if there is no other window on its frame. other Select help window unless the selected window is the only other window on the help window's frame. always (t) Always select the help ...


7

For variety, here's a solution using the :around advice. Copy the below test snippet to the *scratch* buffer and evaluate the progn form. (progn (defvar last-enabled-foo nil) (setq last-enabled-foo nil) (defun enable-foo (foo) (message "last-enabled-foo = %S" last-enabled-foo)) (defun adv/enable-foo (orig-fun &rest args) (setq last-...


6

You can use ad-get-orig-definition to get the original definition and then use help-function-arglist as usual to get the argument list, for example (help-function-arglist (ad-get-orig-definition 'ido-read-internal))


6

The tags-revert-without-query variable is the generic mechanism for skipping this prompt. Check whether setting that directly circumvents the problem. If so, you could let-bind it in a wrapper around the function you're calling to get that behaviour for this scenario only.


6

Store the original function (obtained with symbol-function) in a local variable, and use funcall to call the function object stored in that variable. Cumbersome, but it mostly works. (defadvice TeX-master-file (around TeX-master-file-indirect-buffer activate compile) "Support indirect buffers." (let ((original-buffer-file-name (symbol-function 'buffer-...


6

You can also call advice-remove with the same lambda expression, i.e., replace advice-add with advice-remove and delete :around, then C-x C-e.


6

As lawlist correctly points out in a comment, the Emacs Help system, invoked via C-hfNAMERET (M-xdescribe-functionRETNAMERET) in this case, is a quick way to interactively check whether there is any advice currently active on the function named NAME. This is doubly convenient because the name of the advising function is hyperlinked as a button, allowing you ...


5

This seems unfortunate in that, in order to produce a similar effect, it's necessary to copy-paste code: [...] I can copy ansi-term's interactive form On the contrary, I think it would be a good idea to copy-paste the interactive form of the advised function, even though you don't actually have to do so here. I read you question from top to bottom. When I ...


5

(defun advice-unadvice (sym) "Remove all advices from symbol SYM." (interactive "aFunction symbol: ") (advice-mapc (lambda (advice _props) (advice-remove sym advice)) sym))


5

You don't need a macro for this. And you don't need (but you can certainly use) lexical binding. ;; Without lexical binding: ;; (defun advise-once (symbol where function &optional props) (advice-add symbol :after `(lambda (&rest _) (advice-remove ',symbol ',function))) (advice-add symbol where function props)) ;; With lexical binding: ;; (...


5

Of course you can. You can do it with: (advice-add 'read-from-minibuffer :around #'return-my-name) (defun return-my-name (orig-fun &rest args) (let ((orig-val (apply orig-fun args))) <return-the-new-value>)) Or you can do it with (advice-add 'read-from-minibuffer :filter-return #'return-my-name) (defun return-my-name (orig-val) <...


5

Disabling Evil is the wrong approach to this problem, customize the initial state for term instead: (evil-set-initial-state 'term-mode 'emacs)


4

I agree with PythonNut that the best solution is probably not to use advice at all, but to define a new command my-find-file instead. This said, if you find that advising find-file is a better option (e.g. because you also want to affect pre-exisitng calls to find-file), you might like to do it as follows: (define-minor-mode my-find-file-mode "Tweak `...


4

If you have an Emacs version prior to release 24.4 then you have the doc for `defadvice' available from within Emacs. In that case, Ask Emacs! C-h i to open Info, the doc browser, in Emacs. Then choose the Elisp manual. Then i advice TAB to look up advice in the index. The TAB shows you the index entries that start with advice, one of which is advice, ...


4

Read the source code of volatile-highlights and you'll find you don't need advice at all, supporting any command is built into volatile-highlights. All you need is two lines of code: (vhl/define-extension 'my-evil-highlights 'evil-yank 'evil-move 'some-other-functions ...) (vhl/install-extension 'my-evil-highlights) Read the docs for the two functions ...


4

I agree that using advice is probably the way to go, but if you really, truly have to, you can use something like this. (Comments are welcome.) (defun third-party-func () (message "original")) (defalias 'third-party-func-original (symbol-function 'third-party-func)) (defun third-party-func () (message "new!") (third-party-func-original)) ;...


4

This seems to work. Apparently, defadvice is old-fashioned, and we're supposed to use advice-add instead. (defun jk-advice () (message "Kilroy was here")) (advice-add 'python-mode :before #'jk-advice)


4

The easiest way to find out the arguments passed to a function is to use M-x trace-function RET name-of-your-function RET. Once you're done, use M-x untrace-function or M-x untrace-all. Note that this should work for most functions you're interested in, but there are a few corner cases. See the commentary at the top of trace.el.


Only top voted, non community-wiki answers of a minimum length are eligible