# HG changeset patch # User Kim F. Storm # Date 1079656968 0 # Node ID 3a86bc69c0e3328f3319b6dcd87ca0cac715aa98 # Parent 5636e8542b7745c18dffffe91ad9d379b2f4cbc4 (produce_glyphs): Handle IT_STRETCH. (produce_stretch_glyph): New function to handle space width and align-to display properties on non-window systems. diff -r 5636e8542b77 -r 3a86bc69c0e3 src/term.c --- a/src/term.c Fri Mar 19 00:42:37 2004 +0000 +++ b/src/term.c Fri Mar 19 00:42:48 2004 +0000 @@ -79,6 +79,10 @@ #define OUTPUT1_IF(a) do { if (a) tputs (a, 1, cmputc); } while (0) +/* Display space properties */ + +extern Lisp_Object Qspace, QCalign_to, QCwidth; + /* Function to use to ring the bell. */ Lisp_Object Vring_bell_function; @@ -1595,6 +1599,7 @@ ***********************************************************************/ static void append_glyph P_ ((struct it *)); +static void produce_stretch_glyph P_ ((struct it *)); /* Append glyphs to IT's glyph_row. Called from produce_glyphs for @@ -1658,9 +1663,14 @@ /* If a hook is installed, let it do the work. */ xassert (it->what == IT_CHARACTER || it->what == IT_COMPOSITION - || it->what == IT_IMAGE || it->what == IT_STRETCH); + if (it->what == IT_STRETCH) + { + produce_stretch_glyph (it); + goto done; + } + /* Nothing but characters are supported on terminal frames. For a composition sequence, it->c is the first character of the sequence. */ @@ -1734,6 +1744,7 @@ append_glyph (it); } + done: /* Advance current_x by the pixel width as a convenience for the caller. */ if (it->area == TEXT_AREA) @@ -1743,6 +1754,81 @@ } +/* Produce a stretch glyph for iterator IT. IT->object is the value + of the glyph property displayed. The value must be a list + `(space KEYWORD VALUE ...)' with the following KEYWORD/VALUE pairs + being recognized: + + 1. `:width WIDTH' specifies that the space should be WIDTH * + canonical char width wide. WIDTH may be an integer or floating + point number. + + 2. `:align-to HPOS' specifies that the space should be wide enough + to reach HPOS, a value in canonical character units. */ + +static void +produce_stretch_glyph (it) + struct it *it; +{ + /* (space :width WIDTH ...) */ + Lisp_Object prop, plist; + int width = 0, align_to = -1; + int zero_width_ok_p = 0; + double tem; + + /* List should start with `space'. */ + xassert (CONSP (it->object) && EQ (XCAR (it->object), Qspace)); + plist = XCDR (it->object); + + /* Compute the width of the stretch. */ + if ((prop = Fplist_get (plist, QCwidth), !NILP (prop)) + && calc_pixel_width_or_height (&tem, it, prop, 0, 1, 0)) + { + /* Absolute width `:width WIDTH' specified and valid. */ + zero_width_ok_p = 1; + width = (int)(tem + 0.5); + } + else if ((prop = Fplist_get (plist, QCalign_to), !NILP (prop)) + && calc_pixel_width_or_height (&tem, it, prop, 0, 1, &align_to)) + { + if (it->glyph_row == NULL || !it->glyph_row->mode_line_p) + align_to = (align_to < 0 + ? 0 + : align_to - window_box_left_offset (it->w, TEXT_AREA)); + else if (align_to < 0) + align_to = window_box_left_offset (it->w, TEXT_AREA); + width = max (0, (int)(tem + 0.5) + align_to - it->current_x); + zero_width_ok_p = 1; + } + else + /* Nothing specified -> width defaults to canonical char width. */ + width = FRAME_COLUMN_WIDTH (it->f); + + if (width <= 0 && (width < 0 || !zero_width_ok_p)) + width = 1; + + if (width > 0 && it->glyph_row) + { + Lisp_Object o_object = it->object; + Lisp_Object object = it->stack[it->sp - 1].string; + int n = width; + int c = it->c; + + if (!STRINGP (object)) + object = it->w->buffer; + it->object = object; + it->c = ' '; + it->pixel_width = it->len = 1; + while (n--) + append_glyph (it); + it->object = o_object; + it->c = c; + } + it->pixel_width = width; + it->nglyphs = width; +} + + /* Get information about special display element WHAT in an environment described by IT. WHAT is one of IT_TRUNCATION or IT_CONTINUATION. Maybe produce glyphs for WHAT if IT has a