]> code.delx.au - gnu-emacs/blobdiff - src/editfns.c
(TeX_commands): Skip comments.
[gnu-emacs] / src / editfns.c
index 7f94150d0ee25735846a21e42df39dd1b168171d..a2e2aaf269e3e468289b9876bfb9a17ed452296c 100644 (file)
@@ -1,5 +1,5 @@
 /* Lisp functions pertaining to editing.
-   Copyright (C) 1985,86,87,89,93,94,95,96,97,98, 1999, 2000, 2001
+   Copyright (C) 1985,86,87,89,93,94,95,96,97,98, 1999, 2000, 2001, 2002
        Free Software Foundation, Inc.
 
 This file is part of GNU Emacs.
@@ -33,6 +33,12 @@ Boston, MA 02111-1307, USA.  */
 #include <unistd.h>
 #endif
 
+/* Without this, sprintf on Mac OS Classic will produce wrong
+   result.  */
+#ifdef MAC_OS8
+#include <stdio.h>
+#endif
+
 #include <ctype.h>
 
 #include "lisp.h"
@@ -64,7 +70,7 @@ extern Lisp_Object make_time P_ ((time_t));
 extern size_t emacs_strftimeu P_ ((char *, size_t, const char *,
                                   const struct tm *, int));
 static int tm_diff P_ ((struct tm *, struct tm *));
-static void find_field P_ ((Lisp_Object, Lisp_Object, int *, int *));
+static void find_field P_ ((Lisp_Object, Lisp_Object, Lisp_Object, int *, Lisp_Object, int *));
 static void update_buffer_properties P_ ((int, int));
 static Lisp_Object region_limit P_ ((int));
 static int lisp_time_argument P_ ((Lisp_Object, time_t *, int *));
@@ -293,7 +299,7 @@ region_limit (beginningp)
   
   m = Fmarker_position (current_buffer->mark);
   if (NILP (m))
-    error ("There is no region now");
+    error ("The mark is not set now, so there is no region");
   
   if ((PT < XFASTINT (m)) == beginningp)
     m = make_number (PT);
@@ -323,87 +329,14 @@ If you set the marker not to point anywhere, the buffer will have no mark.  */)
   return current_buffer->mark;
 }
 
-\f
-#if 0 /* Not used.  */
-
-/* Return nonzero if POS1 and POS2 have the same value
-   for the text property PROP.  */
-
-static int
-char_property_eq (prop, pos1, pos2)
-     Lisp_Object prop;
-     Lisp_Object pos1, pos2;
-{
-  Lisp_Object pval1, pval2;
-
-  pval1 = Fget_char_property (pos1, prop, Qnil);
-  pval2 = Fget_char_property (pos2, prop, Qnil);
-
-  return EQ (pval1, pval2);
-}
-
-#endif /* 0 */
-
-/* Return the direction from which the text-property PROP would be
-   inherited by any new text inserted at POS: 1 if it would be
-   inherited from the char after POS, -1 if it would be inherited from
-   the char before POS, and 0 if from neither.  */
-
-static int
-text_property_stickiness (prop, pos)
-     Lisp_Object prop;
-     Lisp_Object pos;
-{
-  Lisp_Object prev_pos, front_sticky;
-  int is_rear_sticky = 1, is_front_sticky = 0; /* defaults */
-
-  if (XINT (pos) > BEGV)
-    /* Consider previous character.  */
-    {
-      Lisp_Object rear_non_sticky;
-
-      prev_pos = make_number (XINT (pos) - 1);
-      rear_non_sticky = Fget_text_property (prev_pos, Qrear_nonsticky, Qnil);
-
-      if (!NILP (CONSP (rear_non_sticky)
-                ? Fmemq (prop, rear_non_sticky)
-                : rear_non_sticky))
-       /* PROP is rear-non-sticky.  */
-       is_rear_sticky = 0;
-    }
-
-  /* Consider following character.  */
-  front_sticky = Fget_text_property (pos, Qfront_sticky, Qnil);
-
-  if (EQ (front_sticky, Qt)
-      || (CONSP (front_sticky)
-         && !NILP (Fmemq (prop, front_sticky))))
-    /* PROP is inherited from after.  */
-    is_front_sticky = 1;
-
-  /* Simple cases, where the properties are consistent.  */
-  if (is_rear_sticky && !is_front_sticky)
-    return -1;
-  else if (!is_rear_sticky && is_front_sticky)
-    return 1;
-  else if (!is_rear_sticky && !is_front_sticky)
-    return 0;
-
-  /* The stickiness properties are inconsistent, so we have to
-     disambiguate.  Basically, rear-sticky wins, _except_ if the
-     property that would be inherited has a value of nil, in which case
-     front-sticky wins.  */
-  if (XINT (pos) == BEGV || NILP (Fget_text_property (prev_pos, prop, Qnil)))
-    return 1;
-  else
-    return -1;
-}
-
 \f
 /* Find the field surrounding POS in *BEG and *END.  If POS is nil,
    the value of point is used instead.  If BEG or END null,
    means don't store the beginning or end of the field.
 
+   BEG_LIMIT and END_LIMIT serve to limit the ranged of the returned
+   results; they do not effect boundary behavior.
+
    If MERGE_AT_BOUNDARY is nonzero, then if POS is at the very first
    position of a field, then the beginning of the previous field is
    returned instead of the beginning of POS's field (since the end of a
@@ -418,9 +351,10 @@ text_property_stickiness (prop, pos)
    is not stored.  */
 
 static void
