# HG changeset patch # User Stefan Monnier # Date 1206564407 0 # Node ID 6b2d6832b219085a342ae937010b6495ac72cf4e # Parent e40fb0b0ea6c9633959aec7a40c0ad7e342f03aa (check_display_width): New fun. (scan_for_column): Use it. diff -r e40fb0b0ea6c -r 6b2d6832b219 src/ChangeLog --- a/src/ChangeLog Wed Mar 26 20:26:50 2008 +0000 +++ b/src/ChangeLog Wed Mar 26 20:46:47 2008 +0000 @@ -1,5 +1,8 @@ 2008-03-26 Stefan Monnier + * indent.c (check_display_width): New fun. + (scan_for_column): Use it. + * data.c (syms_of_data): Mark most-positive-fixnum and most-negative-fixnum as constants. diff -r e40fb0b0ea6c -r 6b2d6832b219 src/indent.c --- a/src/indent.c Wed Mar 26 20:26:50 2008 +0000 +++ b/src/indent.c Wed Mar 26 20:46:47 2008 +0000 @@ -504,6 +504,47 @@ return col; } +extern Lisp_Object Qspace, QCwidth, QCalign_to; + +/* Check the presence of a display property and compute its width. + If a property was found and its width was found as well, return + its width (>= 0) and set the position of the end of the property + in ENDPOS. + Otherwise just return -1. */ +static int +check_display_width (EMACS_INT pos, EMACS_INT col, EMACS_INT *endpos) +{ + Lisp_Object val, overlay; + + if (CONSP (val = get_char_property_and_overlay + (make_number (pos), Qdisplay, Qnil, &overlay)) + && EQ (Qspace, XCAR (val))) + { /* FIXME: Use calc_pixel_width_or_height, as in term.c. */ + Lisp_Object plist = XCDR (val), prop; + int width = -1; + + if ((prop = Fplist_get (plist, QCwidth), NATNUMP (prop))) + width = XINT (prop); + else if (FLOATP (prop)) + width = (int)(XFLOAT_DATA (prop) + 0.5); + else if ((prop = Fplist_get (plist, QCalign_to), NATNUMP (prop))) + width = XINT (prop) - col; + else if (FLOATP (prop)) + width = (int)(XFLOAT_DATA (prop) + 0.5) - col; + + if (width >= 0) + { + EMACS_INT start; + if (OVERLAYP (overlay)) + *endpos = OVERLAY_POSITION (OVERLAY_END (overlay)); + else + get_property_and_range (pos, Qdisplay, &val, &start, endpos, Qnil); + return width; + } + } + return -1; +} + /* Scanning from the beginning of the current line, stop at the buffer position ENDPOS or at the column GOALCOL or at the end of line, whichever comes first. @@ -560,8 +601,7 @@ break; prev_col = col; - /* Check composition sequence. */ - { + { /* Check composition sequence. */ int len, len_byte, width; if (check_composition (scan, scan_byte, end, @@ -575,6 +615,20 @@ } } + { /* Check display property. */ + EMACS_INT end; + int width = check_display_width (scan, col, &end); + if (width >= 0) + { + col += width; + if (end > scan) /* Avoid infinite loops with 0-width overlays. */ + { + scan = end; scan_byte = charpos_to_bytepos (scan); + continue; + } + } + } + c = FETCH_BYTE (scan_byte); /* See if there is a display table and it relates