emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Simple isearch concerns


From: Juri Linkov
Subject: Re: Simple isearch concerns
Date: Tue, 11 May 2021 23:56:14 +0300
User-agent: Gnus/5.13 (Gnus v5.13) Emacs/28.0.50 (x86_64-pc-linux-gnu)

> Testing shows that the `isearch-buffer-local' change works fine,
> with only one deficiency: as (info "(elisp) Searching Keymaps") says
> get-char-property takes precedence over emulation-mode-map-alists.
>
> This means that typing isearch characters when point is e.g.
> on a Gnus attachment line, typing a character like 'o' bound
> to 'gnus-mime-save-part' will exit isearch and run this command.
>
> I see no way to workaround this limitation.

Here is a patch that allows minor mode keys to take precedence over
char-property keys, by adding a special property to mode symbol, e.g.

  (put 'isearch-mode 'overriding-keymap t)

indicated in the decision tree by NEW:

     (or (if overriding-terminal-local-map
             (FIND-IN overriding-terminal-local-map))
         (if overriding-local-map
             (FIND-IN overriding-local-map)
           (or ;; => NEW: modes with overriding-keymap
               (FIND-IN (get-char-property (point) 'keymap))
               (FIND-IN-ANY emulation-mode-map-alists)
               (FIND-IN-ANY minor-mode-overriding-map-alist)
               (FIND-IN-ANY minor-mode-map-alist)
               (if (get-text-property (point) 'local-map)
                   (FIND-IN (get-char-property (point) 'local-map))
                 (FIND-IN (current-local-map)))))
         (FIND-IN (current-global-map)))

diff --git a/src/keymap.c b/src/keymap.c
index fb8eceaec1..c3801cca67 100644
--- a/src/keymap.c
+++ b/src/keymap.c
@@ -1331,7 +1331,7 @@ silly_event_symbol_error (Lisp_Object c)
    list, let the key sequence be read, and hope some other piece of
    code signals the error.  */
 ptrdiff_t
-current_minor_maps (Lisp_Object **modeptr, Lisp_Object **mapptr)
+current_minor_maps (Lisp_Object **modeptr, Lisp_Object **mapptr, int 
overriding)
 {
   ptrdiff_t i = 0;
   Lisp_Object alist, assoc, var, val;
@@ -1358,7 +1358,10 @@ current_minor_maps (Lisp_Object **modeptr, Lisp_Object 
**mapptr)
        if ((assoc = XCAR (alist), CONSP (assoc))
            && (var = XCAR (assoc), SYMBOLP (var))
            && (val = find_symbol_value (var), !EQ (val, Qunbound))
-           && !NILP (val))
+           && !NILP (val)
+           && (overriding == 0
+               || (overriding == 1 && NILP (Fget (var, Qoverriding_keymap)))
+               || (overriding == 2 && !NILP (Fget (var, Qoverriding_keymap)))))
          {
            Lisp_Object temp;
 
@@ -1556,7 +1559,7 @@ DEFUN ("current-active-maps", Fcurrent_active_maps, 
Scurrent_active_maps,
        keymaps = Fcons (local_map, keymaps);
 
       /* Now put all the minor mode keymaps on the list.  */
-      nmaps = current_minor_maps (0, &maps);
+      nmaps = current_minor_maps (0, &maps, 1);
 
       for (int i = --nmaps; i >= 0; i--)
        if (!NILP (maps[i]))
@@ -1565,6 +1568,12 @@ DEFUN ("current-active-maps", Fcurrent_active_maps, 
Scurrent_active_maps,
       if (!NILP (keymap))
        keymaps = Fcons (keymap, keymaps);
 
+      /* Now put all the overriding minor mode keymaps on the list.  */
+      nmaps = current_minor_maps (0, &maps, 2);
+      for (int i = --nmaps; i >= 0; i--)
+       if (!NILP (maps[i]))
+         keymaps = Fcons (maps[i], keymaps);
+
       if (!NILP (olp) && !NILP (otlp))
        keymaps = Fcons (otlp, keymaps);
     }
@@ -1658,7 +1667,7 @@ DEFUN ("minor-mode-key-binding", Fminor_mode_key_binding, 
Sminor_mode_key_bindin
   (Lisp_Object key, Lisp_Object accept_default)
 {
   Lisp_Object *modes, *maps;
-  int nmaps = current_minor_maps (&modes, &maps);
+  int nmaps = current_minor_maps (&modes, &maps, 0);
   Lisp_Object binding = Qnil;
 
   int j;
@@ -1719,7 +1728,7 @@ DEFUN ("current-minor-mode-maps", 
Fcurrent_minor_mode_maps, Scurrent_minor_mode_
   (void)
 {
   Lisp_Object *maps;
-  int nmaps = current_minor_maps (0, &maps);
+  int nmaps = current_minor_maps (0, &maps, 0);
 
   return Flist (nmaps, maps);
 }
@@ -2713,7 +2722,7 @@ DEFUN ("describe-buffer-bindings", 
Fdescribe_buffer_bindings, Sdescribe_buffer_b
         minor modes correctly.  */
       Fset_buffer (buffer);
 
-      int nmaps = current_minor_maps (&modes, &maps);
+      int nmaps = current_minor_maps (&modes, &maps, 0);
       Fset_buffer (outbuf);
 
       start1 = get_local_map (BUF_PT (XBUFFER (buffer)),
@@ -3124,6 +3133,7 @@ syms_of_keymap (void)
   DEFSYM (Qdescribe_map_tree, "describe-map-tree");
 
   DEFSYM (Qkeymap_canonicalize, "keymap-canonicalize");
+  DEFSYM (Qoverriding_keymap, "overriding-keymap");
 
   /* Now we are ready to set up this property, so we can
      create char tables.  */
diff --git a/src/keymap.h b/src/keymap.h
index f417301c8f..b01698d394 100644
--- a/src/keymap.h
+++ b/src/keymap.h
@@ -36,7 +36,7 @@ #define KEYMAPP(m) (!NILP (get_keymap (m, false, false)))
 extern char *push_key_description (EMACS_INT, char *);
 extern Lisp_Object access_keymap (Lisp_Object, Lisp_Object, bool, bool, bool);
 extern Lisp_Object get_keymap (Lisp_Object, bool, bool);
-extern ptrdiff_t current_minor_maps (Lisp_Object **, Lisp_Object **);
+extern ptrdiff_t current_minor_maps (Lisp_Object **, Lisp_Object **, int);
 extern void initial_define_lispy_key (Lisp_Object, const char *, const char *);
 extern void syms_of_keymap (void);
 
diff --git a/src/keyboard.c b/src/keyboard.c
index 47b5e59024..a64d99e4c3 100644
--- a/src/keyboard.c
+++ b/src/keyboard.c
@@ -7395,7 +7395,7 @@ menu_bar_items (Lisp_Object old)
           properties may not work reliable, as they are only
           recognized when the menu-bar (or mode-line) is updated,
           which does not normally happen after every command.  */
-       ptrdiff_t nminor = current_minor_maps (NULL, &tmaps);
+       ptrdiff_t nminor = current_minor_maps (NULL, &tmaps, 0);
        SAFE_NALLOCA (maps, 1, nminor + 4);
        nmaps = 0;
        Lisp_Object tem = KVAR (current_kboard, Voverriding_terminal_local_map);
@@ -7948,7 +7948,7 @@ tab_bar_items (Lisp_Object reuse, int *nitems)
         properties may not work reliably, as they are only
         recognized when the tab-bar (or mode-line) is updated,
         which does not normally happen after every command.  */
-      ptrdiff_t nminor = current_minor_maps (NULL, &tmaps);
+      ptrdiff_t nminor = current_minor_maps (NULL, &tmaps, 0);
       SAFE_NALLOCA (maps, 1, nminor + 4);
       nmaps = 0;
       Lisp_Object tem = KVAR (current_kboard, Voverriding_terminal_local_map);
@@ -8332,7 +8332,7 @@ tool_bar_items (Lisp_Object reuse, int *nitems)
         properties may not work reliably, as they are only
         recognized when the tool-bar (or mode-line) is updated,
         which does not normally happen after every command.  */
-      ptrdiff_t nminor = current_minor_maps (NULL, &tmaps);
+      ptrdiff_t nminor = current_minor_maps (NULL, &tmaps, 0);
       SAFE_NALLOCA (maps, 1, nminor + 4);
       nmaps = 0;
       Lisp_Object tem = KVAR (current_kboard, Voverriding_terminal_local_map);

reply via email to

[Prev in Thread] Current Thread [Next in Thread]