-find_field (pos, merge_at_boundary, beg, end)
+find_field (pos, merge_at_boundary, beg_limit, beg, end_limit, end)
      Lisp_Object pos;
      Lisp_Object merge_at_boundary;
+     Lisp_Object beg_limit, end_limit;
      int *beg, *end;
 {
   /* Fields right before and after the point.  */
@@ -544,9 +478,11 @@ find_field (pos, merge_at_boundary, beg, end)
        {
          if (!NILP (merge_at_boundary) && EQ (before_field, Qboundary))
            /* Skip a `boundary' field.  */
-           pos = Fprevious_single_char_property_change (pos, Qfield, Qnil,Qnil);
+           pos = Fprevious_single_char_property_change (pos, Qfield, Qnil,
+                                                        beg_limit);
 
-         pos = Fprevious_single_char_property_change (pos, Qfield, Qnil, Qnil);
+         pos = Fprevious_single_char_property_change (pos, Qfield, Qnil,
+                                                      beg_limit);
          *beg = NILP (pos) ? BEGV : XFASTINT (pos);
        }
     }
@@ -562,9 +498,11 @@ find_field (pos, merge_at_boundary, beg, end)
        {
          if (!NILP (merge_at_boundary) && EQ (after_field, Qboundary))
            /* Skip a `boundary' field.  */
-           pos = Fnext_single_char_property_change (pos, Qfield, Qnil, Qnil);
+           pos = Fnext_single_char_property_change (pos, Qfield, Qnil,
+                                                    end_limit);
 
-         pos = Fnext_single_char_property_change (pos, Qfield, Qnil, Qnil);
+         pos = Fnext_single_char_property_change (pos, Qfield, Qnil,
+                                                  end_limit);
          *end = NILP (pos) ? ZV : XFASTINT (pos);
        }
     }
@@ -579,7 +517,7 @@ If POS is nil, the value of point is used for POS.  */)
      Lisp_Object pos;
 {
   int beg, end;
-  find_field (pos, Qnil, &beg, &end);
+  find_field (pos, Qnil, Qnil, &beg, Qnil, &end);
   if (beg != end)
     del_range (beg, end);
   return Qnil;
@@ -593,7 +531,7 @@ If POS is nil, the value of point is used for POS.  */)
      Lisp_Object pos;
 {
   int beg, end;
-  find_field (pos, Qnil, &beg, &end);
+  find_field (pos, Qnil, Qnil, &beg, Qnil, &end);
   return make_buffer_string (beg, end, 1);
 }
 
@@ -605,35 +543,39 @@ If POS is nil, the value of point is used for POS.  */)
      Lisp_Object pos;
 {
   int beg, end;
-  find_field (pos, Qnil, &beg, &end);
+  find_field (pos, Qnil, Qnil, &beg, Qnil, &end);
   return make_buffer_string (beg, end, 0);
 }
 
-DEFUN ("field-beginning", Ffield_beginning, Sfield_beginning, 0, 2, 0,
+DEFUN ("field-beginning", Ffield_beginning, Sfield_beginning, 0, 3, 0,
        doc: /* Return the beginning of the field surrounding POS.
 A field is a region of text with the same `field' property.
 If POS is nil, the value of point is used for POS.
 If ESCAPE-FROM-EDGE is non-nil and POS is at the beginning of its
-field, then the beginning of the *previous* field is returned.  */)
-     (pos, escape_from_edge)
-     Lisp_Object pos, escape_from_edge;
+field, then the beginning of the *previous* field is returned.
+If LIMIT is non-nil, it is a buffer position; if the beginning of the field
+is before LIMIT, then LIMIT will be returned instead.  */)
+     (pos, escape_from_edge, limit)
+     Lisp_Object pos, escape_from_edge, limit;
 {
   int beg;
-  find_field (pos, escape_from_edge, &beg, 0);
+  find_field (pos, escape_from_edge, limit, &beg, Qnil, 0);
   return make_number (beg);
 }
 
