3

In another question (IDO rebind C-j to C-<RET>), Seraph asked about defining the <C-return> key for ido-mode.

It turned out that the key was already bound in cua-global-keymap, which overrode its binding in ido-common-completion-map.

Steps to reproduce:

  1. emacs -Q
  2. M-x cua-mode RET
  3. M-x ido-mode RET
  4. (define-key ido-common-completion-map (kbd "<C-return>")
      (lambda () 
        (interactive)
        (message "C-j called")))
    
  5. C-x C-e
  6. M-x ido-dired RET
  7. C-h k C-return

Which turns out to be bound to cua-set-rectangle-mark in cua-global-keymap, as opposed to the anonymous command above in ido-completion-map.

As a workaround, I recommended removing the definition in cua-global-map.

Question: is there a way to make the definition in ido-common-completion-map override the definition in cua-global-map?

Basil
  • 12,019
  • 43
  • 69
Realraptor
  • 1,253
  • 6
  • 17
  • 1
    See (elisp) [Active Keymaps](https://www.gnu.org/software/emacs/manual/html_node/elisp/Active-Keymaps.html). – Drew Dec 03 '17 at 18:45

1 Answers1

5

It turned out that the key was already bound in cua-global-keymap, which overrode its binding in ido-common-completion-map.

Indeed, this is because cua-mode uses emulation-mode-map-alists, which has one of the highest priorities in key lookup, to store and select from many of its key bindings. See (elisp) Active Keymaps, (elisp) Searching Keymaps and (elisp) Controlling Active Maps for more information on this.

is there a way to make the definition in ido-common-completion-map override the definition in cua-global-map?

There are, of course, several ways to achieve this, but I'm not sure which one would prove the simplest or most desirable, elegant or robust. Here are a couple of suggestions:

  1. Simply unbind the key from cua-global-keymap if it is unwanted:

    (with-eval-after-load 'cua-base
      (define-key cua-global-keymap [C-return] nil))
    
  2. Try to override the cua-mode overrides in emulation-mode-map-alists:

    (defun my-shave-yak ()
      "No-one was using those CPU cycles anyway."
      (interactive)
      (message ">>> Hello, World!"))
    
    (defvar my-ido-map
      (let ((map (make-sparse-keymap)))
        (define-key map [C-return] #'my-shave-yak)
        map)
      "Keymap for personal `ido' bindings.")
    
    ;; Bind keys as we want them ideally,
    ;; assuming no pesky external overrides are in place
    (with-eval-after-load 'ido
      ;; Perhaps composing keymaps or similar
      ;; would avoid duplicating `my-ido-map'
      (define-key ido-common-completion-map [C-return] #'my-shave-yak))
    
    ;; Activate `my-ido-map' with `cua-mode' and place
    ;; it at a lower index than `cua--keymap-alist'
    (add-to-ordered-list 'emulation-mode-map-alists
                         `((cua-mode . ,my-ido-map))
                         0)
    
Basil
  • 12,019
  • 43
  • 69