automatically disable a global minor mode for a specific major mode
Global minor modes created with the define-globalized-minor-mode
1 macro are a bit tricky. The reason your code doesn't appear to do anything is that globalized modes utilise after-change-major-mode-hook
to activate the buffer-local minor mode that they control; and that hook runs immediately after the major mode's own hooks4.
Individual modes may implement custom ways of specifying some kind of black list or other method of preventing the mode from being enabled in certain circumstances, so in general it would be worth looking at the relevant M-x customize-group
options for the package to see if such facilities exist. However, a nice clean general way of achieving this for ANY globalized minor mode is eluding me for the moment.
It's a shame that the MODE-enable-in-buffers
function defined by that macro doesn't do the same (with-current-buffer buf (if ,global-mode ...))
check which is performed by the global mode function. If it did, you could simply use slime-repl-mode-hook to make the global mode variable buffer-local and nil.
A quick hack is to check2 what the turn-on
argument is for the globalized minor mode definition (in this instance it's centered-cursor-mode
itself3), and write some around advice to stop that from being evaluated for the modes in question.
(defadvice centered-cursor-mode (around my-centered-cursor-mode-turn-on-maybe)
(unless (memq major-mode
(list 'slime-repl-mode 'shell-mode))
ad-do-it))
(ad-activate 'centered-cursor-mode)
Something we can do (with an easy re-usable pattern) is immediately disable the buffer-local minor mode again after it has been enabled. An after-change-major-mode-hook
function added with the APPEND
argument to add-hook
will reliably run after the globalized minor mode has acted, and so we can do things like:
(add-hook 'term-mode-hook 'my-inhibit-global-linum-mode)
(defun my-inhibit-global-linum-mode ()
"Counter-act `global-linum-mode'."
(add-hook 'after-change-major-mode-hook
(lambda () (linum-mode 0))
:append :local))
1 or its alias define-global-minor-mode
which I feel should be avoided, due to the potential for confusion with "global" minor modes created with define-minor-mode
. "Globalized" minor modes, while still involving a global minor mode, work very differently in practice, so it is better to refer to them as "globalized" rather than "global".
2C-hf define-globalized-minor-mode
RET shows that turn-on
is the third argument, and we check that in the mode definition with M-x find-function
RET global-centered-cursor-mode
RET.
3 with this approach, that fact is going to prevent you from ever enabling this minor mode with slime-repl-mode or shell-mode buffers, whereas a globalized minor mode with a separate turn-on function could still be invoked in its non-global form if you so desired.
4https://stackoverflow.com/a/19295380/324105
I made a new global minor mode, that doesn't get activated in certain modes. The lambda is the function that gets called in every new buffer to activate the minor mode. That is the right place to make exceptions.
(require 'centered-cursor-mode)
(define-global-minor-mode my-global-centered-cursor-mode centered-cursor-mode
(lambda ()
(when (not (memq major-mode
(list 'slime-repl-mode 'shell-mode)))
(centered-cursor-mode))))
(my-global-centered-cursor-mode 1)
It should work for every other global minor mode. Just copy the definition global-xxx-mode and make the right exceptions.