-DEFUN ("field-end", Ffield_end, Sfield_end, 0, 2, 0,
+DEFUN ("field-end", Ffield_end, Sfield_end, 0, 3, 0,
        doc: /* Return the end of the field surrounding POS.
 A field is a region of text with the same `field' property.
 If POS is nil, the value of point is used for POS.
 If ESCAPE-FROM-EDGE is non-nil and POS is at the end of its field,
-then the end of the *following* field is returned.  */)
-     (pos, escape_from_edge)
-     Lisp_Object pos, escape_from_edge;
+then the end of the *following* field is returned.
+If LIMIT is non-nil, it is a buffer position; if the end of the field
+is after LIMIT, then LIMIT will be returned instead.  */)
+     (pos, escape_from_edge, limit)
+     Lisp_Object pos, escape_from_edge, limit;
 {
   int end;
-  find_field (pos, escape_from_edge, 0, &end);
+  find_field (pos, escape_from_edge, Qnil, 0, limit, &end);
   return make_number (end);
 }
 
@@ -696,9 +638,9 @@ Field boundaries are not noticed if `inhibit-field-text-motion' is non-nil.  */)
       fwd = (XFASTINT (new_pos) > XFASTINT (old_pos));
 
       if (fwd)
-       field_bound = Ffield_end (old_pos, escape_from_edge);
+       field_bound = Ffield_end (old_pos, escape_from_edge, new_pos);
       else
-       field_bound = Ffield_beginning (old_pos, escape_from_edge);
+       field_bound = Ffield_beginning (old_pos, escape_from_edge, new_pos);
 
       if (/* See if ESCAPE_FROM_EDGE caused FIELD_BOUND to jump to the
              other side of NEW_POS, which would mean that NEW_POS is
@@ -2461,6 +2403,8 @@ determines whether case is significant or ignored.  */)
         characters, not just the bytes.  */
       int c1, c2;
 
+      QUIT;
+
       if (! NILP (bp1->enable_multibyte_characters))
        {
          c1 = BUF_FETCH_MULTIBYTE_CHAR (bp1, i1_byte);
@@ -3082,7 +3026,7 @@ DEFUN ("current-message", Fcurrent_message, Scurrent_message, 0, 0, 0,
 }
 
 
-DEFUN ("propertize", Fpropertize, Spropertize, 3, MANY, 0,
+DEFUN ("propertize", Fpropertize, Spropertize, 1, MANY, 0,
        doc: /* Return a copy of STRING with text properties added.
 First argument is the string to copy.
 Remaining arguments form a sequence of PROPERTY VALUE pairs for text
@@ -3097,7 +3041,7 @@ usage: (propertize STRING &rest PROPERTIES)  */)
   int i;
 
   /* Number of args must be odd.  */
-  if ((nargs & 1) == 0 || nargs < 3)
+  if ((nargs & 1) == 0 || nargs < 1)
     error ("Wrong number of arguments");
 
   properties = string = Qnil;
@@ -3203,6 +3147,7 @@ usage: (format STRING &rest OBJECTS)  */)
     if (*format++ == '%')
       {
        int thissize = 0;
+       int actual_width = 0;
        unsigned char *this_format_start = format - 1;
        int field_width, precision;
 
@@ -3268,7 +3213,7 @@ usage: (format STRING &rest OBJECTS)  */)
          {
            /* Use a temp var to avoid problems when ENABLE_CHECKING
               is turned on.  */
-           struct Lisp_String *t = XSYMBOL (args[n])->name;
+           struct Lisp_String *t = XSTRING (SYMBOL_NAME (args[n]));
            XSETSTRING (args[n], t);
            if (STRING_MULTIBYTE (args[n]) && ! multibyte)
              {
@@ -3283,6 +3228,7 @@ usage: (format STRING &rest OBJECTS)  */)
            if (*format != 's' && *format != 'S')
              error ("Format specifier doesn't match argument type");
            thissize = CONVERTED_BYTE_SIZE (multibyte, args[n]);
+           actual_width = lisp_string_width (args[n], -1, NULL, NULL);
          }
        /* Would get MPV otherwise, since Lisp_Int's `point' to low memory.  */
        else if (INTEGERP (args[n]) && *format != 's')
@@ -3336,7 +3282,7 @@ usage: (format STRING &rest OBJECTS)  */)
            goto string;
          }
 
-       thissize = max (field_width, thissize);
+       thissize += max (0, field_width - actual_width);
        total += thissize + 4;
       }
 
@@ -3979,7 +3925,7 @@ syms_of_editfns ()
   staticpro (&Qbuffer_access_fontify_functions);
 
   DEFVAR_LISP ("inhibit-field-text-motion", &Vinhibit_field_text_motion,
-              doc: /* Non-nil means.text motion commands don't notice fields.  */);
+              doc: /* Non-nil means text motion commands don't notice fields.  */);
   Vinhibit_field_text_motion = Qnil;
 
   DEFVAR_LISP ("buffer-access-fontify-functions",