2

I'm working on an Emacs minor mode, and I'd like it to apply only when the major mode is a certain mode (i.e. js-mode). In other words, when I activate my-super-mode, I'd like the keymap it defines to be available in all JS buffers (like it was global) but without affecting non-js buffers.

I know it's possible via hooks but I'd like to avoid this solution. Ideally my minor mode would be activated only when needed via M-x (and when activated it should be in effect in all JS buffers). Possible?

mishoo
  • 2,415
  • 1
  • 18
  • 12
  • 1
    Sounds like you should be defining your own `js` mode instead. Check out `define-derived-mode`. – tripleee Feb 16 '13 at 10:52
  • What's the problem with doing that via a global mode? You `define-globalized-minor-mode`, and then check if each specific buffer is in `js-mode` in the `turn-on` function. – Dmitry Feb 17 '13 at 02:23

1 Answers1

1

One solution that comes to mind is to define a buffer-local minor mode that implements the actual functionality, but is not invoked directly by the user and its name prefixed by an internal prefix to prevent accidental triggering:

(define-minor-mode my--mode
  "Mode implementing blah, invoke it with M-x my-super-mode."
  nil " Super" nil
  ;; mode definition goes here, including keymaps, etc.
  )

The public mode invoked by the user is global. When switched on or off, it automatically switches the internal mode in all existing and future JS buffers:

(defun my--mode-set-maybe ()
  (my--mode (if my-super-mode 1 0)))

(define-minor-mode my-super-mode
  "Super mode, only in effect in JS buffers."
  nil "" nil
  :global t
  (dolist (buf (buffer-list))
    (with-current-buffer buf
      (my--mode-set-maybe))))

(add-hook 'js-mode-hook 'my--mode-set-maybe)
user4815162342
  • 141,790
  • 18
  • 296
  • 355
  • Because I had to look it up, the `nil " Super" nil` is equivalent to `:init-value nil :lighter " Super" :keymap nil` – mtalexan Jul 09 '15 at 22:10