]> code.delx.au - gnu-emacs/blobdiff - src/keymap.c
* macfns.c (mac_window): Replace WindowPtr with WindowRef.
[gnu-emacs] / src / keymap.c
index 11e3e348da5b1b2834102c0eac1e32567dbd2a3a..f57fe34e7f60eeb566ddd80533b511b840a4e158 100644 (file)
@@ -1,13 +1,13 @@
 /* Manipulation of keymaps
    Copyright (C) 1985, 1986, 1987, 1988, 1993, 1994, 1995,
                  1998, 1999, 2000, 2001, 2002, 2003, 2004,
-                 2005, 2006 Free Software Foundation, Inc.
+                 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
 
 This file is part of GNU Emacs.
 
 GNU Emacs is free software; you can redistribute it and/or modify
 it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
+the Free Software Foundation; either version 3, or (at your option)
 any later version.
 
 GNU Emacs is distributed in the hope that it will be useful,
@@ -1124,7 +1124,9 @@ DEF is anything that can be a key's definition:
     or another symbol whose function definition is used, etc.),
  a cons (STRING . DEFN), meaning that DEFN is the definition
     (DEFN should be a valid definition in its own right),
- or a cons (MAP . CHAR), meaning use definition of CHAR in keymap MAP.
+ or a cons (MAP . CHAR), meaning use definition of CHAR in keymap MAP,
+ or an extended menu item definition.
+ (See info node `(elisp)Extended Menu Items'.)
 
 If KEYMAP is a sparse keymap with a binding for KEY, the existing
 binding is altered.  If there is no binding for KEY, the new pair
@@ -1223,23 +1225,42 @@ binding KEY to DEF is added at the front of KEYMAP.  */)
 
 /* This function may GC (it calls Fkey_binding).  */
 
-DEFUN ("command-remapping", Fcommand_remapping, Scommand_remapping, 1, 2, 0,
-       doc: /* Return the remapping for command COMMAND in current keymaps.
+DEFUN ("command-remapping", Fcommand_remapping, Scommand_remapping, 1, 3, 0,
+       doc: /* Return the remapping for command COMMAND.
 Returns nil if COMMAND is not remapped (or not a symbol).
 
 If the optional argument POSITION is non-nil, it specifies a mouse
 position as returned by `event-start' and `event-end', and the
 remapping occurs in the keymaps associated with it.  It can also be a
 number or marker, in which case the keymap properties at the specified
-buffer position instead of point are used. */)
-     (command, position)
-     Lisp_Object command, position;
+buffer position instead of point are used.  The KEYMAPS argument is
+ignored if POSITION is non-nil.
+
+If the optional argument KEYMAPS is non-nil, it should be a list of
+keymaps to search for command remapping.  Otherwise, search for the
+remapping in all currently active keymaps.  */)
+     (command, position, keymaps)
+     Lisp_Object command, position, keymaps;
 {
   if (!SYMBOLP (command))
     return Qnil;
 
   ASET (command_remapping_vector, 1, command);
-  return Fkey_binding (command_remapping_vector, Qnil, Qt, position);
+
+  if (NILP (keymaps))
+    return Fkey_binding (command_remapping_vector, Qnil, Qt, position);
+  else
+    {
+      Lisp_Object maps, binding;
+
+      for (maps = keymaps; !NILP (maps); maps = Fcdr (maps))
+       {
+         binding = Flookup_key (Fcar (maps), command_remapping_vector, Qnil);
+         if (!NILP (binding) && !INTEGERP (binding))
+           return binding;
+       }
+      return Qnil;
+    }
 }
 
 /* Value is number if KEY is too long; nil if valid but has no definition. */
@@ -1247,7 +1268,8 @@ buffer position instead of point are used. */)
 
 DEFUN ("lookup-key", Flookup_key, Slookup_key, 2, 3, 0,
        doc: /* In keymap KEYMAP, look up key sequence KEY.  Return the definition.
-nil means undefined.  See doc of `define-key' for kinds of definitions.
+A value of nil means undefined.  See doc of `define-key'
+for kinds of definitions.
 
 A number as value means KEY is "too long";
 that is, characters or symbols in it except for the last one
@@ -1399,8 +1421,10 @@ silly_event_symbol_error (c)
 static Lisp_Object *cmm_modes = NULL, *cmm_maps = NULL;
 static int cmm_size = 0;
 
-/* Store a pointer to an array of the keymaps of the currently active
-   minor modes in *buf, and return the number of maps it contains.
+/* Store a pointer to an array of the currently active minor modes in
+   *modeptr, a pointer to an array of the keymaps of the currently
+   active minor modes in *mapptr, and return the number of maps
+   *mapptr contains.
 
    This function always returns a pointer to the same buffer, and may
    free or reallocate it, so if you want to keep it for a long time or
@@ -1610,10 +1634,10 @@ specified buffer position instead of point are used.
 
       /* We are not interested in locations without event data */
 
-      if (EVENT_HAS_PARAMETERS (event))
+      if (EVENT_HAS_PARAMETERS (event) && CONSP (XCDR (event)))
        {
          Lisp_Object kind = EVENT_HEAD_KIND (EVENT_HEAD (event));
-         if (CONSP (XCDR (event)) && EQ (kind, Qmouse_click))
+         if (EQ (kind, Qmouse_click))
            position = EVENT_START (event);
        }
     }
@@ -1622,13 +1646,13 @@ specified buffer position instead of point are used.
      are read using the keymaps of the buffer clicked on, not
      the current buffer.  So we may have to switch the buffer
      here. */
-  
+
   if (CONSP (position))
     {
       Lisp_Object window;
-      
+
       window = POSN_WINDOW (position);
-         
+
       if (WINDOWP (window)
          && BUFFERP (XWINDOW (window)->buffer)
          && XBUFFER (XWINDOW (window)->buffer) != current_buffer)
@@ -1640,13 +1664,13 @@ specified buffer position instead of point are used.
             would not be a problem here, but it is easier to keep
             things the same.
          */
-             
+
          record_unwind_protect (Fset_buffer, Fcurrent_buffer ());
-         
+
          set_buffer_internal (XBUFFER (XWINDOW (window)->buffer));
        }
     }
-  
+
   if (! NILP (current_kboard->Voverriding_terminal_local_map))
     {
       value = Flookup_key (current_kboard->Voverriding_terminal_local_map,
@@ -1669,8 +1693,8 @@ specified buffer position instead of point are used.
        : MARKERP (position) ? marker_position (position)
        : PT;
 
-      local_map = get_local_map (pt, current_buffer, Qlocal_map); 
-      keymap = get_local_map (pt, current_buffer, Qkeymap); 
+      local_map = get_local_map (pt, current_buffer, Qlocal_map);
+      keymap = get_local_map (pt, current_buffer, Qkeymap);
 
       if (CONSP (position))
        {
@@ -1678,7 +1702,7 @@ specified buffer position instead of point are used.
 
          /* For a mouse click, get the local text-property keymap
             of the place clicked on, rather than point.  */
-         
+
          if (POSN_INBUFFER_P (position))
            {
              Lisp_Object pos;
@@ -1689,7 +1713,7 @@ specified buffer position instead of point are used.
                {
                  local_map = get_local_map (XINT (pos),
                                             current_buffer, Qlocal_map);
-                 
+
                  keymap = get_local_map (XINT (pos),
                                          current_buffer, Qkeymap);
                }
@@ -1700,12 +1724,12 @@ specified buffer position instead of point are used.
             string displayed via the `display' property,
             consider `local-map' and `keymap' properties of
             that string.  */
-         
+
          if (string = POSN_STRING (position),
              (CONSP (string) && STRINGP (XCAR (string))))
            {
              Lisp_Object pos, map;
-             
+
              pos = XCDR (string);
              string = XCAR (string);
              if (INTEGERP (pos)
@@ -1721,7 +1745,7 @@ specified buffer position instead of point are used.
                    keymap = map;
                }
            }
-         
+
        }
 
       if (! NILP (keymap))
@@ -1766,7 +1790,7 @@ specified buffer position instead of point are used.
   if (NILP (no_remap) && SYMBOLP (value))
     {
       Lisp_Object value1;
-      if (value1 = Fcommand_remapping (value, position), !NILP (value1))
+      if (value1 = Fcommand_remapping (value, position, Qnil), !NILP (value1))
        value = value1;
     }
 
@@ -2575,15 +2599,6 @@ where_is_internal (definition, keymaps, firstonly, noindirect, no_remap)
   /* 1 means ignore all menu bindings entirely.  */
   int nomenus = !NILP (firstonly) && !EQ (firstonly, Qnon_ascii);
 
-  /* If this command is remapped, then it has no key bindings
-     of its own.  */
-  if (NILP (no_remap) && SYMBOLP (definition))
-    {
-      Lisp_Object tem;
-      if (tem = Fcommand_remapping (definition, Qnil), !NILP (tem))
-       return Qnil;
-    }
-
   found = keymaps;
   while (CONSP (found))
     {
@@ -2597,6 +2612,13 @@ where_is_internal (definition, keymaps, firstonly, noindirect, no_remap)
   found = Qnil;
   sequences = Qnil;
 
+  /* If this command is remapped, then it has no key bindings
+     of its own.  */
+  if (NILP (no_remap)
+      && SYMBOLP (definition)
+      && !NILP (Fcommand_remapping (definition, Qnil, keymaps)))
+    RETURN_UNGCPRO (Qnil);
+
   for (; !NILP (maps); maps = Fcdr (maps))
     {
       /* Key sequence to reach map, and the map that it reaches */
@@ -2990,6 +3012,8 @@ Keyboard translations:\n\n\
 You type        Translation\n\
 --------        -----------\n";
 
+  CHECK_BUFFER (buffer);
+
   shadow = Qnil;
   GCPRO1 (shadow);
 
@@ -3453,9 +3477,13 @@ describe_map (map, prefix, elt_describer, partial, shadow,
              tem = shadow_lookup (shadow, kludge, Qt);
              if (!NILP (tem))
                {
+                 /* If both bindings are keymaps, this key is a prefix key,
+                    so don't say it is shadowed.  */
+                 if (KEYMAPP (definition) && KEYMAPP (tem))
+                   ;
                  /* Avoid generating duplicate entries if the
-                    shadowed binding has the same definition. */
-                 if (mention_shadow && !EQ (tem, definition))
+                    shadowed binding has the same definition.  */
+                 else if (mention_shadow && !EQ (tem, definition))
                    this_shadowed = 1;
                  else
                    continue;
@@ -4065,7 +4093,7 @@ don't alter it yourself.  */);
   DEFVAR_LISP ("minor-mode-map-alist", &Vminor_mode_map_alist,
               doc: /* Alist of keymaps to use for minor modes.
 Each element looks like (VARIABLE . KEYMAP); KEYMAP is used to read
-key sequences and look up bindings iff VARIABLE's value is non-nil.
+key sequences and look up bindings if VARIABLE's value is non-nil.
 If two active keymaps bind the same key, the keymap appearing earlier
 in the list takes precedence.  */);
   Vminor_mode_map_alist = Qnil;