]> code.delx.au - gnu-emacs/blob - src/xdisp.c
Merge from origin/emacs-24
[gnu-emacs] / src / xdisp.c
1 /* Display generation from window structure and buffer text.
2
3 Copyright (C) 1985-1988, 1993-1995, 1997-2015 Free Software Foundation,
4 Inc.
5
6 This file is part of GNU Emacs.
7
8 GNU Emacs is free software: you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation, either version 3 of the License, or
11 (at your option) any later version.
12
13 GNU Emacs is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
20
21 /* New redisplay written by Gerd Moellmann <gerd@gnu.org>.
22
23 Redisplay.
24
25 Emacs separates the task of updating the display from code
26 modifying global state, e.g. buffer text. This way functions
27 operating on buffers don't also have to be concerned with updating
28 the display.
29
30 Updating the display is triggered by the Lisp interpreter when it
31 decides it's time to do it. This is done either automatically for
32 you as part of the interpreter's command loop or as the result of
33 calling Lisp functions like `sit-for'. The C function `redisplay'
34 in xdisp.c is the only entry into the inner redisplay code.
35
36 The following diagram shows how redisplay code is invoked. As you
37 can see, Lisp calls redisplay and vice versa. Under window systems
38 like X, some portions of the redisplay code are also called
39 asynchronously during mouse movement or expose events. It is very
40 important that these code parts do NOT use the C library (malloc,
41 free) because many C libraries under Unix are not reentrant. They
42 may also NOT call functions of the Lisp interpreter which could
43 change the interpreter's state. If you don't follow these rules,
44 you will encounter bugs which are very hard to explain.
45
46 +--------------+ redisplay +----------------+
47 | Lisp machine |---------------->| Redisplay code |<--+
48 +--------------+ (xdisp.c) +----------------+ |
49 ^ | |
50 +----------------------------------+ |
51 Don't use this path when called |
52 asynchronously! |
53 |
54 expose_window (asynchronous) |
55 |
56 X expose events -----+
57
58 What does redisplay do? Obviously, it has to figure out somehow what
59 has been changed since the last time the display has been updated,
60 and to make these changes visible. Preferably it would do that in
61 a moderately intelligent way, i.e. fast.
62
63 Changes in buffer text can be deduced from window and buffer
64 structures, and from some global variables like `beg_unchanged' and
65 `end_unchanged'. The contents of the display are additionally
66 recorded in a `glyph matrix', a two-dimensional matrix of glyph
67 structures. Each row in such a matrix corresponds to a line on the
68 display, and each glyph in a row corresponds to a column displaying
69 a character, an image, or what else. This matrix is called the
70 `current glyph matrix' or `current matrix' in redisplay
71 terminology.
72
73 For buffer parts that have been changed since the last update, a
74 second glyph matrix is constructed, the so called `desired glyph
75 matrix' or short `desired matrix'. Current and desired matrix are
76 then compared to find a cheap way to update the display, e.g. by
77 reusing part of the display by scrolling lines.
78
79 You will find a lot of redisplay optimizations when you start
80 looking at the innards of redisplay. The overall goal of all these
81 optimizations is to make redisplay fast because it is done
82 frequently. Some of these optimizations are implemented by the
83 following functions:
84
85 . try_cursor_movement
86
87 This function tries to update the display if the text in the
88 window did not change and did not scroll, only point moved, and
89 it did not move off the displayed portion of the text.
90
91 . try_window_reusing_current_matrix
92
93 This function reuses the current matrix of a window when text
94 has not changed, but the window start changed (e.g., due to
95 scrolling).
96
97 . try_window_id
98
99 This function attempts to redisplay a window by reusing parts of
100 its existing display. It finds and reuses the part that was not
101 changed, and redraws the rest. (The "id" part in the function's
102 name stands for "insert/delete", not for "identification" or
103 somesuch.)
104
105 . try_window
106
107 This function performs the full redisplay of a single window
108 assuming that its fonts were not changed and that the cursor
109 will not end up in the scroll margins. (Loading fonts requires
110 re-adjustment of dimensions of glyph matrices, which makes this
111 method impossible to use.)
112
113 These optimizations are tried in sequence (some can be skipped if
114 it is known that they are not applicable). If none of the
115 optimizations were successful, redisplay calls redisplay_windows,
116 which performs a full redisplay of all windows.
117
118 Note that there's one more important optimization up Emacs's
119 sleeve, but it is related to actually redrawing the potentially
120 changed portions of the window/frame, not to reproducing the
121 desired matrices of those potentially changed portions. Namely,
122 the function update_frame and its subroutines, which you will find
123 in dispnew.c, compare the desired matrices with the current
124 matrices, and only redraw the portions that changed. So it could
125 happen that the functions in this file for some reason decide that
126 the entire desired matrix needs to be regenerated from scratch, and
127 still only parts of the Emacs display, or even nothing at all, will
128 be actually delivered to the glass, because update_frame has found
129 that the new and the old screen contents are similar or identical.
130
131 Desired matrices.
132
133 Desired matrices are always built per Emacs window. The function
134 `display_line' is the central function to look at if you are
135 interested. It constructs one row in a desired matrix given an
136 iterator structure containing both a buffer position and a
137 description of the environment in which the text is to be
138 displayed. But this is too early, read on.
139
140 Characters and pixmaps displayed for a range of buffer text depend
141 on various settings of buffers and windows, on overlays and text
142 properties, on display tables, on selective display. The good news
143 is that all this hairy stuff is hidden behind a small set of
144 interface functions taking an iterator structure (struct it)
145 argument.
146
147 Iteration over things to be displayed is then simple. It is
148 started by initializing an iterator with a call to init_iterator,
149 passing it the buffer position where to start iteration. For
150 iteration over strings, pass -1 as the position to init_iterator,
151 and call reseat_to_string when the string is ready, to initialize
152 the iterator for that string. Thereafter, calls to
153 get_next_display_element fill the iterator structure with relevant
154 information about the next thing to display. Calls to
155 set_iterator_to_next move the iterator to the next thing.
156
157 Besides this, an iterator also contains information about the
158 display environment in which glyphs for display elements are to be
159 produced. It has fields for the width and height of the display,
160 the information whether long lines are truncated or continued, a
161 current X and Y position, and lots of other stuff you can better
162 see in dispextern.h.
163
164 Glyphs in a desired matrix are normally constructed in a loop
165 calling get_next_display_element and then PRODUCE_GLYPHS. The call
166 to PRODUCE_GLYPHS will fill the iterator structure with pixel
167 information about the element being displayed and at the same time
168 produce glyphs for it. If the display element fits on the line
169 being displayed, set_iterator_to_next is called next, otherwise the
170 glyphs produced are discarded. The function display_line is the
171 workhorse of filling glyph rows in the desired matrix with glyphs.
172 In addition to producing glyphs, it also handles line truncation
173 and continuation, word wrap, and cursor positioning (for the
174 latter, see also set_cursor_from_row).
175
176 Frame matrices.
177
178 That just couldn't be all, could it? What about terminal types not
179 supporting operations on sub-windows of the screen? To update the
180 display on such a terminal, window-based glyph matrices are not
181 well suited. To be able to reuse part of the display (scrolling
182 lines up and down), we must instead have a view of the whole
183 screen. This is what `frame matrices' are for. They are a trick.
184
185 Frames on terminals like above have a glyph pool. Windows on such
186 a frame sub-allocate their glyph memory from their frame's glyph
187 pool. The frame itself is given its own glyph matrices. By
188 coincidence---or maybe something else---rows in window glyph
189 matrices are slices of corresponding rows in frame matrices. Thus
190 writing to window matrices implicitly updates a frame matrix which
191 provides us with the view of the whole screen that we originally
192 wanted to have without having to move many bytes around. To be
193 honest, there is a little bit more done, but not much more. If you
194 plan to extend that code, take a look at dispnew.c. The function
195 build_frame_matrix is a good starting point.
196
197 Bidirectional display.
198
199 Bidirectional display adds quite some hair to this already complex
200 design. The good news are that a large portion of that hairy stuff
201 is hidden in bidi.c behind only 3 interfaces. bidi.c implements a
202 reordering engine which is called by set_iterator_to_next and
203 returns the next character to display in the visual order. See
204 commentary on bidi.c for more details. As far as redisplay is
205 concerned, the effect of calling bidi_move_to_visually_next, the
206 main interface of the reordering engine, is that the iterator gets
207 magically placed on the buffer or string position that is to be
208 displayed next. In other words, a linear iteration through the
209 buffer/string is replaced with a non-linear one. All the rest of
210 the redisplay is oblivious to the bidi reordering.
211
212 Well, almost oblivious---there are still complications, most of
213 them due to the fact that buffer and string positions no longer
214 change monotonously with glyph indices in a glyph row. Moreover,
215 for continued lines, the buffer positions may not even be
216 monotonously changing with vertical positions. Also, accounting
217 for face changes, overlays, etc. becomes more complex because
218 non-linear iteration could potentially skip many positions with
219 changes, and then cross them again on the way back...
220
221 One other prominent effect of bidirectional display is that some
222 paragraphs of text need to be displayed starting at the right
223 margin of the window---the so-called right-to-left, or R2L
224 paragraphs. R2L paragraphs are displayed with R2L glyph rows,
225 which have their reversed_p flag set. The bidi reordering engine
226 produces characters in such rows starting from the character which
227 should be the rightmost on display. PRODUCE_GLYPHS then reverses
228 the order, when it fills up the glyph row whose reversed_p flag is
229 set, by prepending each new glyph to what is already there, instead
230 of appending it. When the glyph row is complete, the function
231 extend_face_to_end_of_line fills the empty space to the left of the
232 leftmost character with special glyphs, which will display as,
233 well, empty. On text terminals, these special glyphs are simply
234 blank characters. On graphics terminals, there's a single stretch
235 glyph of a suitably computed width. Both the blanks and the
236 stretch glyph are given the face of the background of the line.
237 This way, the terminal-specific back-end can still draw the glyphs
238 left to right, even for R2L lines.
239
240 Bidirectional display and character compositions
241
242 Some scripts cannot be displayed by drawing each character
243 individually, because adjacent characters change each other's shape
244 on display. For example, Arabic and Indic scripts belong to this
245 category.
246
247 Emacs display supports this by providing "character compositions",
248 most of which is implemented in composite.c. During the buffer
249 scan that delivers characters to PRODUCE_GLYPHS, if the next
250 character to be delivered is a composed character, the iteration
251 calls composition_reseat_it and next_element_from_composition. If
252 they succeed to compose the character with one or more of the
253 following characters, the whole sequence of characters that where
254 composed is recorded in the `struct composition_it' object that is
255 part of the buffer iterator. The composed sequence could produce
256 one or more font glyphs (called "grapheme clusters") on the screen.
257 Each of these grapheme clusters is then delivered to PRODUCE_GLYPHS
258 in the direction corresponding to the current bidi scan direction
259 (recorded in the scan_dir member of the `struct bidi_it' object
260 that is part of the buffer iterator). In particular, if the bidi
261 iterator currently scans the buffer backwards, the grapheme
262 clusters are delivered back to front. This reorders the grapheme
263 clusters as appropriate for the current bidi context. Note that
264 this means that the grapheme clusters are always stored in the
265 LGSTRING object (see composite.c) in the logical order.
266
267 Moving an iterator in bidirectional text
268 without producing glyphs
269
270 Note one important detail mentioned above: that the bidi reordering
271 engine, driven by the iterator, produces characters in R2L rows
272 starting at the character that will be the rightmost on display.
273 As far as the iterator is concerned, the geometry of such rows is
274 still left to right, i.e. the iterator "thinks" the first character
275 is at the leftmost pixel position. The iterator does not know that
276 PRODUCE_GLYPHS reverses the order of the glyphs that the iterator
277 delivers. This is important when functions from the move_it_*
278 family are used to get to certain screen position or to match
279 screen coordinates with buffer coordinates: these functions use the
280 iterator geometry, which is left to right even in R2L paragraphs.
281 This works well with most callers of move_it_*, because they need
282 to get to a specific column, and columns are still numbered in the
283 reading order, i.e. the rightmost character in a R2L paragraph is
284 still column zero. But some callers do not get well with this; a
285 notable example is mouse clicks that need to find the character
286 that corresponds to certain pixel coordinates. See
287 buffer_posn_from_coords in dispnew.c for how this is handled. */
288
289 #include <config.h>
290 #include <stdio.h>
291 #include <limits.h>
292
293 #include "lisp.h"
294 #include "atimer.h"
295 #include "keyboard.h"
296 #include "frame.h"
297 #include "window.h"
298 #include "termchar.h"
299 #include "dispextern.h"
300 #include "character.h"
301 #include "buffer.h"
302 #include "charset.h"
303 #include "indent.h"
304 #include "commands.h"
305 #include "keymap.h"
306 #include "macros.h"
307 #include "disptab.h"
308 #include "termhooks.h"
309 #include "termopts.h"
310 #include "intervals.h"
311 #include "coding.h"
312 #include "process.h"
313 #include "region-cache.h"
314 #include "font.h"
315 #include "fontset.h"
316 #include "blockinput.h"
317 #ifdef HAVE_WINDOW_SYSTEM
318 #include TERM_HEADER
319 #endif /* HAVE_WINDOW_SYSTEM */
320
321 #ifndef FRAME_X_OUTPUT
322 #define FRAME_X_OUTPUT(f) ((f)->output_data.x)
323 #endif
324
325 #define INFINITY 10000000
326
327 /* Holds the list (error). */
328 static Lisp_Object list_of_error;
329
330 #ifdef HAVE_WINDOW_SYSTEM
331
332 /* Test if overflow newline into fringe. Called with iterator IT
333 at or past right window margin, and with IT->current_x set. */
334
335 #define IT_OVERFLOW_NEWLINE_INTO_FRINGE(IT) \
336 (!NILP (Voverflow_newline_into_fringe) \
337 && FRAME_WINDOW_P ((IT)->f) \
338 && ((IT)->bidi_it.paragraph_dir == R2L \
339 ? (WINDOW_LEFT_FRINGE_WIDTH ((IT)->w) > 0) \
340 : (WINDOW_RIGHT_FRINGE_WIDTH ((IT)->w) > 0)) \
341 && (IT)->current_x == (IT)->last_visible_x)
342
343 #else /* !HAVE_WINDOW_SYSTEM */
344 #define IT_OVERFLOW_NEWLINE_INTO_FRINGE(it) 0
345 #endif /* HAVE_WINDOW_SYSTEM */
346
347 /* Test if the display element loaded in IT, or the underlying buffer
348 or string character, is a space or a TAB character. This is used
349 to determine where word wrapping can occur. */
350
351 #define IT_DISPLAYING_WHITESPACE(it) \
352 ((it->what == IT_CHARACTER && (it->c == ' ' || it->c == '\t')) \
353 || ((STRINGP (it->string) \
354 && (SREF (it->string, IT_STRING_BYTEPOS (*it)) == ' ' \
355 || SREF (it->string, IT_STRING_BYTEPOS (*it)) == '\t')) \
356 || (it->s \
357 && (it->s[IT_BYTEPOS (*it)] == ' ' \
358 || it->s[IT_BYTEPOS (*it)] == '\t')) \
359 || (IT_BYTEPOS (*it) < ZV_BYTE \
360 && (*BYTE_POS_ADDR (IT_BYTEPOS (*it)) == ' ' \
361 || *BYTE_POS_ADDR (IT_BYTEPOS (*it)) == '\t')))) \
362
363 /* Non-zero means print newline to stdout before next mini-buffer
364 message. */
365
366 bool noninteractive_need_newline;
367
368 /* Non-zero means print newline to message log before next message. */
369
370 static bool message_log_need_newline;
371
372 /* Three markers that message_dolog uses.
373 It could allocate them itself, but that causes trouble
374 in handling memory-full errors. */
375 static Lisp_Object message_dolog_marker1;
376 static Lisp_Object message_dolog_marker2;
377 static Lisp_Object message_dolog_marker3;
378 \f
379 /* The buffer position of the first character appearing entirely or
380 partially on the line of the selected window which contains the
381 cursor; <= 0 if not known. Set by set_cursor_from_row, used for
382 redisplay optimization in redisplay_internal. */
383
384 static struct text_pos this_line_start_pos;
385
386 /* Number of characters past the end of the line above, including the
387 terminating newline. */
388
389 static struct text_pos this_line_end_pos;
390
391 /* The vertical positions and the height of this line. */
392
393 static int this_line_vpos;
394 static int this_line_y;
395 static int this_line_pixel_height;
396
397 /* X position at which this display line starts. Usually zero;
398 negative if first character is partially visible. */
399
400 static int this_line_start_x;
401
402 /* The smallest character position seen by move_it_* functions as they
403 move across display lines. Used to set MATRIX_ROW_START_CHARPOS of
404 hscrolled lines, see display_line. */
405
406 static struct text_pos this_line_min_pos;
407
408 /* Buffer that this_line_.* variables are referring to. */
409
410 static struct buffer *this_line_buffer;
411
412 /* Nonzero if an overlay arrow has been displayed in this window. */
413
414 static bool overlay_arrow_seen;
415
416 /* Vector containing glyphs for an ellipsis `...'. */
417
418 static Lisp_Object default_invis_vector[3];
419
420 /* This is the window where the echo area message was displayed. It
421 is always a mini-buffer window, but it may not be the same window
422 currently active as a mini-buffer. */
423
424 Lisp_Object echo_area_window;
425
426 /* List of pairs (MESSAGE . MULTIBYTE). The function save_message
427 pushes the current message and the value of
428 message_enable_multibyte on the stack, the function restore_message
429 pops the stack and displays MESSAGE again. */
430
431 static Lisp_Object Vmessage_stack;
432
433 /* Nonzero means multibyte characters were enabled when the echo area
434 message was specified. */
435
436 static bool message_enable_multibyte;
437
438 /* Nonzero if we should redraw the mode lines on the next redisplay.
439 If it has value REDISPLAY_SOME, then only redisplay the mode lines where
440 the `redisplay' bit has been set. Otherwise, redisplay all mode lines
441 (the number used is then only used to track down the cause for this
442 full-redisplay). */
443
444 int update_mode_lines;
445
446 /* Nonzero if window sizes or contents other than selected-window have changed
447 since last redisplay that finished.
448 If it has value REDISPLAY_SOME, then only redisplay the windows where
449 the `redisplay' bit has been set. Otherwise, redisplay all windows
450 (the number used is then only used to track down the cause for this
451 full-redisplay). */
452
453 int windows_or_buffers_changed;
454
455 /* Nonzero after display_mode_line if %l was used and it displayed a
456 line number. */
457
458 static bool line_number_displayed;
459
460 /* The name of the *Messages* buffer, a string. */
461
462 static Lisp_Object Vmessages_buffer_name;
463
464 /* Current, index 0, and last displayed echo area message. Either
465 buffers from echo_buffers, or nil to indicate no message. */
466
467 Lisp_Object echo_area_buffer[2];
468
469 /* The buffers referenced from echo_area_buffer. */
470
471 static Lisp_Object echo_buffer[2];
472
473 /* A vector saved used in with_area_buffer to reduce consing. */
474
475 static Lisp_Object Vwith_echo_area_save_vector;
476
477 /* Non-zero means display_echo_area should display the last echo area
478 message again. Set by redisplay_preserve_echo_area. */
479
480 static bool display_last_displayed_message_p;
481
482 /* Nonzero if echo area is being used by print; zero if being used by
483 message. */
484
485 static bool message_buf_print;
486
487 /* Set to 1 in clear_message to make redisplay_internal aware
488 of an emptied echo area. */
489
490 static bool message_cleared_p;
491
492 /* A scratch glyph row with contents used for generating truncation
493 glyphs. Also used in direct_output_for_insert. */
494
495 #define MAX_SCRATCH_GLYPHS 100
496 static struct glyph_row scratch_glyph_row;
497 static struct glyph scratch_glyphs[MAX_SCRATCH_GLYPHS];
498
499 /* Ascent and height of the last line processed by move_it_to. */
500
501 static int last_height;
502
503 /* Non-zero if there's a help-echo in the echo area. */
504
505 bool help_echo_showing_p;
506
507 /* The maximum distance to look ahead for text properties. Values
508 that are too small let us call compute_char_face and similar
509 functions too often which is expensive. Values that are too large
510 let us call compute_char_face and alike too often because we
511 might not be interested in text properties that far away. */
512
513 #define TEXT_PROP_DISTANCE_LIMIT 100
514
515 /* SAVE_IT and RESTORE_IT are called when we save a snapshot of the
516 iterator state and later restore it. This is needed because the
517 bidi iterator on bidi.c keeps a stacked cache of its states, which
518 is really a singleton. When we use scratch iterator objects to
519 move around the buffer, we can cause the bidi cache to be pushed or
520 popped, and therefore we need to restore the cache state when we
521 return to the original iterator. */
522 #define SAVE_IT(ITCOPY,ITORIG,CACHE) \
523 do { \
524 if (CACHE) \
525 bidi_unshelve_cache (CACHE, 1); \
526 ITCOPY = ITORIG; \
527 CACHE = bidi_shelve_cache (); \
528 } while (0)
529
530 #define RESTORE_IT(pITORIG,pITCOPY,CACHE) \
531 do { \
532 if (pITORIG != pITCOPY) \
533 *(pITORIG) = *(pITCOPY); \
534 bidi_unshelve_cache (CACHE, 0); \
535 CACHE = NULL; \
536 } while (0)
537
538 /* Functions to mark elements as needing redisplay. */
539 enum { REDISPLAY_SOME = 2}; /* Arbitrary choice. */
540
541 void
542 redisplay_other_windows (void)
543 {
544 if (!windows_or_buffers_changed)
545 windows_or_buffers_changed = REDISPLAY_SOME;
546 }
547
548 void
549 wset_redisplay (struct window *w)
550 {
551 /* Beware: selected_window can be nil during early stages. */
552 if (!EQ (make_lisp_ptr (w, Lisp_Vectorlike), selected_window))
553 redisplay_other_windows ();
554 w->redisplay = true;
555 }
556
557 void
558 fset_redisplay (struct frame *f)
559 {
560 redisplay_other_windows ();
561 f->redisplay = true;
562 }
563
564 void
565 bset_redisplay (struct buffer *b)
566 {
567 int count = buffer_window_count (b);
568 if (count > 0)
569 {
570 /* ... it's visible in other window than selected, */
571 if (count > 1 || b != XBUFFER (XWINDOW (selected_window)->contents))
572 redisplay_other_windows ();
573 /* Even if we don't set windows_or_buffers_changed, do set `redisplay'
574 so that if we later set windows_or_buffers_changed, this buffer will
575 not be omitted. */
576 b->text->redisplay = true;
577 }
578 }
579
580 void
581 bset_update_mode_line (struct buffer *b)
582 {
583 if (!update_mode_lines)
584 update_mode_lines = REDISPLAY_SOME;
585 b->text->redisplay = true;
586 }
587
588 #ifdef GLYPH_DEBUG
589
590 /* Non-zero means print traces of redisplay if compiled with
591 GLYPH_DEBUG defined. */
592
593 bool trace_redisplay_p;
594
595 #endif /* GLYPH_DEBUG */
596
597 #ifdef DEBUG_TRACE_MOVE
598 /* Non-zero means trace with TRACE_MOVE to stderr. */
599 int trace_move;
600
601 #define TRACE_MOVE(x) if (trace_move) fprintf x; else (void) 0
602 #else
603 #define TRACE_MOVE(x) (void) 0
604 #endif
605
606 /* Buffer being redisplayed -- for redisplay_window_error. */
607
608 static struct buffer *displayed_buffer;
609
610 /* Value returned from text property handlers (see below). */
611
612 enum prop_handled
613 {
614 HANDLED_NORMALLY,
615 HANDLED_RECOMPUTE_PROPS,
616 HANDLED_OVERLAY_STRING_CONSUMED,
617 HANDLED_RETURN
618 };
619
620 /* A description of text properties that redisplay is interested
621 in. */
622
623 struct props
624 {
625 /* The symbol index of the name of the property. */
626 short name;
627
628 /* A unique index for the property. */
629 enum prop_idx idx;
630
631 /* A handler function called to set up iterator IT from the property
632 at IT's current position. Value is used to steer handle_stop. */
633 enum prop_handled (*handler) (struct it *it);
634 };
635
636 static enum prop_handled handle_face_prop (struct it *);
637 static enum prop_handled handle_invisible_prop (struct it *);
638 static enum prop_handled handle_display_prop (struct it *);
639 static enum prop_handled handle_composition_prop (struct it *);
640 static enum prop_handled handle_overlay_change (struct it *);
641 static enum prop_handled handle_fontified_prop (struct it *);
642
643 /* Properties handled by iterators. */
644
645 static struct props it_props[] =
646 {
647 {SYMBOL_INDEX (Qfontified), FONTIFIED_PROP_IDX, handle_fontified_prop},
648 /* Handle `face' before `display' because some sub-properties of
649 `display' need to know the face. */
650 {SYMBOL_INDEX (Qface), FACE_PROP_IDX, handle_face_prop},
651 {SYMBOL_INDEX (Qdisplay), DISPLAY_PROP_IDX, handle_display_prop},
652 {SYMBOL_INDEX (Qinvisible), INVISIBLE_PROP_IDX, handle_invisible_prop},
653 {SYMBOL_INDEX (Qcomposition), COMPOSITION_PROP_IDX, handle_composition_prop},
654 {0, 0, NULL}
655 };
656
657 /* Value is the position described by X. If X is a marker, value is
658 the marker_position of X. Otherwise, value is X. */
659
660 #define COERCE_MARKER(X) (MARKERP ((X)) ? Fmarker_position (X) : (X))
661
662 /* Enumeration returned by some move_it_.* functions internally. */
663
664 enum move_it_result
665 {
666 /* Not used. Undefined value. */
667 MOVE_UNDEFINED,
668
669 /* Move ended at the requested buffer position or ZV. */
670 MOVE_POS_MATCH_OR_ZV,
671
672 /* Move ended at the requested X pixel position. */
673 MOVE_X_REACHED,
674
675 /* Move within a line ended at the end of a line that must be
676 continued. */
677 MOVE_LINE_CONTINUED,
678
679 /* Move within a line ended at the end of a line that would
680 be displayed truncated. */
681 MOVE_LINE_TRUNCATED,
682
683 /* Move within a line ended at a line end. */
684 MOVE_NEWLINE_OR_CR
685 };
686
687 /* This counter is used to clear the face cache every once in a while
688 in redisplay_internal. It is incremented for each redisplay.
689 Every CLEAR_FACE_CACHE_COUNT full redisplays, the face cache is
690 cleared. */
691
692 #define CLEAR_FACE_CACHE_COUNT 500
693 static int clear_face_cache_count;
694
695 /* Similarly for the image cache. */
696
697 #ifdef HAVE_WINDOW_SYSTEM
698 #define CLEAR_IMAGE_CACHE_COUNT 101
699 static int clear_image_cache_count;
700
701 /* Null glyph slice */
702 static struct glyph_slice null_glyph_slice = { 0, 0, 0, 0 };
703 #endif
704
705 /* True while redisplay_internal is in progress. */
706
707 bool redisplaying_p;
708
709 /* If a string, XTread_socket generates an event to display that string.
710 (The display is done in read_char.) */
711
712 Lisp_Object help_echo_string;
713 Lisp_Object help_echo_window;
714 Lisp_Object help_echo_object;
715 ptrdiff_t help_echo_pos;
716
717 /* Temporary variable for XTread_socket. */
718
719 Lisp_Object previous_help_echo_string;
720
721 /* Platform-independent portion of hourglass implementation. */
722
723 #ifdef HAVE_WINDOW_SYSTEM
724
725 /* Non-zero means an hourglass cursor is currently shown. */
726 static bool hourglass_shown_p;
727
728 /* If non-null, an asynchronous timer that, when it expires, displays
729 an hourglass cursor on all frames. */
730 static struct atimer *hourglass_atimer;
731
732 #endif /* HAVE_WINDOW_SYSTEM */
733
734 /* Default number of seconds to wait before displaying an hourglass
735 cursor. */
736 #define DEFAULT_HOURGLASS_DELAY 1
737
738 #ifdef HAVE_WINDOW_SYSTEM
739
740 /* Default pixel width of `thin-space' display method. */
741 #define THIN_SPACE_WIDTH 1
742
743 #endif /* HAVE_WINDOW_SYSTEM */
744
745 /* Function prototypes. */
746
747 static void setup_for_ellipsis (struct it *, int);
748 static void set_iterator_to_next (struct it *, int);
749 static void mark_window_display_accurate_1 (struct window *, int);
750 static int single_display_spec_string_p (Lisp_Object, Lisp_Object);
751 static int display_prop_string_p (Lisp_Object, Lisp_Object);
752 static int row_for_charpos_p (struct glyph_row *, ptrdiff_t);
753 static int cursor_row_p (struct glyph_row *);
754 static int redisplay_mode_lines (Lisp_Object, bool);
755 static char *decode_mode_spec_coding (Lisp_Object, char *, int);
756
757 static Lisp_Object get_it_property (struct it *it, Lisp_Object prop);
758
759 static void handle_line_prefix (struct it *);
760
761 static void pint2str (char *, int, ptrdiff_t);
762 static void pint2hrstr (char *, int, ptrdiff_t);
763 static struct text_pos run_window_scroll_functions (Lisp_Object,
764 struct text_pos);
765 static int text_outside_line_unchanged_p (struct window *,
766 ptrdiff_t, ptrdiff_t);
767 static void store_mode_line_noprop_char (char);
768 static int store_mode_line_noprop (const char *, int, int);
769 static void handle_stop (struct it *);
770 static void handle_stop_backwards (struct it *, ptrdiff_t);
771 static void vmessage (const char *, va_list) ATTRIBUTE_FORMAT_PRINTF (1, 0);
772 static void ensure_echo_area_buffers (void);
773 static void unwind_with_echo_area_buffer (Lisp_Object);
774 static Lisp_Object with_echo_area_buffer_unwind_data (struct window *);
775 static int with_echo_area_buffer (struct window *, int,
776 int (*) (ptrdiff_t, Lisp_Object),
777 ptrdiff_t, Lisp_Object);
778 static void clear_garbaged_frames (void);
779 static int current_message_1 (ptrdiff_t, Lisp_Object);
780 static int truncate_message_1 (ptrdiff_t, Lisp_Object);
781 static void set_message (Lisp_Object);
782 static int set_message_1 (ptrdiff_t, Lisp_Object);
783 static int display_echo_area (struct window *);
784 static int display_echo_area_1 (ptrdiff_t, Lisp_Object);
785 static int resize_mini_window_1 (ptrdiff_t, Lisp_Object);
786 static void unwind_redisplay (void);
787 static int string_char_and_length (const unsigned char *, int *);
788 static struct text_pos display_prop_end (struct it *, Lisp_Object,
789 struct text_pos);
790 static int compute_window_start_on_continuation_line (struct window *);
791 static void insert_left_trunc_glyphs (struct it *);
792 static struct glyph_row *get_overlay_arrow_glyph_row (struct window *,
793 Lisp_Object);
794 static void extend_face_to_end_of_line (struct it *);
795 static int append_space_for_newline (struct it *, int);
796 static int cursor_row_fully_visible_p (struct window *, int, int);
797 static int try_scrolling (Lisp_Object, int, ptrdiff_t, ptrdiff_t, int, int);
798 static int try_cursor_movement (Lisp_Object, struct text_pos, int *);
799 static int trailing_whitespace_p (ptrdiff_t);
800 static intmax_t message_log_check_duplicate (ptrdiff_t, ptrdiff_t);
801 static void push_it (struct it *, struct text_pos *);
802 static void iterate_out_of_display_property (struct it *);
803 static void pop_it (struct it *);
804 static void sync_frame_with_window_matrix_rows (struct window *);
805 static void redisplay_internal (void);
806 static bool echo_area_display (bool);
807 static void redisplay_windows (Lisp_Object);
808 static void redisplay_window (Lisp_Object, bool);
809 static Lisp_Object redisplay_window_error (Lisp_Object);
810 static Lisp_Object redisplay_window_0 (Lisp_Object);
811 static Lisp_Object redisplay_window_1 (Lisp_Object);
812 static int set_cursor_from_row (struct window *, struct glyph_row *,
813 struct glyph_matrix *, ptrdiff_t, ptrdiff_t,
814 int, int);
815 static int update_menu_bar (struct frame *, int, int);
816 static int try_window_reusing_current_matrix (struct window *);
817 static int try_window_id (struct window *);
818 static int display_line (struct it *);
819 static int display_mode_lines (struct window *);
820 static int display_mode_line (struct window *, enum face_id, Lisp_Object);
821 static int display_mode_element (struct it *, int, int, int, Lisp_Object, Lisp_Object, int);
822 static int store_mode_line_string (const char *, Lisp_Object, int, int, int, Lisp_Object);
823 static const char *decode_mode_spec (struct window *, int, int, Lisp_Object *);
824 static void display_menu_bar (struct window *);
825 static ptrdiff_t display_count_lines (ptrdiff_t, ptrdiff_t, ptrdiff_t,
826 ptrdiff_t *);
827 static int display_string (const char *, Lisp_Object, Lisp_Object,
828 ptrdiff_t, ptrdiff_t, struct it *, int, int, int, int);
829 static void compute_line_metrics (struct it *);
830 static void run_redisplay_end_trigger_hook (struct it *);
831 static int get_overlay_strings (struct it *, ptrdiff_t);
832 static int get_overlay_strings_1 (struct it *, ptrdiff_t, int);
833 static void next_overlay_string (struct it *);
834 static void reseat (struct it *, struct text_pos, int);
835 static void reseat_1 (struct it *, struct text_pos, int);
836 static void back_to_previous_visible_line_start (struct it *);
837 static void reseat_at_next_visible_line_start (struct it *, int);
838 static int next_element_from_ellipsis (struct it *);
839 static int next_element_from_display_vector (struct it *);
840 static int next_element_from_string (struct it *);
841 static int next_element_from_c_string (struct it *);
842 static int next_element_from_buffer (struct it *);
843 static int next_element_from_composition (struct it *);
844 static int next_element_from_image (struct it *);
845 static int next_element_from_stretch (struct it *);
846 static void load_overlay_strings (struct it *, ptrdiff_t);
847 static int init_from_display_pos (struct it *, struct window *,
848 struct display_pos *);
849 static void reseat_to_string (struct it *, const char *,
850 Lisp_Object, ptrdiff_t, ptrdiff_t, int, int);
851 static int get_next_display_element (struct it *);
852 static enum move_it_result
853 move_it_in_display_line_to (struct it *, ptrdiff_t, int,
854 enum move_operation_enum);
855 static void get_visually_first_element (struct it *);
856 static void init_to_row_start (struct it *, struct window *,
857 struct glyph_row *);
858 static int init_to_row_end (struct it *, struct window *,
859 struct glyph_row *);
860 static void back_to_previous_line_start (struct it *);
861 static int forward_to_next_line_start (struct it *, int *, struct bidi_it *);
862 static struct text_pos string_pos_nchars_ahead (struct text_pos,
863 Lisp_Object, ptrdiff_t);
864 static struct text_pos string_pos (ptrdiff_t, Lisp_Object);
865 static struct text_pos c_string_pos (ptrdiff_t, const char *, bool);
866 static ptrdiff_t number_of_chars (const char *, bool);
867 static void compute_stop_pos (struct it *);
868 static void compute_string_pos (struct text_pos *, struct text_pos,
869 Lisp_Object);
870 static int face_before_or_after_it_pos (struct it *, int);
871 static ptrdiff_t next_overlay_change (ptrdiff_t);
872 static int handle_display_spec (struct it *, Lisp_Object, Lisp_Object,
873 Lisp_Object, struct text_pos *, ptrdiff_t, int);
874 static int handle_single_display_spec (struct it *, Lisp_Object,
875 Lisp_Object, Lisp_Object,
876 struct text_pos *, ptrdiff_t, int, int);
877 static int underlying_face_id (struct it *);
878 static int in_ellipses_for_invisible_text_p (struct display_pos *,
879 struct window *);
880
881 #define face_before_it_pos(IT) face_before_or_after_it_pos ((IT), 1)
882 #define face_after_it_pos(IT) face_before_or_after_it_pos ((IT), 0)
883
884 #ifdef HAVE_WINDOW_SYSTEM
885
886 static void x_consider_frame_title (Lisp_Object);
887 static void update_tool_bar (struct frame *, int);
888 static int redisplay_tool_bar (struct frame *);
889 static void x_draw_bottom_divider (struct window *w);
890 static void notice_overwritten_cursor (struct window *,
891 enum glyph_row_area,
892 int, int, int, int);
893 static void append_stretch_glyph (struct it *, Lisp_Object,
894 int, int, int);
895
896
897 #endif /* HAVE_WINDOW_SYSTEM */
898
899 static void produce_special_glyphs (struct it *, enum display_element_type);
900 static void show_mouse_face (Mouse_HLInfo *, enum draw_glyphs_face);
901 static bool coords_in_mouse_face_p (struct window *, int, int);
902
903
904 \f
905 /***********************************************************************
906 Window display dimensions
907 ***********************************************************************/
908
909 /* Return the bottom boundary y-position for text lines in window W.
910 This is the first y position at which a line cannot start.
911 It is relative to the top of the window.
912
913 This is the height of W minus the height of a mode line, if any. */
914
915 int
916 window_text_bottom_y (struct window *w)
917 {
918 int height = WINDOW_PIXEL_HEIGHT (w);
919
920 height -= WINDOW_BOTTOM_DIVIDER_WIDTH (w);
921
922 if (WINDOW_WANTS_MODELINE_P (w))
923 height -= CURRENT_MODE_LINE_HEIGHT (w);
924
925 height -= WINDOW_SCROLL_BAR_AREA_HEIGHT (w);
926
927 return height;
928 }
929
930 /* Return the pixel width of display area AREA of window W.
931 ANY_AREA means return the total width of W, not including
932 fringes to the left and right of the window. */
933
934 int
935 window_box_width (struct window *w, enum glyph_row_area area)
936 {
937 int width = w->pixel_width;
938
939 if (!w->pseudo_window_p)
940 {
941 width -= WINDOW_SCROLL_BAR_AREA_WIDTH (w);
942 width -= WINDOW_RIGHT_DIVIDER_WIDTH (w);
943
944 if (area == TEXT_AREA)
945 width -= (WINDOW_MARGINS_WIDTH (w)
946 + WINDOW_FRINGES_WIDTH (w));
947 else if (area == LEFT_MARGIN_AREA)
948 width = WINDOW_LEFT_MARGIN_WIDTH (w);
949 else if (area == RIGHT_MARGIN_AREA)
950 width = WINDOW_RIGHT_MARGIN_WIDTH (w);
951 }
952
953 /* With wide margins, fringes, etc. we might end up with a negative
954 width, correct that here. */
955 return max (0, width);
956 }
957
958
959 /* Return the pixel height of the display area of window W, not
960 including mode lines of W, if any. */
961
962 int
963 window_box_height (struct window *w)
964 {
965 struct frame *f = XFRAME (w->frame);
966 int height = WINDOW_PIXEL_HEIGHT (w);
967
968 eassert (height >= 0);
969
970 height -= WINDOW_BOTTOM_DIVIDER_WIDTH (w);
971 height -= WINDOW_SCROLL_BAR_AREA_HEIGHT (w);
972
973 /* Note: the code below that determines the mode-line/header-line
974 height is essentially the same as that contained in the macro
975 CURRENT_{MODE,HEADER}_LINE_HEIGHT, except that it checks whether
976 the appropriate glyph row has its `mode_line_p' flag set,
977 and if it doesn't, uses estimate_mode_line_height instead. */
978
979 if (WINDOW_WANTS_MODELINE_P (w))
980 {
981 struct glyph_row *ml_row
982 = (w->current_matrix && w->current_matrix->rows
983 ? MATRIX_MODE_LINE_ROW (w->current_matrix)
984 : 0);
985 if (ml_row && ml_row->mode_line_p)
986 height -= ml_row->height;
987 else
988 height -= estimate_mode_line_height (f, CURRENT_MODE_LINE_FACE_ID (w));
989 }
990
991 if (WINDOW_WANTS_HEADER_LINE_P (w))
992 {
993 struct glyph_row *hl_row
994 = (w->current_matrix && w->current_matrix->rows
995 ? MATRIX_HEADER_LINE_ROW (w->current_matrix)
996 : 0);
997 if (hl_row && hl_row->mode_line_p)
998 height -= hl_row->height;
999 else
1000 height -= estimate_mode_line_height (f, HEADER_LINE_FACE_ID);
1001 }
1002
1003 /* With a very small font and a mode-line that's taller than
1004 default, we might end up with a negative height. */
1005 return max (0, height);
1006 }
1007
1008 /* Return the window-relative coordinate of the left edge of display
1009 area AREA of window W. ANY_AREA means return the left edge of the
1010 whole window, to the right of the left fringe of W. */
1011
1012 int
1013 window_box_left_offset (struct window *w, enum glyph_row_area area)
1014 {
1015 int x;
1016
1017 if (w->pseudo_window_p)
1018 return 0;
1019
1020 x = WINDOW_LEFT_SCROLL_BAR_AREA_WIDTH (w);
1021
1022 if (area == TEXT_AREA)
1023 x += (WINDOW_LEFT_FRINGE_WIDTH (w)
1024 + window_box_width (w, LEFT_MARGIN_AREA));
1025 else if (area == RIGHT_MARGIN_AREA)
1026 x += (WINDOW_LEFT_FRINGE_WIDTH (w)
1027 + window_box_width (w, LEFT_MARGIN_AREA)
1028 + window_box_width (w, TEXT_AREA)
1029 + (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
1030 ? 0
1031 : WINDOW_RIGHT_FRINGE_WIDTH (w)));
1032 else if (area == LEFT_MARGIN_AREA
1033 && WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w))
1034 x += WINDOW_LEFT_FRINGE_WIDTH (w);
1035
1036 /* Don't return more than the window's pixel width. */
1037 return min (x, w->pixel_width);
1038 }
1039
1040
1041 /* Return the window-relative coordinate of the right edge of display
1042 area AREA of window W. ANY_AREA means return the right edge of the
1043 whole window, to the left of the right fringe of W. */
1044
1045 static int
1046 window_box_right_offset (struct window *w, enum glyph_row_area area)
1047 {
1048 /* Don't return more than the window's pixel width. */
1049 return min (window_box_left_offset (w, area) + window_box_width (w, area),
1050 w->pixel_width);
1051 }
1052
1053 /* Return the frame-relative coordinate of the left edge of display
1054 area AREA of window W. ANY_AREA means return the left edge of the
1055 whole window, to the right of the left fringe of W. */
1056
1057 int
1058 window_box_left (struct window *w, enum glyph_row_area area)
1059 {
1060 struct frame *f = XFRAME (w->frame);
1061 int x;
1062
1063 if (w->pseudo_window_p)
1064 return FRAME_INTERNAL_BORDER_WIDTH (f);
1065
1066 x = (WINDOW_LEFT_EDGE_X (w)
1067 + window_box_left_offset (w, area));
1068
1069 return x;
1070 }
1071
1072
1073 /* Return the frame-relative coordinate of the right edge of display
1074 area AREA of window W. ANY_AREA means return the right edge of the
1075 whole window, to the left of the right fringe of W. */
1076
1077 int
1078 window_box_right (struct window *w, enum glyph_row_area area)
1079 {
1080 return window_box_left (w, area) + window_box_width (w, area);
1081 }
1082
1083 /* Get the bounding box of the display area AREA of window W, without
1084 mode lines, in frame-relative coordinates. ANY_AREA means the
1085 whole window, not including the left and right fringes of
1086 the window. Return in *BOX_X and *BOX_Y the frame-relative pixel
1087 coordinates of the upper-left corner of the box. Return in
1088 *BOX_WIDTH, and *BOX_HEIGHT the pixel width and height of the box. */
1089
1090 void
1091 window_box (struct window *w, enum glyph_row_area area, int *box_x,
1092 int *box_y, int *box_width, int *box_height)
1093 {
1094 if (box_width)
1095 *box_width = window_box_width (w, area);
1096 if (box_height)
1097 *box_height = window_box_height (w);
1098 if (box_x)
1099 *box_x = window_box_left (w, area);
1100 if (box_y)
1101 {
1102 *box_y = WINDOW_TOP_EDGE_Y (w);
1103 if (WINDOW_WANTS_HEADER_LINE_P (w))
1104 *box_y += CURRENT_HEADER_LINE_HEIGHT (w);
1105 }
1106 }
1107
1108 #ifdef HAVE_WINDOW_SYSTEM
1109
1110 /* Get the bounding box of the display area AREA of window W, without
1111 mode lines and both fringes of the window. Return in *TOP_LEFT_X
1112 and TOP_LEFT_Y the frame-relative pixel coordinates of the
1113 upper-left corner of the box. Return in *BOTTOM_RIGHT_X, and
1114 *BOTTOM_RIGHT_Y the coordinates of the bottom-right corner of the
1115 box. */
1116
1117 static void
1118 window_box_edges (struct window *w, int *top_left_x, int *top_left_y,
1119 int *bottom_right_x, int *bottom_right_y)
1120 {
1121 window_box (w, ANY_AREA, top_left_x, top_left_y,
1122 bottom_right_x, bottom_right_y);
1123 *bottom_right_x += *top_left_x;
1124 *bottom_right_y += *top_left_y;
1125 }
1126
1127 #endif /* HAVE_WINDOW_SYSTEM */
1128
1129 /***********************************************************************
1130 Utilities
1131 ***********************************************************************/
1132
1133 /* Return the bottom y-position of the line the iterator IT is in.
1134 This can modify IT's settings. */
1135
1136 int
1137 line_bottom_y (struct it *it)
1138 {
1139 int line_height = it->max_ascent + it->max_descent;
1140 int line_top_y = it->current_y;
1141
1142 if (line_height == 0)
1143 {
1144 if (last_height)
1145 line_height = last_height;
1146 else if (IT_CHARPOS (*it) < ZV)
1147 {
1148 move_it_by_lines (it, 1);
1149 line_height = (it->max_ascent || it->max_descent
1150 ? it->max_ascent + it->max_descent
1151 : last_height);
1152 }
1153 else
1154 {
1155 struct glyph_row *row = it->glyph_row;
1156
1157 /* Use the default character height. */
1158 it->glyph_row = NULL;
1159 it->what = IT_CHARACTER;
1160 it->c = ' ';
1161 it->len = 1;
1162 PRODUCE_GLYPHS (it);
1163 line_height = it->ascent + it->descent;
1164 it->glyph_row = row;
1165 }
1166 }
1167
1168 return line_top_y + line_height;
1169 }
1170
1171 DEFUN ("line-pixel-height", Fline_pixel_height,
1172 Sline_pixel_height, 0, 0, 0,
1173 doc: /* Return height in pixels of text line in the selected window.
1174
1175 Value is the height in pixels of the line at point. */)
1176 (void)
1177 {
1178 struct it it;
1179 struct text_pos pt;
1180 struct window *w = XWINDOW (selected_window);
1181 struct buffer *old_buffer = NULL;
1182 Lisp_Object result;
1183
1184 if (XBUFFER (w->contents) != current_buffer)
1185 {
1186 old_buffer = current_buffer;
1187 set_buffer_internal_1 (XBUFFER (w->contents));
1188 }
1189 SET_TEXT_POS (pt, PT, PT_BYTE);
1190 start_display (&it, w, pt);
1191 it.vpos = it.current_y = 0;
1192 last_height = 0;
1193 result = make_number (line_bottom_y (&it));
1194 if (old_buffer)
1195 set_buffer_internal_1 (old_buffer);
1196
1197 return result;
1198 }
1199
1200 /* Return the default pixel height of text lines in window W. The
1201 value is the canonical height of the W frame's default font, plus
1202 any extra space required by the line-spacing variable or frame
1203 parameter.
1204
1205 Implementation note: this ignores any line-spacing text properties
1206 put on the newline characters. This is because those properties
1207 only affect the _screen_ line ending in the newline (i.e., in a
1208 continued line, only the last screen line will be affected), which
1209 means only a small number of lines in a buffer can ever use this
1210 feature. Since this function is used to compute the default pixel
1211 equivalent of text lines in a window, we can safely ignore those
1212 few lines. For the same reasons, we ignore the line-height
1213 properties. */
1214 int
1215 default_line_pixel_height (struct window *w)
1216 {
1217 struct frame *f = WINDOW_XFRAME (w);
1218 int height = FRAME_LINE_HEIGHT (f);
1219
1220 if (!FRAME_INITIAL_P (f) && BUFFERP (w->contents))
1221 {
1222 struct buffer *b = XBUFFER (w->contents);
1223 Lisp_Object val = BVAR (b, extra_line_spacing);
1224
1225 if (NILP (val))
1226 val = BVAR (&buffer_defaults, extra_line_spacing);
1227 if (!NILP (val))
1228 {
1229 if (RANGED_INTEGERP (0, val, INT_MAX))
1230 height += XFASTINT (val);
1231 else if (FLOATP (val))
1232 {
1233 int addon = XFLOAT_DATA (val) * height + 0.5;
1234
1235 if (addon >= 0)
1236 height += addon;
1237 }
1238 }
1239 else
1240 height += f->extra_line_spacing;
1241 }
1242
1243 return height;
1244 }
1245
1246 /* Subroutine of pos_visible_p below. Extracts a display string, if
1247 any, from the display spec given as its argument. */
1248 static Lisp_Object
1249 string_from_display_spec (Lisp_Object spec)
1250 {
1251 if (CONSP (spec))
1252 {
1253 while (CONSP (spec))
1254 {
1255 if (STRINGP (XCAR (spec)))
1256 return XCAR (spec);
1257 spec = XCDR (spec);
1258 }
1259 }
1260 else if (VECTORP (spec))
1261 {
1262 ptrdiff_t i;
1263
1264 for (i = 0; i < ASIZE (spec); i++)
1265 {
1266 if (STRINGP (AREF (spec, i)))
1267 return AREF (spec, i);
1268 }
1269 return Qnil;
1270 }
1271
1272 return spec;
1273 }
1274
1275
1276 /* Limit insanely large values of W->hscroll on frame F to the largest
1277 value that will still prevent first_visible_x and last_visible_x of
1278 'struct it' from overflowing an int. */
1279 static int
1280 window_hscroll_limited (struct window *w, struct frame *f)
1281 {
1282 ptrdiff_t window_hscroll = w->hscroll;
1283 int window_text_width = window_box_width (w, TEXT_AREA);
1284 int colwidth = FRAME_COLUMN_WIDTH (f);
1285
1286 if (window_hscroll > (INT_MAX - window_text_width) / colwidth - 1)
1287 window_hscroll = (INT_MAX - window_text_width) / colwidth - 1;
1288
1289 return window_hscroll;
1290 }
1291
1292 /* Return 1 if position CHARPOS is visible in window W.
1293 CHARPOS < 0 means return info about WINDOW_END position.
1294 If visible, set *X and *Y to pixel coordinates of top left corner.
1295 Set *RTOP and *RBOT to pixel height of an invisible area of glyph at POS.
1296 Set *ROWH and *VPOS to row's visible height and VPOS (row number). */
1297
1298 int
1299 pos_visible_p (struct window *w, ptrdiff_t charpos, int *x, int *y,
1300 int *rtop, int *rbot, int *rowh, int *vpos)
1301 {
1302 struct it it;
1303 void *itdata = bidi_shelve_cache ();
1304 struct text_pos top;
1305 int visible_p = 0;
1306 struct buffer *old_buffer = NULL;
1307 bool r2l = false;
1308
1309 if (FRAME_INITIAL_P (XFRAME (WINDOW_FRAME (w))))
1310 return visible_p;
1311
1312 if (XBUFFER (w->contents) != current_buffer)
1313 {
1314 old_buffer = current_buffer;
1315 set_buffer_internal_1 (XBUFFER (w->contents));
1316 }
1317
1318 SET_TEXT_POS_FROM_MARKER (top, w->start);
1319 /* Scrolling a minibuffer window via scroll bar when the echo area
1320 shows long text sometimes resets the minibuffer contents behind
1321 our backs. */
1322 if (CHARPOS (top) > ZV)
1323 SET_TEXT_POS (top, BEGV, BEGV_BYTE);
1324
1325 /* Compute exact mode line heights. */
1326 if (WINDOW_WANTS_MODELINE_P (w))
1327 w->mode_line_height
1328 = display_mode_line (w, CURRENT_MODE_LINE_FACE_ID (w),
1329 BVAR (current_buffer, mode_line_format));
1330
1331 if (WINDOW_WANTS_HEADER_LINE_P (w))
1332 w->header_line_height
1333 = display_mode_line (w, HEADER_LINE_FACE_ID,
1334 BVAR (current_buffer, header_line_format));
1335
1336 start_display (&it, w, top);
1337 move_it_to (&it, charpos, -1, it.last_visible_y - 1, -1,
1338 (charpos >= 0 ? MOVE_TO_POS : 0) | MOVE_TO_Y);
1339
1340 if (charpos >= 0
1341 && (((!it.bidi_p || it.bidi_it.scan_dir != -1)
1342 && IT_CHARPOS (it) >= charpos)
1343 /* When scanning backwards under bidi iteration, move_it_to
1344 stops at or _before_ CHARPOS, because it stops at or to
1345 the _right_ of the character at CHARPOS. */
1346 || (it.bidi_p && it.bidi_it.scan_dir == -1
1347 && IT_CHARPOS (it) <= charpos)))
1348 {
1349 /* We have reached CHARPOS, or passed it. How the call to
1350 move_it_to can overshoot: (i) If CHARPOS is on invisible text
1351 or covered by a display property, move_it_to stops at the end
1352 of the invisible text, to the right of CHARPOS. (ii) If
1353 CHARPOS is in a display vector, move_it_to stops on its last
1354 glyph. */
1355 int top_x = it.current_x;
1356 int top_y = it.current_y;
1357 int window_top_y = WINDOW_HEADER_LINE_HEIGHT (w);
1358 int bottom_y;
1359 struct it save_it;
1360 void *save_it_data = NULL;
1361
1362 /* Calling line_bottom_y may change it.method, it.position, etc. */
1363 SAVE_IT (save_it, it, save_it_data);
1364 last_height = 0;
1365 bottom_y = line_bottom_y (&it);
1366 if (top_y < window_top_y)
1367 visible_p = bottom_y > window_top_y;
1368 else if (top_y < it.last_visible_y)
1369 visible_p = 1;
1370 if (bottom_y >= it.last_visible_y
1371 && it.bidi_p && it.bidi_it.scan_dir == -1
1372 && IT_CHARPOS (it) < charpos)
1373 {
1374 /* When the last line of the window is scanned backwards
1375 under bidi iteration, we could be duped into thinking
1376 that we have passed CHARPOS, when in fact move_it_to
1377 simply stopped short of CHARPOS because it reached
1378 last_visible_y. To see if that's what happened, we call
1379 move_it_to again with a slightly larger vertical limit,
1380 and see if it actually moved vertically; if it did, we
1381 didn't really reach CHARPOS, which is beyond window end. */
1382 /* Why 10? because we don't know how many canonical lines
1383 will the height of the next line(s) be. So we guess. */
1384 int ten_more_lines = 10 * default_line_pixel_height (w);
1385
1386 move_it_to (&it, charpos, -1, bottom_y + ten_more_lines, -1,
1387 MOVE_TO_POS | MOVE_TO_Y);
1388 if (it.current_y > top_y)
1389 visible_p = 0;
1390
1391 }
1392 RESTORE_IT (&it, &save_it, save_it_data);
1393 if (visible_p)
1394 {
1395 if (it.method == GET_FROM_DISPLAY_VECTOR)
1396 {
1397 /* We stopped on the last glyph of a display vector.
1398 Try and recompute. Hack alert! */
1399 if (charpos < 2 || top.charpos >= charpos)
1400 top_x = it.glyph_row->x;
1401 else
1402 {
1403 struct it it2, it2_prev;
1404 /* The idea is to get to the previous buffer
1405 position, consume the character there, and use
1406 the pixel coordinates we get after that. But if
1407 the previous buffer position is also displayed
1408 from a display vector, we need to consume all of
1409 the glyphs from that display vector. */
1410 start_display (&it2, w, top);
1411 move_it_to (&it2, charpos - 1, -1, -1, -1, MOVE_TO_POS);
1412 /* If we didn't get to CHARPOS - 1, there's some
1413 replacing display property at that position, and
1414 we stopped after it. That is exactly the place
1415 whose coordinates we want. */
1416 if (IT_CHARPOS (it2) != charpos - 1)
1417 it2_prev = it2;
1418 else
1419 {
1420 /* Iterate until we get out of the display
1421 vector that displays the character at
1422 CHARPOS - 1. */
1423 do {
1424 get_next_display_element (&it2);
1425 PRODUCE_GLYPHS (&it2);
1426 it2_prev = it2;
1427 set_iterator_to_next (&it2, 1);
1428 } while (it2.method == GET_FROM_DISPLAY_VECTOR
1429 && IT_CHARPOS (it2) < charpos);
1430 }
1431 if (ITERATOR_AT_END_OF_LINE_P (&it2_prev)
1432 || it2_prev.current_x > it2_prev.last_visible_x)
1433 top_x = it.glyph_row->x;
1434 else
1435 {
1436 top_x = it2_prev.current_x;
1437 top_y = it2_prev.current_y;
1438 }
1439 }
1440 }
1441 else if (IT_CHARPOS (it) != charpos)
1442 {
1443 Lisp_Object cpos = make_number (charpos);
1444 Lisp_Object spec = Fget_char_property (cpos, Qdisplay, Qnil);
1445 Lisp_Object string = string_from_display_spec (spec);
1446 struct text_pos tpos;
1447 int replacing_spec_p;
1448 bool newline_in_string
1449 = (STRINGP (string)
1450 && memchr (SDATA (string), '\n', SBYTES (string)));
1451
1452 SET_TEXT_POS (tpos, charpos, CHAR_TO_BYTE (charpos));
1453 replacing_spec_p
1454 = (!NILP (spec)
1455 && handle_display_spec (NULL, spec, Qnil, Qnil, &tpos,
1456 charpos, FRAME_WINDOW_P (it.f)));
1457 /* The tricky code below is needed because there's a
1458 discrepancy between move_it_to and how we set cursor
1459 when PT is at the beginning of a portion of text
1460 covered by a display property or an overlay with a
1461 display property, or the display line ends in a
1462 newline from a display string. move_it_to will stop
1463 _after_ such display strings, whereas
1464 set_cursor_from_row conspires with cursor_row_p to
1465 place the cursor on the first glyph produced from the
1466 display string. */
1467
1468 /* We have overshoot PT because it is covered by a
1469 display property that replaces the text it covers.
1470 If the string includes embedded newlines, we are also
1471 in the wrong display line. Backtrack to the correct
1472 line, where the display property begins. */
1473 if (replacing_spec_p)
1474 {
1475 Lisp_Object startpos, endpos;
1476 EMACS_INT start, end;
1477 struct it it3;
1478 int it3_moved;
1479
1480 /* Find the first and the last buffer positions
1481 covered by the display string. */
1482 endpos =
1483 Fnext_single_char_property_change (cpos, Qdisplay,
1484 Qnil, Qnil);
1485 startpos =
1486 Fprevious_single_char_property_change (endpos, Qdisplay,
1487 Qnil, Qnil);
1488 start = XFASTINT (startpos);
1489 end = XFASTINT (endpos);
1490 /* Move to the last buffer position before the
1491 display property. */
1492 start_display (&it3, w, top);
1493 if (start > CHARPOS (top))
1494 move_it_to (&it3, start - 1, -1, -1, -1, MOVE_TO_POS);
1495 /* Move forward one more line if the position before
1496 the display string is a newline or if it is the
1497 rightmost character on a line that is
1498 continued or word-wrapped. */
1499 if (it3.method == GET_FROM_BUFFER
1500 && (it3.c == '\n'
1501 || FETCH_BYTE (IT_BYTEPOS (it3)) == '\n'))
1502 move_it_by_lines (&it3, 1);
1503 else if (move_it_in_display_line_to (&it3, -1,
1504 it3.current_x
1505 + it3.pixel_width,
1506 MOVE_TO_X)
1507 == MOVE_LINE_CONTINUED)
1508 {
1509 move_it_by_lines (&it3, 1);
1510 /* When we are under word-wrap, the #$@%!
1511 move_it_by_lines moves 2 lines, so we need to
1512 fix that up. */
1513 if (it3.line_wrap == WORD_WRAP)
1514 move_it_by_lines (&it3, -1);
1515 }
1516
1517 /* Record the vertical coordinate of the display
1518 line where we wound up. */
1519 top_y = it3.current_y;
1520 if (it3.bidi_p)
1521 {
1522 /* When characters are reordered for display,
1523 the character displayed to the left of the
1524 display string could be _after_ the display
1525 property in the logical order. Use the
1526 smallest vertical position of these two. */
1527 start_display (&it3, w, top);
1528 move_it_to (&it3, end + 1, -1, -1, -1, MOVE_TO_POS);
1529 if (it3.current_y < top_y)
1530 top_y = it3.current_y;
1531 }
1532 /* Move from the top of the window to the beginning
1533 of the display line where the display string
1534 begins. */
1535 start_display (&it3, w, top);
1536 move_it_to (&it3, -1, 0, top_y, -1, MOVE_TO_X | MOVE_TO_Y);
1537 /* If it3_moved stays zero after the 'while' loop
1538 below, that means we already were at a newline
1539 before the loop (e.g., the display string begins
1540 with a newline), so we don't need to (and cannot)
1541 inspect the glyphs of it3.glyph_row, because
1542 PRODUCE_GLYPHS will not produce anything for a
1543 newline, and thus it3.glyph_row stays at its
1544 stale content it got at top of the window. */
1545 it3_moved = 0;
1546 /* Finally, advance the iterator until we hit the
1547 first display element whose character position is
1548 CHARPOS, or until the first newline from the
1549 display string, which signals the end of the
1550 display line. */
1551 while (get_next_display_element (&it3))
1552 {
1553 PRODUCE_GLYPHS (&it3);
1554 if (IT_CHARPOS (it3) == charpos
1555 || ITERATOR_AT_END_OF_LINE_P (&it3))
1556 break;
1557 it3_moved = 1;
1558 set_iterator_to_next (&it3, 0);
1559 }
1560 top_x = it3.current_x - it3.pixel_width;
1561 /* Normally, we would exit the above loop because we
1562 found the display element whose character
1563 position is CHARPOS. For the contingency that we
1564 didn't, and stopped at the first newline from the
1565 display string, move back over the glyphs
1566 produced from the string, until we find the
1567 rightmost glyph not from the string. */
1568 if (it3_moved
1569 && newline_in_string
1570 && IT_CHARPOS (it3) != charpos && EQ (it3.object, string))
1571 {
1572 struct glyph *g = it3.glyph_row->glyphs[TEXT_AREA]
1573 + it3.glyph_row->used[TEXT_AREA];
1574
1575 while (EQ ((g - 1)->object, string))
1576 {
1577 --g;
1578 top_x -= g->pixel_width;
1579 }
1580 eassert (g < it3.glyph_row->glyphs[TEXT_AREA]
1581 + it3.glyph_row->used[TEXT_AREA]);
1582 }
1583 }
1584 }
1585
1586 *x = top_x;
1587 *y = max (top_y + max (0, it.max_ascent - it.ascent), window_top_y);
1588 *rtop = max (0, window_top_y - top_y);
1589 *rbot = max (0, bottom_y - it.last_visible_y);
1590 *rowh = max (0, (min (bottom_y, it.last_visible_y)
1591 - max (top_y, window_top_y)));
1592 *vpos = it.vpos;
1593 if (it.bidi_it.paragraph_dir == R2L)
1594 r2l = true;
1595 }
1596 }
1597 else
1598 {
1599 /* Either we were asked to provide info about WINDOW_END, or
1600 CHARPOS is in the partially visible glyph row at end of
1601 window. */
1602 struct it it2;
1603 void *it2data = NULL;
1604
1605 SAVE_IT (it2, it, it2data);
1606 if (IT_CHARPOS (it) < ZV && FETCH_BYTE (IT_BYTEPOS (it)) != '\n')
1607 move_it_by_lines (&it, 1);
1608 if (charpos < IT_CHARPOS (it)
1609 || (it.what == IT_EOB && charpos == IT_CHARPOS (it)))
1610 {
1611 visible_p = true;
1612 RESTORE_IT (&it2, &it2, it2data);
1613 move_it_to (&it2, charpos, -1, -1, -1, MOVE_TO_POS);
1614 *x = it2.current_x;
1615 *y = it2.current_y + it2.max_ascent - it2.ascent;
1616 *rtop = max (0, -it2.current_y);
1617 *rbot = max (0, ((it2.current_y + it2.max_ascent + it2.max_descent)
1618 - it.last_visible_y));
1619 *rowh = max (0, (min (it2.current_y + it2.max_ascent + it2.max_descent,
1620 it.last_visible_y)
1621 - max (it2.current_y,
1622 WINDOW_HEADER_LINE_HEIGHT (w))));
1623 *vpos = it2.vpos;
1624 if (it2.bidi_it.paragraph_dir == R2L)
1625 r2l = true;
1626 }
1627 else
1628 bidi_unshelve_cache (it2data, 1);
1629 }
1630 bidi_unshelve_cache (itdata, 0);
1631
1632 if (old_buffer)
1633 set_buffer_internal_1 (old_buffer);
1634
1635 if (visible_p)
1636 {
1637 if (w->hscroll > 0)
1638 *x -=
1639 window_hscroll_limited (w, WINDOW_XFRAME (w))
1640 * WINDOW_FRAME_COLUMN_WIDTH (w);
1641 /* For lines in an R2L paragraph, we need to mirror the X pixel
1642 coordinate wrt the text area. For the reasons, see the
1643 commentary in buffer_posn_from_coords and the explanation of
1644 the geometry used by the move_it_* functions at the end of
1645 the large commentary near the beginning of this file. */
1646 if (r2l)
1647 *x = window_box_width (w, TEXT_AREA) - *x - 1;
1648 }
1649
1650 #if 0
1651 /* Debugging code. */
1652 if (visible_p)
1653 fprintf (stderr, "+pv pt=%d vs=%d --> x=%d y=%d rt=%d rb=%d rh=%d vp=%d\n",
1654 charpos, w->vscroll, *x, *y, *rtop, *rbot, *rowh, *vpos);
1655 else
1656 fprintf (stderr, "-pv pt=%d vs=%d\n", charpos, w->vscroll);
1657 #endif
1658
1659 return visible_p;
1660 }
1661
1662
1663 /* Return the next character from STR. Return in *LEN the length of
1664 the character. This is like STRING_CHAR_AND_LENGTH but never
1665 returns an invalid character. If we find one, we return a `?', but
1666 with the length of the invalid character. */
1667
1668 static int
1669 string_char_and_length (const unsigned char *str, int *len)
1670 {
1671 int c;
1672
1673 c = STRING_CHAR_AND_LENGTH (str, *len);
1674 if (!CHAR_VALID_P (c))
1675 /* We may not change the length here because other places in Emacs
1676 don't use this function, i.e. they silently accept invalid
1677 characters. */
1678 c = '?';
1679
1680 return c;
1681 }
1682
1683
1684
1685 /* Given a position POS containing a valid character and byte position
1686 in STRING, return the position NCHARS ahead (NCHARS >= 0). */
1687
1688 static struct text_pos
1689 string_pos_nchars_ahead (struct text_pos pos, Lisp_Object string, ptrdiff_t nchars)
1690 {
1691 eassert (STRINGP (string) && nchars >= 0);
1692
1693 if (STRING_MULTIBYTE (string))
1694 {
1695 const unsigned char *p = SDATA (string) + BYTEPOS (pos);
1696 int len;
1697
1698 while (nchars--)
1699 {
1700 string_char_and_length (p, &len);
1701 p += len;
1702 CHARPOS (pos) += 1;
1703 BYTEPOS (pos) += len;
1704 }
1705 }
1706 else
1707 SET_TEXT_POS (pos, CHARPOS (pos) + nchars, BYTEPOS (pos) + nchars);
1708
1709 return pos;
1710 }
1711
1712
1713 /* Value is the text position, i.e. character and byte position,
1714 for character position CHARPOS in STRING. */
1715
1716 static struct text_pos
1717 string_pos (ptrdiff_t charpos, Lisp_Object string)
1718 {
1719 struct text_pos pos;
1720 eassert (STRINGP (string));
1721 eassert (charpos >= 0);
1722 SET_TEXT_POS (pos, charpos, string_char_to_byte (string, charpos));
1723 return pos;
1724 }
1725
1726
1727 /* Value is a text position, i.e. character and byte position, for
1728 character position CHARPOS in C string S. MULTIBYTE_P non-zero
1729 means recognize multibyte characters. */
1730
1731 static struct text_pos
1732 c_string_pos (ptrdiff_t charpos, const char *s, bool multibyte_p)
1733 {
1734 struct text_pos pos;
1735
1736 eassert (s != NULL);
1737 eassert (charpos >= 0);
1738
1739 if (multibyte_p)
1740 {
1741 int len;
1742
1743 SET_TEXT_POS (pos, 0, 0);
1744 while (charpos--)
1745 {
1746 string_char_and_length ((const unsigned char *) s, &len);
1747 s += len;
1748 CHARPOS (pos) += 1;
1749 BYTEPOS (pos) += len;
1750 }
1751 }
1752 else
1753 SET_TEXT_POS (pos, charpos, charpos);
1754
1755 return pos;
1756 }
1757
1758
1759 /* Value is the number of characters in C string S. MULTIBYTE_P
1760 non-zero means recognize multibyte characters. */
1761
1762 static ptrdiff_t
1763 number_of_chars (const char *s, bool multibyte_p)
1764 {
1765 ptrdiff_t nchars;
1766
1767 if (multibyte_p)
1768 {
1769 ptrdiff_t rest = strlen (s);
1770 int len;
1771 const unsigned char *p = (const unsigned char *) s;
1772
1773 for (nchars = 0; rest > 0; ++nchars)
1774 {
1775 string_char_and_length (p, &len);
1776 rest -= len, p += len;
1777 }
1778 }
1779 else
1780 nchars = strlen (s);
1781
1782 return nchars;
1783 }
1784
1785
1786 /* Compute byte position NEWPOS->bytepos corresponding to
1787 NEWPOS->charpos. POS is a known position in string STRING.
1788 NEWPOS->charpos must be >= POS.charpos. */
1789
1790 static void
1791 compute_string_pos (struct text_pos *newpos, struct text_pos pos, Lisp_Object string)
1792 {
1793 eassert (STRINGP (string));
1794 eassert (CHARPOS (*newpos) >= CHARPOS (pos));
1795
1796 if (STRING_MULTIBYTE (string))
1797 *newpos = string_pos_nchars_ahead (pos, string,
1798 CHARPOS (*newpos) - CHARPOS (pos));
1799 else
1800 BYTEPOS (*newpos) = CHARPOS (*newpos);
1801 }
1802
1803 /* EXPORT:
1804 Return an estimation of the pixel height of mode or header lines on
1805 frame F. FACE_ID specifies what line's height to estimate. */
1806
1807 int
1808 estimate_mode_line_height (struct frame *f, enum face_id face_id)
1809 {
1810 #ifdef HAVE_WINDOW_SYSTEM
1811 if (FRAME_WINDOW_P (f))
1812 {
1813 int height = FONT_HEIGHT (FRAME_FONT (f));
1814
1815 /* This function is called so early when Emacs starts that the face
1816 cache and mode line face are not yet initialized. */
1817 if (FRAME_FACE_CACHE (f))
1818 {
1819 struct face *face = FACE_FROM_ID (f, face_id);
1820 if (face)
1821 {
1822 if (face->font)
1823 height = FONT_HEIGHT (face->font);
1824 if (face->box_line_width > 0)
1825 height += 2 * face->box_line_width;
1826 }
1827 }
1828
1829 return height;
1830 }
1831 #endif
1832
1833 return 1;
1834 }
1835
1836 /* Given a pixel position (PIX_X, PIX_Y) on frame F, return glyph
1837 co-ordinates in (*X, *Y). Set *BOUNDS to the rectangle that the
1838 glyph at X, Y occupies, if BOUNDS != 0. If NOCLIP is non-zero, do
1839 not force the value into range. */
1840
1841 void
1842 pixel_to_glyph_coords (struct frame *f, register int pix_x, register int pix_y,
1843 int *x, int *y, NativeRectangle *bounds, int noclip)
1844 {
1845
1846 #ifdef HAVE_WINDOW_SYSTEM
1847 if (FRAME_WINDOW_P (f))
1848 {
1849 /* Arrange for the division in FRAME_PIXEL_X_TO_COL etc. to round down
1850 even for negative values. */
1851 if (pix_x < 0)
1852 pix_x -= FRAME_COLUMN_WIDTH (f) - 1;
1853 if (pix_y < 0)
1854 pix_y -= FRAME_LINE_HEIGHT (f) - 1;
1855
1856 pix_x = FRAME_PIXEL_X_TO_COL (f, pix_x);
1857 pix_y = FRAME_PIXEL_Y_TO_LINE (f, pix_y);
1858
1859 if (bounds)
1860 STORE_NATIVE_RECT (*bounds,
1861 FRAME_COL_TO_PIXEL_X (f, pix_x),
1862 FRAME_LINE_TO_PIXEL_Y (f, pix_y),
1863 FRAME_COLUMN_WIDTH (f) - 1,
1864 FRAME_LINE_HEIGHT (f) - 1);
1865
1866 /* PXW: Should we clip pixels before converting to columns/lines? */
1867 if (!noclip)
1868 {
1869 if (pix_x < 0)
1870 pix_x = 0;
1871 else if (pix_x > FRAME_TOTAL_COLS (f))
1872 pix_x = FRAME_TOTAL_COLS (f);
1873
1874 if (pix_y < 0)
1875 pix_y = 0;
1876 else if (pix_y > FRAME_TOTAL_LINES (f))
1877 pix_y = FRAME_TOTAL_LINES (f);
1878 }
1879 }
1880 #endif
1881
1882 *x = pix_x;
1883 *y = pix_y;
1884 }
1885
1886
1887 /* Find the glyph under window-relative coordinates X/Y in window W.
1888 Consider only glyphs from buffer text, i.e. no glyphs from overlay
1889 strings. Return in *HPOS and *VPOS the row and column number of
1890 the glyph found. Return in *AREA the glyph area containing X.
1891 Value is a pointer to the glyph found or null if X/Y is not on
1892 text, or we can't tell because W's current matrix is not up to
1893 date. */
1894
1895 static struct glyph *
1896 x_y_to_hpos_vpos (struct window *w, int x, int y, int *hpos, int *vpos,
1897 int *dx, int *dy, int *area)
1898 {
1899 struct glyph *glyph, *end;
1900 struct glyph_row *row = NULL;
1901 int x0, i;
1902
1903 /* Find row containing Y. Give up if some row is not enabled. */
1904 for (i = 0; i < w->current_matrix->nrows; ++i)
1905 {
1906 row = MATRIX_ROW (w->current_matrix, i);
1907 if (!row->enabled_p)
1908 return NULL;
1909 if (y >= row->y && y < MATRIX_ROW_BOTTOM_Y (row))
1910 break;
1911 }
1912
1913 *vpos = i;
1914 *hpos = 0;
1915
1916 /* Give up if Y is not in the window. */
1917 if (i == w->current_matrix->nrows)
1918 return NULL;
1919
1920 /* Get the glyph area containing X. */
1921 if (w->pseudo_window_p)
1922 {
1923 *area = TEXT_AREA;
1924 x0 = 0;
1925 }
1926 else
1927 {
1928 if (x < window_box_left_offset (w, TEXT_AREA))
1929 {
1930 *area = LEFT_MARGIN_AREA;
1931 x0 = window_box_left_offset (w, LEFT_MARGIN_AREA);
1932 }
1933 else if (x < window_box_right_offset (w, TEXT_AREA))
1934 {
1935 *area = TEXT_AREA;
1936 x0 = window_box_left_offset (w, TEXT_AREA) + min (row->x, 0);
1937 }
1938 else
1939 {
1940 *area = RIGHT_MARGIN_AREA;
1941 x0 = window_box_left_offset (w, RIGHT_MARGIN_AREA);
1942 }
1943 }
1944
1945 /* Find glyph containing X. */
1946 glyph = row->glyphs[*area];
1947 end = glyph + row->used[*area];
1948 x -= x0;
1949 while (glyph < end && x >= glyph->pixel_width)
1950 {
1951 x -= glyph->pixel_width;
1952 ++glyph;
1953 }
1954
1955 if (glyph == end)
1956 return NULL;
1957
1958 if (dx)
1959 {
1960 *dx = x;
1961 *dy = y - (row->y + row->ascent - glyph->ascent);
1962 }
1963
1964 *hpos = glyph - row->glyphs[*area];
1965 return glyph;
1966 }
1967
1968 /* Convert frame-relative x/y to coordinates relative to window W.
1969 Takes pseudo-windows into account. */
1970
1971 static void
1972 frame_to_window_pixel_xy (struct window *w, int *x, int *y)
1973 {
1974 if (w->pseudo_window_p)
1975 {
1976 /* A pseudo-window is always full-width, and starts at the
1977 left edge of the frame, plus a frame border. */
1978 struct frame *f = XFRAME (w->frame);
1979 *x -= FRAME_INTERNAL_BORDER_WIDTH (f);
1980 *y = FRAME_TO_WINDOW_PIXEL_Y (w, *y);
1981 }
1982 else
1983 {
1984 *x -= WINDOW_LEFT_EDGE_X (w);
1985 *y = FRAME_TO_WINDOW_PIXEL_Y (w, *y);
1986 }
1987 }
1988
1989 #ifdef HAVE_WINDOW_SYSTEM
1990
1991 /* EXPORT:
1992 Return in RECTS[] at most N clipping rectangles for glyph string S.
1993 Return the number of stored rectangles. */
1994
1995 int
1996 get_glyph_string_clip_rects (struct glyph_string *s, NativeRectangle *rects, int n)
1997 {
1998 XRectangle r;
1999
2000 if (n <= 0)
2001 return 0;
2002
2003 if (s->row->full_width_p)
2004 {
2005 /* Draw full-width. X coordinates are relative to S->w->left_col. */
2006 r.x = WINDOW_LEFT_EDGE_X (s->w);
2007 if (s->row->mode_line_p)
2008 r.width = WINDOW_PIXEL_WIDTH (s->w) - WINDOW_RIGHT_DIVIDER_WIDTH (s->w);
2009 else
2010 r.width = WINDOW_PIXEL_WIDTH (s->w);
2011
2012 /* Unless displaying a mode or menu bar line, which are always
2013 fully visible, clip to the visible part of the row. */
2014 if (s->w->pseudo_window_p)
2015 r.height = s->row->visible_height;
2016 else
2017 r.height = s->height;
2018 }
2019 else
2020 {
2021 /* This is a text line that may be partially visible. */
2022 r.x = window_box_left (s->w, s->area);
2023 r.width = window_box_width (s->w, s->area);
2024 r.height = s->row->visible_height;
2025 }
2026
2027 if (s->clip_head)
2028 if (r.x < s->clip_head->x)
2029 {
2030 if (r.width >= s->clip_head->x - r.x)
2031 r.width -= s->clip_head->x - r.x;
2032 else
2033 r.width = 0;
2034 r.x = s->clip_head->x;
2035 }
2036 if (s->clip_tail)
2037 if (r.x + r.width > s->clip_tail->x + s->clip_tail->background_width)
2038 {
2039 if (s->clip_tail->x + s->clip_tail->background_width >= r.x)
2040 r.width = s->clip_tail->x + s->clip_tail->background_width - r.x;
2041 else
2042 r.width = 0;
2043 }
2044
2045 /* If S draws overlapping rows, it's sufficient to use the top and
2046 bottom of the window for clipping because this glyph string
2047 intentionally draws over other lines. */
2048 if (s->for_overlaps)
2049 {
2050 r.y = WINDOW_HEADER_LINE_HEIGHT (s->w);
2051 r.height = window_text_bottom_y (s->w) - r.y;
2052
2053 /* Alas, the above simple strategy does not work for the
2054 environments with anti-aliased text: if the same text is
2055 drawn onto the same place multiple times, it gets thicker.
2056 If the overlap we are processing is for the erased cursor, we
2057 take the intersection with the rectangle of the cursor. */
2058 if (s->for_overlaps & OVERLAPS_ERASED_CURSOR)
2059 {
2060 XRectangle rc, r_save = r;
2061
2062 rc.x = WINDOW_TEXT_TO_FRAME_PIXEL_X (s->w, s->w->phys_cursor.x);
2063 rc.y = s->w->phys_cursor.y;
2064 rc.width = s->w->phys_cursor_width;
2065 rc.height = s->w->phys_cursor_height;
2066
2067 x_intersect_rectangles (&r_save, &rc, &r);
2068 }
2069 }
2070 else
2071 {
2072 /* Don't use S->y for clipping because it doesn't take partially
2073 visible lines into account. For example, it can be negative for
2074 partially visible lines at the top of a window. */
2075 if (!s->row->full_width_p
2076 && MATRIX_ROW_PARTIALLY_VISIBLE_AT_TOP_P (s->w, s->row))
2077 r.y = WINDOW_HEADER_LINE_HEIGHT (s->w);
2078 else
2079 r.y = max (0, s->row->y);
2080 }
2081
2082 r.y = WINDOW_TO_FRAME_PIXEL_Y (s->w, r.y);
2083
2084 /* If drawing the cursor, don't let glyph draw outside its
2085 advertised boundaries. Cleartype does this under some circumstances. */
2086 if (s->hl == DRAW_CURSOR)
2087 {
2088 struct glyph *glyph = s->first_glyph;
2089 int height, max_y;
2090
2091 if (s->x > r.x)
2092 {
2093 if (r.width >= s->x - r.x)
2094 r.width -= s->x - r.x;
2095 else /* R2L hscrolled row with cursor outside text area */
2096 r.width = 0;
2097 r.x = s->x;
2098 }
2099 r.width = min (r.width, glyph->pixel_width);
2100
2101 /* If r.y is below window bottom, ensure that we still see a cursor. */
2102 height = min (glyph->ascent + glyph->descent,
2103 min (FRAME_LINE_HEIGHT (s->f), s->row->visible_height));
2104 max_y = window_text_bottom_y (s->w) - height;
2105 max_y = WINDOW_TO_FRAME_PIXEL_Y (s->w, max_y);
2106 if (s->ybase - glyph->ascent > max_y)
2107 {
2108 r.y = max_y;
2109 r.height = height;
2110 }
2111 else
2112 {
2113 /* Don't draw cursor glyph taller than our actual glyph. */
2114 height = max (FRAME_LINE_HEIGHT (s->f), glyph->ascent + glyph->descent);
2115 if (height < r.height)
2116 {
2117 max_y = r.y + r.height;
2118 r.y = min (max_y, max (r.y, s->ybase + glyph->descent - height));
2119 r.height = min (max_y - r.y, height);
2120 }
2121 }
2122 }
2123
2124 if (s->row->clip)
2125 {
2126 XRectangle r_save = r;
2127
2128 if (! x_intersect_rectangles (&r_save, s->row->clip, &r))
2129 r.width = 0;
2130 }
2131
2132 if ((s->for_overlaps & OVERLAPS_BOTH) == 0
2133 || ((s->for_overlaps & OVERLAPS_BOTH) == OVERLAPS_BOTH && n == 1))
2134 {
2135 #ifdef CONVERT_FROM_XRECT
2136 CONVERT_FROM_XRECT (r, *rects);
2137 #else
2138 *rects = r;
2139 #endif
2140 return 1;
2141 }
2142 else
2143 {
2144 /* If we are processing overlapping and allowed to return
2145 multiple clipping rectangles, we exclude the row of the glyph
2146 string from the clipping rectangle. This is to avoid drawing
2147 the same text on the environment with anti-aliasing. */
2148 #ifdef CONVERT_FROM_XRECT
2149 XRectangle rs[2];
2150 #else
2151 XRectangle *rs = rects;
2152 #endif
2153 int i = 0, row_y = WINDOW_TO_FRAME_PIXEL_Y (s->w, s->row->y);
2154
2155 if (s->for_overlaps & OVERLAPS_PRED)
2156 {
2157 rs[i] = r;
2158 if (r.y + r.height > row_y)
2159 {
2160 if (r.y < row_y)
2161 rs[i].height = row_y - r.y;
2162 else
2163 rs[i].height = 0;
2164 }
2165 i++;
2166 }
2167 if (s->for_overlaps & OVERLAPS_SUCC)
2168 {
2169 rs[i] = r;
2170 if (r.y < row_y + s->row->visible_height)
2171 {
2172 if (r.y + r.height > row_y + s->row->visible_height)
2173 {
2174 rs[i].y = row_y + s->row->visible_height;
2175 rs[i].height = r.y + r.height - rs[i].y;
2176 }
2177 else
2178 rs[i].height = 0;
2179 }
2180 i++;
2181 }
2182
2183 n = i;
2184 #ifdef CONVERT_FROM_XRECT
2185 for (i = 0; i < n; i++)
2186 CONVERT_FROM_XRECT (rs[i], rects[i]);
2187 #endif
2188 return n;
2189 }
2190 }
2191
2192 /* EXPORT:
2193 Return in *NR the clipping rectangle for glyph string S. */
2194
2195 void
2196 get_glyph_string_clip_rect (struct glyph_string *s, NativeRectangle *nr)
2197 {
2198 get_glyph_string_clip_rects (s, nr, 1);
2199 }
2200
2201
2202 /* EXPORT:
2203 Return the position and height of the phys cursor in window W.
2204 Set w->phys_cursor_width to width of phys cursor.
2205 */
2206
2207 void
2208 get_phys_cursor_geometry (struct window *w, struct glyph_row *row,
2209 struct glyph *glyph, int *xp, int *yp, int *heightp)
2210 {
2211 struct frame *f = XFRAME (WINDOW_FRAME (w));
2212 int x, y, wd, h, h0, y0;
2213
2214 /* Compute the width of the rectangle to draw. If on a stretch
2215 glyph, and `x-stretch-block-cursor' is nil, don't draw a
2216 rectangle as wide as the glyph, but use a canonical character
2217 width instead. */
2218 wd = glyph->pixel_width;
2219
2220 x = w->phys_cursor.x;
2221 if (x < 0)
2222 {
2223 wd += x;
2224 x = 0;
2225 }
2226
2227 if (glyph->type == STRETCH_GLYPH
2228 && !x_stretch_cursor_p)
2229 wd = min (FRAME_COLUMN_WIDTH (f), wd);
2230 w->phys_cursor_width = wd;
2231
2232 y = w->phys_cursor.y + row->ascent - glyph->ascent;
2233
2234 /* If y is below window bottom, ensure that we still see a cursor. */
2235 h0 = min (FRAME_LINE_HEIGHT (f), row->visible_height);
2236
2237 h = max (h0, glyph->ascent + glyph->descent);
2238 h0 = min (h0, glyph->ascent + glyph->descent);
2239
2240 y0 = WINDOW_HEADER_LINE_HEIGHT (w);
2241 if (y < y0)
2242 {
2243 h = max (h - (y0 - y) + 1, h0);
2244 y = y0 - 1;
2245 }
2246 else
2247 {
2248 y0 = window_text_bottom_y (w) - h0;
2249 if (y > y0)
2250 {
2251 h += y - y0;
2252 y = y0;
2253 }
2254 }
2255
2256 *xp = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, x);
2257 *yp = WINDOW_TO_FRAME_PIXEL_Y (w, y);
2258 *heightp = h;
2259 }
2260
2261 /*
2262 * Remember which glyph the mouse is over.
2263 */
2264
2265 void
2266 remember_mouse_glyph (struct frame *f, int gx, int gy, NativeRectangle *rect)
2267 {
2268 Lisp_Object window;
2269 struct window *w;
2270 struct glyph_row *r, *gr, *end_row;
2271 enum window_part part;
2272 enum glyph_row_area area;
2273 int x, y, width, height;
2274
2275 /* Try to determine frame pixel position and size of the glyph under
2276 frame pixel coordinates X/Y on frame F. */
2277
2278 if (window_resize_pixelwise)
2279 {
2280 width = height = 1;
2281 goto virtual_glyph;
2282 }
2283 else if (!f->glyphs_initialized_p
2284 || (window = window_from_coordinates (f, gx, gy, &part, 0),
2285 NILP (window)))
2286 {
2287 width = FRAME_SMALLEST_CHAR_WIDTH (f);
2288 height = FRAME_SMALLEST_FONT_HEIGHT (f);
2289 goto virtual_glyph;
2290 }
2291
2292 w = XWINDOW (window);
2293 width = WINDOW_FRAME_COLUMN_WIDTH (w);
2294 height = WINDOW_FRAME_LINE_HEIGHT (w);
2295
2296 x = window_relative_x_coord (w, part, gx);
2297 y = gy - WINDOW_TOP_EDGE_Y (w);
2298
2299 r = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
2300 end_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
2301
2302 if (w->pseudo_window_p)
2303 {
2304 area = TEXT_AREA;
2305 part = ON_MODE_LINE; /* Don't adjust margin. */
2306 goto text_glyph;
2307 }
2308
2309 switch (part)
2310 {
2311 case ON_LEFT_MARGIN:
2312 area = LEFT_MARGIN_AREA;
2313 goto text_glyph;
2314
2315 case ON_RIGHT_MARGIN:
2316 area = RIGHT_MARGIN_AREA;
2317 goto text_glyph;
2318
2319 case ON_HEADER_LINE:
2320 case ON_MODE_LINE:
2321 gr = (part == ON_HEADER_LINE
2322 ? MATRIX_HEADER_LINE_ROW (w->current_matrix)
2323 : MATRIX_MODE_LINE_ROW (w->current_matrix));
2324 gy = gr->y;
2325 area = TEXT_AREA;
2326 goto text_glyph_row_found;
2327
2328 case ON_TEXT:
2329 area = TEXT_AREA;
2330
2331 text_glyph:
2332 gr = 0; gy = 0;
2333 for (; r <= end_row && r->enabled_p; ++r)
2334 if (r->y + r->height > y)
2335 {
2336 gr = r; gy = r->y;
2337 break;
2338 }
2339
2340 text_glyph_row_found:
2341 if (gr && gy <= y)
2342 {
2343 struct glyph *g = gr->glyphs[area];
2344 struct glyph *end = g + gr->used[area];
2345
2346 height = gr->height;
2347 for (gx = gr->x; g < end; gx += g->pixel_width, ++g)
2348 if (gx + g->pixel_width > x)
2349 break;
2350
2351 if (g < end)
2352 {
2353 if (g->type == IMAGE_GLYPH)
2354 {
2355 /* Don't remember when mouse is over image, as
2356 image may have hot-spots. */
2357 STORE_NATIVE_RECT (*rect, 0, 0, 0, 0);
2358 return;
2359 }
2360 width = g->pixel_width;
2361 }
2362 else
2363 {
2364 /* Use nominal char spacing at end of line. */
2365 x -= gx;
2366 gx += (x / width) * width;
2367 }
2368
2369 if (part != ON_MODE_LINE && part != ON_HEADER_LINE)
2370 {
2371 gx += window_box_left_offset (w, area);
2372 /* Don't expand over the modeline to make sure the vertical
2373 drag cursor is shown early enough. */
2374 height = min (height,
2375 max (0, WINDOW_BOX_HEIGHT_NO_MODE_LINE (w) - gy));
2376 }
2377 }
2378 else
2379 {
2380 /* Use nominal line height at end of window. */
2381 gx = (x / width) * width;
2382 y -= gy;
2383 gy += (y / height) * height;
2384 if (part != ON_MODE_LINE && part != ON_HEADER_LINE)
2385 /* See comment above. */
2386 height = min (height,
2387 max (0, WINDOW_BOX_HEIGHT_NO_MODE_LINE (w) - gy));
2388 }
2389 break;
2390
2391 case ON_LEFT_FRINGE:
2392 gx = (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
2393 ? WINDOW_LEFT_SCROLL_BAR_AREA_WIDTH (w)
2394 : window_box_right_offset (w, LEFT_MARGIN_AREA));
2395 width = WINDOW_LEFT_FRINGE_WIDTH (w);
2396 goto row_glyph;
2397
2398 case ON_RIGHT_FRINGE:
2399 gx = (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
2400 ? window_box_right_offset (w, RIGHT_MARGIN_AREA)
2401 : window_box_right_offset (w, TEXT_AREA));
2402 if (WINDOW_RIGHT_DIVIDER_WIDTH (w) == 0
2403 && !WINDOW_HAS_VERTICAL_SCROLL_BAR (w)
2404 && !WINDOW_RIGHTMOST_P (w))
2405 if (gx < WINDOW_PIXEL_WIDTH (w) - width)
2406 /* Make sure the vertical border can get her own glyph to the
2407 right of the one we build here. */
2408 width = WINDOW_RIGHT_FRINGE_WIDTH (w) - width;
2409 else
2410 width = WINDOW_PIXEL_WIDTH (w) - gx;
2411 else
2412 width = WINDOW_RIGHT_FRINGE_WIDTH (w);
2413
2414 goto row_glyph;
2415
2416 case ON_VERTICAL_BORDER:
2417 gx = WINDOW_PIXEL_WIDTH (w) - width;
2418 goto row_glyph;
2419
2420 case ON_VERTICAL_SCROLL_BAR:
2421 gx = (WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_LEFT (w)
2422 ? 0
2423 : (window_box_right_offset (w, RIGHT_MARGIN_AREA)
2424 + (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
2425 ? WINDOW_RIGHT_FRINGE_WIDTH (w)
2426 : 0)));
2427 width = WINDOW_SCROLL_BAR_AREA_WIDTH (w);
2428
2429 row_glyph:
2430 gr = 0, gy = 0;
2431 for (; r <= end_row && r->enabled_p; ++r)
2432 if (r->y + r->height > y)
2433 {
2434 gr = r; gy = r->y;
2435 break;
2436 }
2437
2438 if (gr && gy <= y)
2439 height = gr->height;
2440 else
2441 {
2442 /* Use nominal line height at end of window. */
2443 y -= gy;
2444 gy += (y / height) * height;
2445 }
2446 break;
2447
2448 case ON_RIGHT_DIVIDER:
2449 gx = WINDOW_PIXEL_WIDTH (w) - WINDOW_RIGHT_DIVIDER_WIDTH (w);
2450 width = WINDOW_RIGHT_DIVIDER_WIDTH (w);
2451 gy = 0;
2452 /* The bottom divider prevails. */
2453 height = WINDOW_PIXEL_HEIGHT (w) - WINDOW_BOTTOM_DIVIDER_WIDTH (w);
2454 goto add_edge;
2455
2456 case ON_BOTTOM_DIVIDER:
2457 gx = 0;
2458 width = WINDOW_PIXEL_WIDTH (w);
2459 gy = WINDOW_PIXEL_HEIGHT (w) - WINDOW_BOTTOM_DIVIDER_WIDTH (w);
2460 height = WINDOW_BOTTOM_DIVIDER_WIDTH (w);
2461 goto add_edge;
2462
2463 default:
2464 ;
2465 virtual_glyph:
2466 /* If there is no glyph under the mouse, then we divide the screen
2467 into a grid of the smallest glyph in the frame, and use that
2468 as our "glyph". */
2469
2470 /* Arrange for the division in FRAME_PIXEL_X_TO_COL etc. to
2471 round down even for negative values. */
2472 if (gx < 0)
2473 gx -= width - 1;
2474 if (gy < 0)
2475 gy -= height - 1;
2476
2477 gx = (gx / width) * width;
2478 gy = (gy / height) * height;
2479
2480 goto store_rect;
2481 }
2482
2483 add_edge:
2484 gx += WINDOW_LEFT_EDGE_X (w);
2485 gy += WINDOW_TOP_EDGE_Y (w);
2486
2487 store_rect:
2488 STORE_NATIVE_RECT (*rect, gx, gy, width, height);
2489
2490 /* Visible feedback for debugging. */
2491 #if 0
2492 #if HAVE_X_WINDOWS
2493 XDrawRectangle (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
2494 f->output_data.x->normal_gc,
2495 gx, gy, width, height);
2496 #endif
2497 #endif
2498 }
2499
2500
2501 #endif /* HAVE_WINDOW_SYSTEM */
2502
2503 static void
2504 adjust_window_ends (struct window *w, struct glyph_row *row, bool current)
2505 {
2506 eassert (w);
2507 w->window_end_pos = Z - MATRIX_ROW_END_CHARPOS (row);
2508 w->window_end_bytepos = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
2509 w->window_end_vpos
2510 = MATRIX_ROW_VPOS (row, current ? w->current_matrix : w->desired_matrix);
2511 }
2512
2513 /***********************************************************************
2514 Lisp form evaluation
2515 ***********************************************************************/
2516
2517 /* Error handler for safe_eval and safe_call. */
2518
2519 static Lisp_Object
2520 safe_eval_handler (Lisp_Object arg, ptrdiff_t nargs, Lisp_Object *args)
2521 {
2522 add_to_log ("Error during redisplay: %S signaled %S",
2523 Flist (nargs, args), arg);
2524 return Qnil;
2525 }
2526
2527 /* Call function FUNC with the rest of NARGS - 1 arguments
2528 following. Return the result, or nil if something went
2529 wrong. Prevent redisplay during the evaluation. */
2530
2531 static Lisp_Object
2532 safe__call (bool inhibit_quit, ptrdiff_t nargs, Lisp_Object func, va_list ap)
2533 {
2534 Lisp_Object val;
2535
2536 if (inhibit_eval_during_redisplay)
2537 val = Qnil;
2538 else
2539 {
2540 ptrdiff_t i;
2541 ptrdiff_t count = SPECPDL_INDEX ();
2542 Lisp_Object *args;
2543 USE_SAFE_ALLOCA;
2544 SAFE_ALLOCA_LISP (args, nargs);
2545
2546 args[0] = func;
2547 for (i = 1; i < nargs; i++)
2548 args[i] = va_arg (ap, Lisp_Object);
2549
2550 specbind (Qinhibit_redisplay, Qt);
2551 if (inhibit_quit)
2552 specbind (Qinhibit_quit, Qt);
2553 /* Use Qt to ensure debugger does not run,
2554 so there is no possibility of wanting to redisplay. */
2555 val = internal_condition_case_n (Ffuncall, nargs, args, Qt,
2556 safe_eval_handler);
2557 SAFE_FREE ();
2558 val = unbind_to (count, val);
2559 }
2560
2561 return val;
2562 }
2563
2564 Lisp_Object
2565 safe_call (ptrdiff_t nargs, Lisp_Object func, ...)
2566 {
2567 Lisp_Object retval;
2568 va_list ap;
2569
2570 va_start (ap, func);
2571 retval = safe__call (false, nargs, func, ap);
2572 va_end (ap);
2573 return retval;
2574 }
2575
2576 /* Call function FN with one argument ARG.
2577 Return the result, or nil if something went wrong. */
2578
2579 Lisp_Object
2580 safe_call1 (Lisp_Object fn, Lisp_Object arg)
2581 {
2582 return safe_call (2, fn, arg);
2583 }
2584
2585 static Lisp_Object
2586 safe__call1 (bool inhibit_quit, Lisp_Object fn, ...)
2587 {
2588 Lisp_Object retval;
2589 va_list ap;
2590
2591 va_start (ap, fn);
2592 retval = safe__call (inhibit_quit, 2, fn, ap);
2593 va_end (ap);
2594 return retval;
2595 }
2596
2597 Lisp_Object
2598 safe_eval (Lisp_Object sexpr)
2599 {
2600 return safe__call1 (false, Qeval, sexpr);
2601 }
2602
2603 static Lisp_Object
2604 safe__eval (bool inhibit_quit, Lisp_Object sexpr)
2605 {
2606 return safe__call1 (inhibit_quit, Qeval, sexpr);
2607 }
2608
2609 /* Call function FN with two arguments ARG1 and ARG2.
2610 Return the result, or nil if something went wrong. */
2611
2612 Lisp_Object
2613 safe_call2 (Lisp_Object fn, Lisp_Object arg1, Lisp_Object arg2)
2614 {
2615 return safe_call (3, fn, arg1, arg2);
2616 }
2617
2618
2619 \f
2620 /***********************************************************************
2621 Debugging
2622 ***********************************************************************/
2623
2624 #if 0
2625
2626 /* Define CHECK_IT to perform sanity checks on iterators.
2627 This is for debugging. It is too slow to do unconditionally. */
2628
2629 static void
2630 check_it (struct it *it)
2631 {
2632 if (it->method == GET_FROM_STRING)
2633 {
2634 eassert (STRINGP (it->string));
2635 eassert (IT_STRING_CHARPOS (*it) >= 0);
2636 }
2637 else
2638 {
2639 eassert (IT_STRING_CHARPOS (*it) < 0);
2640 if (it->method == GET_FROM_BUFFER)
2641 {
2642 /* Check that character and byte positions agree. */
2643 eassert (IT_CHARPOS (*it) == BYTE_TO_CHAR (IT_BYTEPOS (*it)));
2644 }
2645 }
2646
2647 if (it->dpvec)
2648 eassert (it->current.dpvec_index >= 0);
2649 else
2650 eassert (it->current.dpvec_index < 0);
2651 }
2652
2653 #define CHECK_IT(IT) check_it ((IT))
2654
2655 #else /* not 0 */
2656
2657 #define CHECK_IT(IT) (void) 0
2658
2659 #endif /* not 0 */
2660
2661
2662 #if defined GLYPH_DEBUG && defined ENABLE_CHECKING
2663
2664 /* Check that the window end of window W is what we expect it
2665 to be---the last row in the current matrix displaying text. */
2666
2667 static void
2668 check_window_end (struct window *w)
2669 {
2670 if (!MINI_WINDOW_P (w) && w->window_end_valid)
2671 {
2672 struct glyph_row *row;
2673 eassert ((row = MATRIX_ROW (w->current_matrix, w->window_end_vpos),
2674 !row->enabled_p
2675 || MATRIX_ROW_DISPLAYS_TEXT_P (row)
2676 || MATRIX_ROW_VPOS (row, w->current_matrix) == 0));
2677 }
2678 }
2679
2680 #define CHECK_WINDOW_END(W) check_window_end ((W))
2681
2682 #else
2683
2684 #define CHECK_WINDOW_END(W) (void) 0
2685
2686 #endif /* GLYPH_DEBUG and ENABLE_CHECKING */
2687
2688 /***********************************************************************
2689 Iterator initialization
2690 ***********************************************************************/
2691
2692 /* Initialize IT for displaying current_buffer in window W, starting
2693 at character position CHARPOS. CHARPOS < 0 means that no buffer
2694 position is specified which is useful when the iterator is assigned
2695 a position later. BYTEPOS is the byte position corresponding to
2696 CHARPOS.
2697
2698 If ROW is not null, calls to produce_glyphs with IT as parameter
2699 will produce glyphs in that row.
2700
2701 BASE_FACE_ID is the id of a base face to use. It must be one of
2702 DEFAULT_FACE_ID for normal text, MODE_LINE_FACE_ID,
2703 MODE_LINE_INACTIVE_FACE_ID, or HEADER_LINE_FACE_ID for displaying
2704 mode lines, or TOOL_BAR_FACE_ID for displaying the tool-bar.
2705
2706 If ROW is null and BASE_FACE_ID is equal to MODE_LINE_FACE_ID,
2707 MODE_LINE_INACTIVE_FACE_ID, or HEADER_LINE_FACE_ID, the iterator
2708 will be initialized to use the corresponding mode line glyph row of
2709 the desired matrix of W. */
2710
2711 void
2712 init_iterator (struct it *it, struct window *w,
2713 ptrdiff_t charpos, ptrdiff_t bytepos,
2714 struct glyph_row *row, enum face_id base_face_id)
2715 {
2716 enum face_id remapped_base_face_id = base_face_id;
2717
2718 /* Some precondition checks. */
2719 eassert (w != NULL && it != NULL);
2720 eassert (charpos < 0 || (charpos >= BUF_BEG (current_buffer)
2721 && charpos <= ZV));
2722
2723 /* If face attributes have been changed since the last redisplay,
2724 free realized faces now because they depend on face definitions
2725 that might have changed. Don't free faces while there might be
2726 desired matrices pending which reference these faces. */
2727 if (face_change_count && !inhibit_free_realized_faces)
2728 {
2729 face_change_count = 0;
2730 free_all_realized_faces (Qnil);
2731 }
2732
2733 /* Perhaps remap BASE_FACE_ID to a user-specified alternative. */
2734 if (! NILP (Vface_remapping_alist))
2735 remapped_base_face_id
2736 = lookup_basic_face (XFRAME (w->frame), base_face_id);
2737
2738 /* Use one of the mode line rows of W's desired matrix if
2739 appropriate. */
2740 if (row == NULL)
2741 {
2742 if (base_face_id == MODE_LINE_FACE_ID
2743 || base_face_id == MODE_LINE_INACTIVE_FACE_ID)
2744 row = MATRIX_MODE_LINE_ROW (w->desired_matrix);
2745 else if (base_face_id == HEADER_LINE_FACE_ID)
2746 row = MATRIX_HEADER_LINE_ROW (w->desired_matrix);
2747 }
2748
2749 /* Clear IT, and set it->object and other IT's Lisp objects to Qnil.
2750 Other parts of redisplay rely on that. */
2751 memclear (it, sizeof *it);
2752 it->current.overlay_string_index = -1;
2753 it->current.dpvec_index = -1;
2754 it->base_face_id = remapped_base_face_id;
2755 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = -1;
2756 it->paragraph_embedding = L2R;
2757 it->bidi_it.w = w;
2758
2759 /* The window in which we iterate over current_buffer: */
2760 XSETWINDOW (it->window, w);
2761 it->w = w;
2762 it->f = XFRAME (w->frame);
2763
2764 it->cmp_it.id = -1;
2765
2766 /* Extra space between lines (on window systems only). */
2767 if (base_face_id == DEFAULT_FACE_ID
2768 && FRAME_WINDOW_P (it->f))
2769 {
2770 if (NATNUMP (BVAR (current_buffer, extra_line_spacing)))
2771 it->extra_line_spacing = XFASTINT (BVAR (current_buffer, extra_line_spacing));
2772 else if (FLOATP (BVAR (current_buffer, extra_line_spacing)))
2773 it->extra_line_spacing = (XFLOAT_DATA (BVAR (current_buffer, extra_line_spacing))
2774 * FRAME_LINE_HEIGHT (it->f));
2775 else if (it->f->extra_line_spacing > 0)
2776 it->extra_line_spacing = it->f->extra_line_spacing;
2777 }
2778
2779 /* If realized faces have been removed, e.g. because of face
2780 attribute changes of named faces, recompute them. When running
2781 in batch mode, the face cache of the initial frame is null. If
2782 we happen to get called, make a dummy face cache. */
2783 if (FRAME_FACE_CACHE (it->f) == NULL)
2784 init_frame_faces (it->f);
2785 if (FRAME_FACE_CACHE (it->f)->used == 0)
2786 recompute_basic_faces (it->f);
2787
2788 it->override_ascent = -1;
2789
2790 /* Are control characters displayed as `^C'? */
2791 it->ctl_arrow_p = !NILP (BVAR (current_buffer, ctl_arrow));
2792
2793 /* -1 means everything between a CR and the following line end
2794 is invisible. >0 means lines indented more than this value are
2795 invisible. */
2796 it->selective = (INTEGERP (BVAR (current_buffer, selective_display))
2797 ? (clip_to_bounds
2798 (-1, XINT (BVAR (current_buffer, selective_display)),
2799 PTRDIFF_MAX))
2800 : (!NILP (BVAR (current_buffer, selective_display))
2801 ? -1 : 0));
2802 it->selective_display_ellipsis_p
2803 = !NILP (BVAR (current_buffer, selective_display_ellipses));
2804
2805 /* Display table to use. */
2806 it->dp = window_display_table (w);
2807
2808 /* Are multibyte characters enabled in current_buffer? */
2809 it->multibyte_p = !NILP (BVAR (current_buffer, enable_multibyte_characters));
2810
2811 /* Get the position at which the redisplay_end_trigger hook should
2812 be run, if it is to be run at all. */
2813 if (MARKERP (w->redisplay_end_trigger)
2814 && XMARKER (w->redisplay_end_trigger)->buffer != 0)
2815 it->redisplay_end_trigger_charpos
2816 = marker_position (w->redisplay_end_trigger);
2817 else if (INTEGERP (w->redisplay_end_trigger))
2818 it->redisplay_end_trigger_charpos
2819 = clip_to_bounds (PTRDIFF_MIN, XINT (w->redisplay_end_trigger),
2820 PTRDIFF_MAX);
2821
2822 it->tab_width = SANE_TAB_WIDTH (current_buffer);
2823
2824 /* Are lines in the display truncated? */
2825 if (TRUNCATE != 0)
2826 it->line_wrap = TRUNCATE;
2827 if (base_face_id == DEFAULT_FACE_ID
2828 && !it->w->hscroll
2829 && (WINDOW_FULL_WIDTH_P (it->w)
2830 || NILP (Vtruncate_partial_width_windows)
2831 || (INTEGERP (Vtruncate_partial_width_windows)
2832 /* PXW: Shall we do something about this? */
2833 && (XINT (Vtruncate_partial_width_windows)
2834 <= WINDOW_TOTAL_COLS (it->w))))
2835 && NILP (BVAR (current_buffer, truncate_lines)))
2836 it->line_wrap = NILP (BVAR (current_buffer, word_wrap))
2837 ? WINDOW_WRAP : WORD_WRAP;
2838
2839 /* Get dimensions of truncation and continuation glyphs. These are
2840 displayed as fringe bitmaps under X, but we need them for such
2841 frames when the fringes are turned off. But leave the dimensions
2842 zero for tooltip frames, as these glyphs look ugly there and also
2843 sabotage calculations of tooltip dimensions in x-show-tip. */
2844 #ifdef HAVE_WINDOW_SYSTEM
2845 if (!(FRAME_WINDOW_P (it->f)
2846 && FRAMEP (tip_frame)
2847 && it->f == XFRAME (tip_frame)))
2848 #endif
2849 {
2850 if (it->line_wrap == TRUNCATE)
2851 {
2852 /* We will need the truncation glyph. */
2853 eassert (it->glyph_row == NULL);
2854 produce_special_glyphs (it, IT_TRUNCATION);
2855 it->truncation_pixel_width = it->pixel_width;
2856 }
2857 else
2858 {
2859 /* We will need the continuation glyph. */
2860 eassert (it->glyph_row == NULL);
2861 produce_special_glyphs (it, IT_CONTINUATION);
2862 it->continuation_pixel_width = it->pixel_width;
2863 }
2864 }
2865
2866 /* Reset these values to zero because the produce_special_glyphs
2867 above has changed them. */
2868 it->pixel_width = it->ascent = it->descent = 0;
2869 it->phys_ascent = it->phys_descent = 0;
2870
2871 /* Set this after getting the dimensions of truncation and
2872 continuation glyphs, so that we don't produce glyphs when calling
2873 produce_special_glyphs, above. */
2874 it->glyph_row = row;
2875 it->area = TEXT_AREA;
2876
2877 /* Get the dimensions of the display area. The display area
2878 consists of the visible window area plus a horizontally scrolled
2879 part to the left of the window. All x-values are relative to the
2880 start of this total display area. */
2881 if (base_face_id != DEFAULT_FACE_ID)
2882 {
2883 /* Mode lines, menu bar in terminal frames. */
2884 it->first_visible_x = 0;
2885 it->last_visible_x = WINDOW_PIXEL_WIDTH (w);
2886 }
2887 else
2888 {
2889 it->first_visible_x
2890 = window_hscroll_limited (it->w, it->f) * FRAME_COLUMN_WIDTH (it->f);
2891 it->last_visible_x = (it->first_visible_x
2892 + window_box_width (w, TEXT_AREA));
2893
2894 /* If we truncate lines, leave room for the truncation glyph(s) at
2895 the right margin. Otherwise, leave room for the continuation
2896 glyph(s). Done only if the window has no right fringe. */
2897 if (WINDOW_RIGHT_FRINGE_WIDTH (it->w) == 0)
2898 {
2899 if (it->line_wrap == TRUNCATE)
2900 it->last_visible_x -= it->truncation_pixel_width;
2901 else
2902 it->last_visible_x -= it->continuation_pixel_width;
2903 }
2904
2905 it->header_line_p = WINDOW_WANTS_HEADER_LINE_P (w);
2906 it->current_y = WINDOW_HEADER_LINE_HEIGHT (w) + w->vscroll;
2907 }
2908
2909 /* Leave room for a border glyph. */
2910 if (!FRAME_WINDOW_P (it->f)
2911 && !WINDOW_RIGHTMOST_P (it->w))
2912 it->last_visible_x -= 1;
2913
2914 it->last_visible_y = window_text_bottom_y (w);
2915
2916 /* For mode lines and alike, arrange for the first glyph having a
2917 left box line if the face specifies a box. */
2918 if (base_face_id != DEFAULT_FACE_ID)
2919 {
2920 struct face *face;
2921
2922 it->face_id = remapped_base_face_id;
2923
2924 /* If we have a boxed mode line, make the first character appear
2925 with a left box line. */
2926 face = FACE_FROM_ID (it->f, remapped_base_face_id);
2927 if (face && face->box != FACE_NO_BOX)
2928 it->start_of_box_run_p = true;
2929 }
2930
2931 /* If a buffer position was specified, set the iterator there,
2932 getting overlays and face properties from that position. */
2933 if (charpos >= BUF_BEG (current_buffer))
2934 {
2935 it->stop_charpos = charpos;
2936 it->end_charpos = ZV;
2937 eassert (charpos == BYTE_TO_CHAR (bytepos));
2938 IT_CHARPOS (*it) = charpos;
2939 IT_BYTEPOS (*it) = bytepos;
2940
2941 /* We will rely on `reseat' to set this up properly, via
2942 handle_face_prop. */
2943 it->face_id = it->base_face_id;
2944
2945 it->start = it->current;
2946 /* Do we need to reorder bidirectional text? Not if this is a
2947 unibyte buffer: by definition, none of the single-byte
2948 characters are strong R2L, so no reordering is needed. And
2949 bidi.c doesn't support unibyte buffers anyway. Also, don't
2950 reorder while we are loading loadup.el, since the tables of
2951 character properties needed for reordering are not yet
2952 available. */
2953 it->bidi_p =
2954 NILP (Vpurify_flag)
2955 && !NILP (BVAR (current_buffer, bidi_display_reordering))
2956 && it->multibyte_p;
2957
2958 /* If we are to reorder bidirectional text, init the bidi
2959 iterator. */
2960 if (it->bidi_p)
2961 {
2962 /* Since we don't know at this point whether there will be
2963 any R2L lines in the window, we reserve space for
2964 truncation/continuation glyphs even if only the left
2965 fringe is absent. */
2966 if (base_face_id == DEFAULT_FACE_ID
2967 && WINDOW_LEFT_FRINGE_WIDTH (it->w) == 0
2968 && WINDOW_RIGHT_FRINGE_WIDTH (it->w) != 0)
2969 {
2970 if (it->line_wrap == TRUNCATE)
2971 it->last_visible_x -= it->truncation_pixel_width;
2972 else
2973 it->last_visible_x -= it->continuation_pixel_width;
2974 }
2975 /* Note the paragraph direction that this buffer wants to
2976 use. */
2977 if (EQ (BVAR (current_buffer, bidi_paragraph_direction),
2978 Qleft_to_right))
2979 it->paragraph_embedding = L2R;
2980 else if (EQ (BVAR (current_buffer, bidi_paragraph_direction),
2981 Qright_to_left))
2982 it->paragraph_embedding = R2L;
2983 else
2984 it->paragraph_embedding = NEUTRAL_DIR;
2985 bidi_unshelve_cache (NULL, 0);
2986 bidi_init_it (charpos, IT_BYTEPOS (*it), FRAME_WINDOW_P (it->f),
2987 &it->bidi_it);
2988 }
2989
2990 /* Compute faces etc. */
2991 reseat (it, it->current.pos, 1);
2992 }
2993
2994 CHECK_IT (it);
2995 }
2996
2997
2998 /* Initialize IT for the display of window W with window start POS. */
2999
3000 void
3001 start_display (struct it *it, struct window *w, struct text_pos pos)
3002 {
3003 struct glyph_row *row;
3004 int first_vpos = WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0;
3005
3006 row = w->desired_matrix->rows + first_vpos;
3007 init_iterator (it, w, CHARPOS (pos), BYTEPOS (pos), row, DEFAULT_FACE_ID);
3008 it->first_vpos = first_vpos;
3009
3010 /* Don't reseat to previous visible line start if current start
3011 position is in a string or image. */
3012 if (it->method == GET_FROM_BUFFER && it->line_wrap != TRUNCATE)
3013 {
3014 int start_at_line_beg_p;
3015 int first_y = it->current_y;
3016
3017 /* If window start is not at a line start, skip forward to POS to
3018 get the correct continuation lines width. */
3019 start_at_line_beg_p = (CHARPOS (pos) == BEGV
3020 || FETCH_BYTE (BYTEPOS (pos) - 1) == '\n');
3021 if (!start_at_line_beg_p)
3022 {
3023 int new_x;
3024
3025 reseat_at_previous_visible_line_start (it);
3026 move_it_to (it, CHARPOS (pos), -1, -1, -1, MOVE_TO_POS);
3027
3028 new_x = it->current_x + it->pixel_width;
3029
3030 /* If lines are continued, this line may end in the middle
3031 of a multi-glyph character (e.g. a control character
3032 displayed as \003, or in the middle of an overlay
3033 string). In this case move_it_to above will not have
3034 taken us to the start of the continuation line but to the
3035 end of the continued line. */
3036 if (it->current_x > 0
3037 && it->line_wrap != TRUNCATE /* Lines are continued. */
3038 && (/* And glyph doesn't fit on the line. */
3039 new_x > it->last_visible_x
3040 /* Or it fits exactly and we're on a window
3041 system frame. */
3042 || (new_x == it->last_visible_x
3043 && FRAME_WINDOW_P (it->f)
3044 && ((it->bidi_p && it->bidi_it.paragraph_dir == R2L)
3045 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
3046 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)))))
3047 {
3048 if ((it->current.dpvec_index >= 0
3049 || it->current.overlay_string_index >= 0)
3050 /* If we are on a newline from a display vector or
3051 overlay string, then we are already at the end of
3052 a screen line; no need to go to the next line in
3053 that case, as this line is not really continued.
3054 (If we do go to the next line, C-e will not DTRT.) */
3055 && it->c != '\n')
3056 {
3057 set_iterator_to_next (it, 1);
3058 move_it_in_display_line_to (it, -1, -1, 0);
3059 }
3060
3061 it->continuation_lines_width += it->current_x;
3062 }
3063 /* If the character at POS is displayed via a display
3064 vector, move_it_to above stops at the final glyph of
3065 IT->dpvec. To make the caller redisplay that character
3066 again (a.k.a. start at POS), we need to reset the
3067 dpvec_index to the beginning of IT->dpvec. */
3068 else if (it->current.dpvec_index >= 0)
3069 it->current.dpvec_index = 0;
3070
3071 /* We're starting a new display line, not affected by the
3072 height of the continued line, so clear the appropriate
3073 fields in the iterator structure. */
3074 it->max_ascent = it->max_descent = 0;
3075 it->max_phys_ascent = it->max_phys_descent = 0;
3076
3077 it->current_y = first_y;
3078 it->vpos = 0;
3079 it->current_x = it->hpos = 0;
3080 }
3081 }
3082 }
3083
3084
3085 /* Return 1 if POS is a position in ellipses displayed for invisible
3086 text. W is the window we display, for text property lookup. */
3087
3088 static int
3089 in_ellipses_for_invisible_text_p (struct display_pos *pos, struct window *w)
3090 {
3091 Lisp_Object prop, window;
3092 int ellipses_p = 0;
3093 ptrdiff_t charpos = CHARPOS (pos->pos);
3094
3095 /* If POS specifies a position in a display vector, this might
3096 be for an ellipsis displayed for invisible text. We won't
3097 get the iterator set up for delivering that ellipsis unless
3098 we make sure that it gets aware of the invisible text. */
3099 if (pos->dpvec_index >= 0
3100 && pos->overlay_string_index < 0
3101 && CHARPOS (pos->string_pos) < 0
3102 && charpos > BEGV
3103 && (XSETWINDOW (window, w),
3104 prop = Fget_char_property (make_number (charpos),
3105 Qinvisible, window),
3106 !TEXT_PROP_MEANS_INVISIBLE (prop)))
3107 {
3108 prop = Fget_char_property (make_number (charpos - 1), Qinvisible,
3109 window);
3110 ellipses_p = 2 == TEXT_PROP_MEANS_INVISIBLE (prop);
3111 }
3112
3113 return ellipses_p;
3114 }
3115
3116
3117 /* Initialize IT for stepping through current_buffer in window W,
3118 starting at position POS that includes overlay string and display
3119 vector/ control character translation position information. Value
3120 is zero if there are overlay strings with newlines at POS. */
3121
3122 static int
3123 init_from_display_pos (struct it *it, struct window *w, struct display_pos *pos)
3124 {
3125 ptrdiff_t charpos = CHARPOS (pos->pos), bytepos = BYTEPOS (pos->pos);
3126 int i, overlay_strings_with_newlines = 0;
3127
3128 /* If POS specifies a position in a display vector, this might
3129 be for an ellipsis displayed for invisible text. We won't
3130 get the iterator set up for delivering that ellipsis unless
3131 we make sure that it gets aware of the invisible text. */
3132 if (in_ellipses_for_invisible_text_p (pos, w))
3133 {
3134 --charpos;
3135 bytepos = 0;
3136 }
3137
3138 /* Keep in mind: the call to reseat in init_iterator skips invisible
3139 text, so we might end up at a position different from POS. This
3140 is only a problem when POS is a row start after a newline and an
3141 overlay starts there with an after-string, and the overlay has an
3142 invisible property. Since we don't skip invisible text in
3143 display_line and elsewhere immediately after consuming the
3144 newline before the row start, such a POS will not be in a string,
3145 but the call to init_iterator below will move us to the
3146 after-string. */
3147 init_iterator (it, w, charpos, bytepos, NULL, DEFAULT_FACE_ID);
3148
3149 /* This only scans the current chunk -- it should scan all chunks.
3150 However, OVERLAY_STRING_CHUNK_SIZE has been increased from 3 in 21.1
3151 to 16 in 22.1 to make this a lesser problem. */
3152 for (i = 0; i < it->n_overlay_strings && i < OVERLAY_STRING_CHUNK_SIZE; ++i)
3153 {
3154 const char *s = SSDATA (it->overlay_strings[i]);
3155 const char *e = s + SBYTES (it->overlay_strings[i]);
3156
3157 while (s < e && *s != '\n')
3158 ++s;
3159
3160 if (s < e)
3161 {
3162 overlay_strings_with_newlines = 1;
3163 break;
3164 }
3165 }
3166
3167 /* If position is within an overlay string, set up IT to the right
3168 overlay string. */
3169 if (pos->overlay_string_index >= 0)
3170 {
3171 int relative_index;
3172
3173 /* If the first overlay string happens to have a `display'
3174 property for an image, the iterator will be set up for that
3175 image, and we have to undo that setup first before we can
3176 correct the overlay string index. */
3177 if (it->method == GET_FROM_IMAGE)
3178 pop_it (it);
3179
3180 /* We already have the first chunk of overlay strings in
3181 IT->overlay_strings. Load more until the one for
3182 pos->overlay_string_index is in IT->overlay_strings. */
3183 if (pos->overlay_string_index >= OVERLAY_STRING_CHUNK_SIZE)
3184 {
3185 ptrdiff_t n = pos->overlay_string_index / OVERLAY_STRING_CHUNK_SIZE;
3186 it->current.overlay_string_index = 0;
3187 while (n--)
3188 {
3189 load_overlay_strings (it, 0);
3190 it->current.overlay_string_index += OVERLAY_STRING_CHUNK_SIZE;
3191 }
3192 }
3193
3194 it->current.overlay_string_index = pos->overlay_string_index;
3195 relative_index = (it->current.overlay_string_index
3196 % OVERLAY_STRING_CHUNK_SIZE);
3197 it->string = it->overlay_strings[relative_index];
3198 eassert (STRINGP (it->string));
3199 it->current.string_pos = pos->string_pos;
3200 it->method = GET_FROM_STRING;
3201 it->end_charpos = SCHARS (it->string);
3202 /* Set up the bidi iterator for this overlay string. */
3203 if (it->bidi_p)
3204 {
3205 it->bidi_it.string.lstring = it->string;
3206 it->bidi_it.string.s = NULL;
3207 it->bidi_it.string.schars = SCHARS (it->string);
3208 it->bidi_it.string.bufpos = it->overlay_strings_charpos;
3209 it->bidi_it.string.from_disp_str = it->string_from_display_prop_p;
3210 it->bidi_it.string.unibyte = !it->multibyte_p;
3211 it->bidi_it.w = it->w;
3212 bidi_init_it (IT_STRING_CHARPOS (*it), IT_STRING_BYTEPOS (*it),
3213 FRAME_WINDOW_P (it->f), &it->bidi_it);
3214
3215 /* Synchronize the state of the bidi iterator with
3216 pos->string_pos. For any string position other than
3217 zero, this will be done automagically when we resume
3218 iteration over the string and get_visually_first_element
3219 is called. But if string_pos is zero, and the string is
3220 to be reordered for display, we need to resync manually,
3221 since it could be that the iteration state recorded in
3222 pos ended at string_pos of 0 moving backwards in string. */
3223 if (CHARPOS (pos->string_pos) == 0)
3224 {
3225 get_visually_first_element (it);
3226 if (IT_STRING_CHARPOS (*it) != 0)
3227 do {
3228 /* Paranoia. */
3229 eassert (it->bidi_it.charpos < it->bidi_it.string.schars);
3230 bidi_move_to_visually_next (&it->bidi_it);
3231 } while (it->bidi_it.charpos != 0);
3232 }
3233 eassert (IT_STRING_CHARPOS (*it) == it->bidi_it.charpos
3234 && IT_STRING_BYTEPOS (*it) == it->bidi_it.bytepos);
3235 }
3236 }
3237
3238 if (CHARPOS (pos->string_pos) >= 0)
3239 {
3240 /* Recorded position is not in an overlay string, but in another
3241 string. This can only be a string from a `display' property.
3242 IT should already be filled with that string. */
3243 it->current.string_pos = pos->string_pos;
3244 eassert (STRINGP (it->string));
3245 if (it->bidi_p)
3246 bidi_init_it (IT_STRING_CHARPOS (*it), IT_STRING_BYTEPOS (*it),
3247 FRAME_WINDOW_P (it->f), &it->bidi_it);
3248 }
3249
3250 /* Restore position in display vector translations, control
3251 character translations or ellipses. */
3252 if (pos->dpvec_index >= 0)
3253 {
3254 if (it->dpvec == NULL)
3255 get_next_display_element (it);
3256 eassert (it->dpvec && it->current.dpvec_index == 0);
3257 it->current.dpvec_index = pos->dpvec_index;
3258 }
3259
3260 CHECK_IT (it);
3261 return !overlay_strings_with_newlines;
3262 }
3263
3264
3265 /* Initialize IT for stepping through current_buffer in window W
3266 starting at ROW->start. */
3267
3268 static void
3269 init_to_row_start (struct it *it, struct window *w, struct glyph_row *row)
3270 {
3271 init_from_display_pos (it, w, &row->start);
3272 it->start = row->start;
3273 it->continuation_lines_width = row->continuation_lines_width;
3274 CHECK_IT (it);
3275 }
3276
3277
3278 /* Initialize IT for stepping through current_buffer in window W
3279 starting in the line following ROW, i.e. starting at ROW->end.
3280 Value is zero if there are overlay strings with newlines at ROW's
3281 end position. */
3282
3283 static int
3284 init_to_row_end (struct it *it, struct window *w, struct glyph_row *row)
3285 {
3286 int success = 0;
3287
3288 if (init_from_display_pos (it, w, &row->end))
3289 {
3290 if (row->continued_p)
3291 it->continuation_lines_width
3292 = row->continuation_lines_width + row->pixel_width;
3293 CHECK_IT (it);
3294 success = 1;
3295 }
3296
3297 return success;
3298 }
3299
3300
3301
3302 \f
3303 /***********************************************************************
3304 Text properties
3305 ***********************************************************************/
3306
3307 /* Called when IT reaches IT->stop_charpos. Handle text property and
3308 overlay changes. Set IT->stop_charpos to the next position where
3309 to stop. */
3310
3311 static void
3312 handle_stop (struct it *it)
3313 {
3314 enum prop_handled handled;
3315 int handle_overlay_change_p;
3316 struct props *p;
3317
3318 it->dpvec = NULL;
3319 it->current.dpvec_index = -1;
3320 handle_overlay_change_p = !it->ignore_overlay_strings_at_pos_p;
3321 it->ignore_overlay_strings_at_pos_p = 0;
3322 it->ellipsis_p = 0;
3323
3324 /* Use face of preceding text for ellipsis (if invisible) */
3325 if (it->selective_display_ellipsis_p)
3326 it->saved_face_id = it->face_id;
3327
3328 /* Here's the description of the semantics of, and the logic behind,
3329 the various HANDLED_* statuses:
3330
3331 HANDLED_NORMALLY means the handler did its job, and the loop
3332 should proceed to calling the next handler in order.
3333
3334 HANDLED_RECOMPUTE_PROPS means the handler caused a significant
3335 change in the properties and overlays at current position, so the
3336 loop should be restarted, to re-invoke the handlers that were
3337 already called. This happens when fontification-functions were
3338 called by handle_fontified_prop, and actually fontified
3339 something. Another case where HANDLED_RECOMPUTE_PROPS is
3340 returned is when we discover overlay strings that need to be
3341 displayed right away. The loop below will continue for as long
3342 as the status is HANDLED_RECOMPUTE_PROPS.
3343
3344 HANDLED_RETURN means return immediately to the caller, to
3345 continue iteration without calling any further handlers. This is
3346 used when we need to act on some property right away, for example
3347 when we need to display the ellipsis or a replacing display
3348 property, such as display string or image.
3349
3350 HANDLED_OVERLAY_STRING_CONSUMED means an overlay string was just
3351 consumed, and the handler switched to the next overlay string.
3352 This signals the loop below to refrain from looking for more
3353 overlays before all the overlay strings of the current overlay
3354 are processed.
3355
3356 Some of the handlers called by the loop push the iterator state
3357 onto the stack (see 'push_it'), and arrange for the iteration to
3358 continue with another object, such as an image, a display string,
3359 or an overlay string. In most such cases, it->stop_charpos is
3360 set to the first character of the string, so that when the
3361 iteration resumes, this function will immediately be called
3362 again, to examine the properties at the beginning of the string.
3363
3364 When a display or overlay string is exhausted, the iterator state
3365 is popped (see 'pop_it'), and iteration continues with the
3366 previous object. Again, in many such cases this function is
3367 called again to find the next position where properties might
3368 change. */
3369
3370 do
3371 {
3372 handled = HANDLED_NORMALLY;
3373
3374 /* Call text property handlers. */
3375 for (p = it_props; p->handler; ++p)
3376 {
3377 handled = p->handler (it);
3378
3379 if (handled == HANDLED_RECOMPUTE_PROPS)
3380 break;
3381 else if (handled == HANDLED_RETURN)
3382 {
3383 /* We still want to show before and after strings from
3384 overlays even if the actual buffer text is replaced. */
3385 if (!handle_overlay_change_p
3386 || it->sp > 1
3387 /* Don't call get_overlay_strings_1 if we already
3388 have overlay strings loaded, because doing so
3389 will load them again and push the iterator state
3390 onto the stack one more time, which is not
3391 expected by the rest of the code that processes
3392 overlay strings. */
3393 || (it->current.overlay_string_index < 0
3394 ? !get_overlay_strings_1 (it, 0, 0)
3395 : 0))
3396 {
3397 if (it->ellipsis_p)
3398 setup_for_ellipsis (it, 0);
3399 /* When handling a display spec, we might load an
3400 empty string. In that case, discard it here. We
3401 used to discard it in handle_single_display_spec,
3402 but that causes get_overlay_strings_1, above, to
3403 ignore overlay strings that we must check. */
3404 if (STRINGP (it->string) && !SCHARS (it->string))
3405 pop_it (it);
3406 return;
3407 }
3408 else if (STRINGP (it->string) && !SCHARS (it->string))
3409 pop_it (it);
3410 else
3411 {
3412 it->ignore_overlay_strings_at_pos_p = true;
3413 it->string_from_display_prop_p = 0;
3414 it->from_disp_prop_p = 0;
3415 handle_overlay_change_p = 0;
3416 }
3417 handled = HANDLED_RECOMPUTE_PROPS;
3418 break;
3419 }
3420 else if (handled == HANDLED_OVERLAY_STRING_CONSUMED)
3421 handle_overlay_change_p = 0;
3422 }
3423
3424 if (handled != HANDLED_RECOMPUTE_PROPS)
3425 {
3426 /* Don't check for overlay strings below when set to deliver
3427 characters from a display vector. */
3428 if (it->method == GET_FROM_DISPLAY_VECTOR)
3429 handle_overlay_change_p = 0;
3430
3431 /* Handle overlay changes.
3432 This sets HANDLED to HANDLED_RECOMPUTE_PROPS
3433 if it finds overlays. */
3434 if (handle_overlay_change_p)
3435 handled = handle_overlay_change (it);
3436 }
3437
3438 if (it->ellipsis_p)
3439 {
3440 setup_for_ellipsis (it, 0);
3441 break;
3442 }
3443 }
3444 while (handled == HANDLED_RECOMPUTE_PROPS);
3445
3446 /* Determine where to stop next. */
3447 if (handled == HANDLED_NORMALLY)
3448 compute_stop_pos (it);
3449 }
3450
3451
3452 /* Compute IT->stop_charpos from text property and overlay change
3453 information for IT's current position. */
3454
3455 static void
3456 compute_stop_pos (struct it *it)
3457 {
3458 register INTERVAL iv, next_iv;
3459 Lisp_Object object, limit, position;
3460 ptrdiff_t charpos, bytepos;
3461
3462 if (STRINGP (it->string))
3463 {
3464 /* Strings are usually short, so don't limit the search for
3465 properties. */
3466 it->stop_charpos = it->end_charpos;
3467 object = it->string;
3468 limit = Qnil;
3469 charpos = IT_STRING_CHARPOS (*it);
3470 bytepos = IT_STRING_BYTEPOS (*it);
3471 }
3472 else
3473 {
3474 ptrdiff_t pos;
3475
3476 /* If end_charpos is out of range for some reason, such as a
3477 misbehaving display function, rationalize it (Bug#5984). */
3478 if (it->end_charpos > ZV)
3479 it->end_charpos = ZV;
3480 it->stop_charpos = it->end_charpos;
3481
3482 /* If next overlay change is in front of the current stop pos
3483 (which is IT->end_charpos), stop there. Note: value of
3484 next_overlay_change is point-max if no overlay change
3485 follows. */
3486 charpos = IT_CHARPOS (*it);
3487 bytepos = IT_BYTEPOS (*it);
3488 pos = next_overlay_change (charpos);
3489 if (pos < it->stop_charpos)
3490 it->stop_charpos = pos;
3491
3492 /* Set up variables for computing the stop position from text
3493 property changes. */
3494 XSETBUFFER (object, current_buffer);
3495 limit = make_number (IT_CHARPOS (*it) + TEXT_PROP_DISTANCE_LIMIT);
3496 }
3497
3498 /* Get the interval containing IT's position. Value is a null
3499 interval if there isn't such an interval. */
3500 position = make_number (charpos);
3501 iv = validate_interval_range (object, &position, &position, 0);
3502 if (iv)
3503 {
3504 Lisp_Object values_here[LAST_PROP_IDX];
3505 struct props *p;
3506
3507 /* Get properties here. */
3508 for (p = it_props; p->handler; ++p)
3509 values_here[p->idx] = textget (iv->plist,
3510 builtin_lisp_symbol (p->name));
3511
3512 /* Look for an interval following iv that has different
3513 properties. */
3514 for (next_iv = next_interval (iv);
3515 (next_iv
3516 && (NILP (limit)
3517 || XFASTINT (limit) > next_iv->position));
3518 next_iv = next_interval (next_iv))
3519 {
3520 for (p = it_props; p->handler; ++p)
3521 {
3522 Lisp_Object new_value = textget (next_iv->plist,
3523 builtin_lisp_symbol (p->name));
3524 if (!EQ (values_here[p->idx], new_value))
3525 break;
3526 }
3527
3528 if (p->handler)
3529 break;
3530 }
3531
3532 if (next_iv)
3533 {
3534 if (INTEGERP (limit)
3535 && next_iv->position >= XFASTINT (limit))
3536 /* No text property change up to limit. */
3537 it->stop_charpos = min (XFASTINT (limit), it->stop_charpos);
3538 else
3539 /* Text properties change in next_iv. */
3540 it->stop_charpos = min (it->stop_charpos, next_iv->position);
3541 }
3542 }
3543
3544 if (it->cmp_it.id < 0)
3545 {
3546 ptrdiff_t stoppos = it->end_charpos;
3547
3548 if (it->bidi_p && it->bidi_it.scan_dir < 0)
3549 stoppos = -1;
3550 composition_compute_stop_pos (&it->cmp_it, charpos, bytepos,
3551 stoppos, it->string);
3552 }
3553
3554 eassert (STRINGP (it->string)
3555 || (it->stop_charpos >= BEGV
3556 && it->stop_charpos >= IT_CHARPOS (*it)));
3557 }
3558
3559
3560 /* Return the position of the next overlay change after POS in
3561 current_buffer. Value is point-max if no overlay change
3562 follows. This is like `next-overlay-change' but doesn't use
3563 xmalloc. */
3564
3565 static ptrdiff_t
3566 next_overlay_change (ptrdiff_t pos)
3567 {
3568 ptrdiff_t i, noverlays;
3569 ptrdiff_t endpos;
3570 Lisp_Object *overlays;
3571 USE_SAFE_ALLOCA;
3572
3573 /* Get all overlays at the given position. */
3574 GET_OVERLAYS_AT (pos, overlays, noverlays, &endpos, 1);
3575
3576 /* If any of these overlays ends before endpos,
3577 use its ending point instead. */
3578 for (i = 0; i < noverlays; ++i)
3579 {
3580 Lisp_Object oend;
3581 ptrdiff_t oendpos;
3582
3583 oend = OVERLAY_END (overlays[i]);
3584 oendpos = OVERLAY_POSITION (oend);
3585 endpos = min (endpos, oendpos);
3586 }
3587
3588 SAFE_FREE ();
3589 return endpos;
3590 }
3591
3592 /* How many characters forward to search for a display property or
3593 display string. Searching too far forward makes the bidi display
3594 sluggish, especially in small windows. */
3595 #define MAX_DISP_SCAN 250
3596
3597 /* Return the character position of a display string at or after
3598 position specified by POSITION. If no display string exists at or
3599 after POSITION, return ZV. A display string is either an overlay
3600 with `display' property whose value is a string, or a `display'
3601 text property whose value is a string. STRING is data about the
3602 string to iterate; if STRING->lstring is nil, we are iterating a
3603 buffer. FRAME_WINDOW_P is non-zero when we are displaying a window
3604 on a GUI frame. DISP_PROP is set to zero if we searched
3605 MAX_DISP_SCAN characters forward without finding any display
3606 strings, non-zero otherwise. It is set to 2 if the display string
3607 uses any kind of `(space ...)' spec that will produce a stretch of
3608 white space in the text area. */
3609 ptrdiff_t
3610 compute_display_string_pos (struct text_pos *position,
3611 struct bidi_string_data *string,
3612 struct window *w,
3613 int frame_window_p, int *disp_prop)
3614 {
3615 /* OBJECT = nil means current buffer. */
3616 Lisp_Object object, object1;
3617 Lisp_Object pos, spec, limpos;
3618 int string_p = (string && (STRINGP (string->lstring) || string->s));
3619 ptrdiff_t eob = string_p ? string->schars : ZV;
3620 ptrdiff_t begb = string_p ? 0 : BEGV;
3621 ptrdiff_t bufpos, charpos = CHARPOS (*position);
3622 ptrdiff_t lim =
3623 (charpos < eob - MAX_DISP_SCAN) ? charpos + MAX_DISP_SCAN : eob;
3624 struct text_pos tpos;
3625 int rv = 0;
3626
3627 if (string && STRINGP (string->lstring))
3628 object1 = object = string->lstring;
3629 else if (w && !string_p)
3630 {
3631 XSETWINDOW (object, w);
3632 object1 = Qnil;
3633 }
3634 else
3635 object1 = object = Qnil;
3636
3637 *disp_prop = 1;
3638
3639 if (charpos >= eob
3640 /* We don't support display properties whose values are strings
3641 that have display string properties. */
3642 || string->from_disp_str
3643 /* C strings cannot have display properties. */
3644 || (string->s && !STRINGP (object)))
3645 {
3646 *disp_prop = 0;
3647 return eob;
3648 }
3649
3650 /* If the character at CHARPOS is where the display string begins,
3651 return CHARPOS. */
3652 pos = make_number (charpos);
3653 if (STRINGP (object))
3654 bufpos = string->bufpos;
3655 else
3656 bufpos = charpos;
3657 tpos = *position;
3658 if (!NILP (spec = Fget_char_property (pos, Qdisplay, object))
3659 && (charpos <= begb
3660 || !EQ (Fget_char_property (make_number (charpos - 1), Qdisplay,
3661 object),
3662 spec))
3663 && (rv = handle_display_spec (NULL, spec, object, Qnil, &tpos, bufpos,
3664 frame_window_p)))
3665 {
3666 if (rv == 2)
3667 *disp_prop = 2;
3668 return charpos;
3669 }
3670
3671 /* Look forward for the first character with a `display' property
3672 that will replace the underlying text when displayed. */
3673 limpos = make_number (lim);
3674 do {
3675 pos = Fnext_single_char_property_change (pos, Qdisplay, object1, limpos);
3676 CHARPOS (tpos) = XFASTINT (pos);
3677 if (CHARPOS (tpos) >= lim)
3678 {
3679 *disp_prop = 0;
3680 break;
3681 }
3682 if (STRINGP (object))
3683 BYTEPOS (tpos) = string_char_to_byte (object, CHARPOS (tpos));
3684 else
3685 BYTEPOS (tpos) = CHAR_TO_BYTE (CHARPOS (tpos));
3686 spec = Fget_char_property (pos, Qdisplay, object);
3687 if (!STRINGP (object))
3688 bufpos = CHARPOS (tpos);
3689 } while (NILP (spec)
3690 || !(rv = handle_display_spec (NULL, spec, object, Qnil, &tpos,
3691 bufpos, frame_window_p)));
3692 if (rv == 2)
3693 *disp_prop = 2;
3694
3695 return CHARPOS (tpos);
3696 }
3697
3698 /* Return the character position of the end of the display string that
3699 started at CHARPOS. If there's no display string at CHARPOS,
3700 return -1. A display string is either an overlay with `display'
3701 property whose value is a string or a `display' text property whose
3702 value is a string. */
3703 ptrdiff_t
3704 compute_display_string_end (ptrdiff_t charpos, struct bidi_string_data *string)
3705 {
3706 /* OBJECT = nil means current buffer. */
3707 Lisp_Object object =
3708 (string && STRINGP (string->lstring)) ? string->lstring : Qnil;
3709 Lisp_Object pos = make_number (charpos);
3710 ptrdiff_t eob =
3711 (STRINGP (object) || (string && string->s)) ? string->schars : ZV;
3712
3713 if (charpos >= eob || (string->s && !STRINGP (object)))
3714 return eob;
3715
3716 /* It could happen that the display property or overlay was removed
3717 since we found it in compute_display_string_pos above. One way
3718 this can happen is if JIT font-lock was called (through
3719 handle_fontified_prop), and jit-lock-functions remove text
3720 properties or overlays from the portion of buffer that includes
3721 CHARPOS. Muse mode is known to do that, for example. In this
3722 case, we return -1 to the caller, to signal that no display
3723 string is actually present at CHARPOS. See bidi_fetch_char for
3724 how this is handled.
3725
3726 An alternative would be to never look for display properties past
3727 it->stop_charpos. But neither compute_display_string_pos nor
3728 bidi_fetch_char that calls it know or care where the next
3729 stop_charpos is. */
3730 if (NILP (Fget_char_property (pos, Qdisplay, object)))
3731 return -1;
3732
3733 /* Look forward for the first character where the `display' property
3734 changes. */
3735 pos = Fnext_single_char_property_change (pos, Qdisplay, object, Qnil);
3736
3737 return XFASTINT (pos);
3738 }
3739
3740
3741 \f
3742 /***********************************************************************
3743 Fontification
3744 ***********************************************************************/
3745
3746 /* Handle changes in the `fontified' property of the current buffer by
3747 calling hook functions from Qfontification_functions to fontify
3748 regions of text. */
3749
3750 static enum prop_handled
3751 handle_fontified_prop (struct it *it)
3752 {
3753 Lisp_Object prop, pos;
3754 enum prop_handled handled = HANDLED_NORMALLY;
3755
3756 if (!NILP (Vmemory_full))
3757 return handled;
3758
3759 /* Get the value of the `fontified' property at IT's current buffer
3760 position. (The `fontified' property doesn't have a special
3761 meaning in strings.) If the value is nil, call functions from
3762 Qfontification_functions. */
3763 if (!STRINGP (it->string)
3764 && it->s == NULL
3765 && !NILP (Vfontification_functions)
3766 && !NILP (Vrun_hooks)
3767 && (pos = make_number (IT_CHARPOS (*it)),
3768 prop = Fget_char_property (pos, Qfontified, Qnil),
3769 /* Ignore the special cased nil value always present at EOB since
3770 no amount of fontifying will be able to change it. */
3771 NILP (prop) && IT_CHARPOS (*it) < Z))
3772 {
3773 ptrdiff_t count = SPECPDL_INDEX ();
3774 Lisp_Object val;
3775 struct buffer *obuf = current_buffer;
3776 ptrdiff_t begv = BEGV, zv = ZV;
3777 bool old_clip_changed = current_buffer->clip_changed;
3778
3779 val = Vfontification_functions;
3780 specbind (Qfontification_functions, Qnil);
3781
3782 eassert (it->end_charpos == ZV);
3783
3784 if (!CONSP (val) || EQ (XCAR (val), Qlambda))
3785 safe_call1 (val, pos);
3786 else
3787 {
3788 Lisp_Object fns, fn;
3789 struct gcpro gcpro1, gcpro2;
3790
3791 fns = Qnil;
3792 GCPRO2 (val, fns);
3793
3794 for (; CONSP (val); val = XCDR (val))
3795 {
3796 fn = XCAR (val);
3797
3798 if (EQ (fn, Qt))
3799 {
3800 /* A value of t indicates this hook has a local
3801 binding; it means to run the global binding too.
3802 In a global value, t should not occur. If it
3803 does, we must ignore it to avoid an endless
3804 loop. */
3805 for (fns = Fdefault_value (Qfontification_functions);
3806 CONSP (fns);
3807 fns = XCDR (fns))
3808 {
3809 fn = XCAR (fns);
3810 if (!EQ (fn, Qt))
3811 safe_call1 (fn, pos);
3812 }
3813 }
3814 else
3815 safe_call1 (fn, pos);
3816 }
3817
3818 UNGCPRO;
3819 }
3820
3821 unbind_to (count, Qnil);
3822
3823 /* Fontification functions routinely call `save-restriction'.
3824 Normally, this tags clip_changed, which can confuse redisplay
3825 (see discussion in Bug#6671). Since we don't perform any
3826 special handling of fontification changes in the case where
3827 `save-restriction' isn't called, there's no point doing so in
3828 this case either. So, if the buffer's restrictions are
3829 actually left unchanged, reset clip_changed. */
3830 if (obuf == current_buffer)
3831 {
3832 if (begv == BEGV && zv == ZV)
3833 current_buffer->clip_changed = old_clip_changed;
3834 }
3835 /* There isn't much we can reasonably do to protect against
3836 misbehaving fontification, but here's a fig leaf. */
3837 else if (BUFFER_LIVE_P (obuf))
3838 set_buffer_internal_1 (obuf);
3839
3840 /* The fontification code may have added/removed text.
3841 It could do even a lot worse, but let's at least protect against
3842 the most obvious case where only the text past `pos' gets changed',
3843 as is/was done in grep.el where some escapes sequences are turned
3844 into face properties (bug#7876). */
3845 it->end_charpos = ZV;
3846
3847 /* Return HANDLED_RECOMPUTE_PROPS only if function fontified
3848 something. This avoids an endless loop if they failed to
3849 fontify the text for which reason ever. */
3850 if (!NILP (Fget_char_property (pos, Qfontified, Qnil)))
3851 handled = HANDLED_RECOMPUTE_PROPS;
3852 }
3853
3854 return handled;
3855 }
3856
3857
3858 \f
3859 /***********************************************************************
3860 Faces
3861 ***********************************************************************/
3862
3863 /* Set up iterator IT from face properties at its current position.
3864 Called from handle_stop. */
3865
3866 static enum prop_handled
3867 handle_face_prop (struct it *it)
3868 {
3869 int new_face_id;
3870 ptrdiff_t next_stop;
3871
3872 if (!STRINGP (it->string))
3873 {
3874 new_face_id
3875 = face_at_buffer_position (it->w,
3876 IT_CHARPOS (*it),
3877 &next_stop,
3878 (IT_CHARPOS (*it)
3879 + TEXT_PROP_DISTANCE_LIMIT),
3880 false, it->base_face_id);
3881
3882 /* Is this a start of a run of characters with box face?
3883 Caveat: this can be called for a freshly initialized
3884 iterator; face_id is -1 in this case. We know that the new
3885 face will not change until limit, i.e. if the new face has a
3886 box, all characters up to limit will have one. But, as
3887 usual, we don't know whether limit is really the end. */
3888 if (new_face_id != it->face_id)
3889 {
3890 struct face *new_face = FACE_FROM_ID (it->f, new_face_id);
3891 /* If it->face_id is -1, old_face below will be NULL, see
3892 the definition of FACE_FROM_ID. This will happen if this
3893 is the initial call that gets the face. */
3894 struct face *old_face = FACE_FROM_ID (it->f, it->face_id);
3895
3896 /* If the value of face_id of the iterator is -1, we have to
3897 look in front of IT's position and see whether there is a
3898 face there that's different from new_face_id. */
3899 if (!old_face && IT_CHARPOS (*it) > BEG)
3900 {
3901 int prev_face_id = face_before_it_pos (it);
3902
3903 old_face = FACE_FROM_ID (it->f, prev_face_id);
3904 }
3905
3906 /* If the new face has a box, but the old face does not,
3907 this is the start of a run of characters with box face,
3908 i.e. this character has a shadow on the left side. */
3909 it->start_of_box_run_p = (new_face->box != FACE_NO_BOX
3910 && (old_face == NULL || !old_face->box));
3911 it->face_box_p = new_face->box != FACE_NO_BOX;
3912 }
3913 }
3914 else
3915 {
3916 int base_face_id;
3917 ptrdiff_t bufpos;
3918 int i;
3919 Lisp_Object from_overlay
3920 = (it->current.overlay_string_index >= 0
3921 ? it->string_overlays[it->current.overlay_string_index
3922 % OVERLAY_STRING_CHUNK_SIZE]
3923 : Qnil);
3924
3925 /* See if we got to this string directly or indirectly from
3926 an overlay property. That includes the before-string or
3927 after-string of an overlay, strings in display properties
3928 provided by an overlay, their text properties, etc.
3929
3930 FROM_OVERLAY is the overlay that brought us here, or nil if none. */
3931 if (! NILP (from_overlay))
3932 for (i = it->sp - 1; i >= 0; i--)
3933 {
3934 if (it->stack[i].current.overlay_string_index >= 0)
3935 from_overlay
3936 = it->string_overlays[it->stack[i].current.overlay_string_index
3937 % OVERLAY_STRING_CHUNK_SIZE];
3938 else if (! NILP (it->stack[i].from_overlay))
3939 from_overlay = it->stack[i].from_overlay;
3940
3941 if (!NILP (from_overlay))
3942 break;
3943 }
3944
3945 if (! NILP (from_overlay))
3946 {
3947 bufpos = IT_CHARPOS (*it);
3948 /* For a string from an overlay, the base face depends
3949 only on text properties and ignores overlays. */
3950 base_face_id
3951 = face_for_overlay_string (it->w,
3952 IT_CHARPOS (*it),
3953 &next_stop,
3954 (IT_CHARPOS (*it)
3955 + TEXT_PROP_DISTANCE_LIMIT),
3956 false,
3957 from_overlay);
3958 }
3959 else
3960 {
3961 bufpos = 0;
3962
3963 /* For strings from a `display' property, use the face at
3964 IT's current buffer position as the base face to merge
3965 with, so that overlay strings appear in the same face as
3966 surrounding text, unless they specify their own faces.
3967 For strings from wrap-prefix and line-prefix properties,
3968 use the default face, possibly remapped via
3969 Vface_remapping_alist. */
3970 /* Note that the fact that we use the face at _buffer_
3971 position means that a 'display' property on an overlay
3972 string will not inherit the face of that overlay string,
3973 but will instead revert to the face of buffer text
3974 covered by the overlay. This is visible, e.g., when the
3975 overlay specifies a box face, but neither the buffer nor
3976 the display string do. This sounds like a design bug,
3977 but Emacs always did that since v21.1, so changing that
3978 might be a big deal. */
3979 base_face_id = it->string_from_prefix_prop_p
3980 ? (!NILP (Vface_remapping_alist)
3981 ? lookup_basic_face (it->f, DEFAULT_FACE_ID)
3982 : DEFAULT_FACE_ID)
3983 : underlying_face_id (it);
3984 }
3985
3986 new_face_id = face_at_string_position (it->w,
3987 it->string,
3988 IT_STRING_CHARPOS (*it),
3989 bufpos,
3990 &next_stop,
3991 base_face_id, false);
3992
3993 /* Is this a start of a run of characters with box? Caveat:
3994 this can be called for a freshly allocated iterator; face_id
3995 is -1 is this case. We know that the new face will not
3996 change until the next check pos, i.e. if the new face has a
3997 box, all characters up to that position will have a
3998 box. But, as usual, we don't know whether that position
3999 is really the end. */
4000 if (new_face_id != it->face_id)
4001 {
4002 struct face *new_face = FACE_FROM_ID (it->f, new_face_id);
4003 struct face *old_face = FACE_FROM_ID (it->f, it->face_id);
4004
4005 /* If new face has a box but old face hasn't, this is the
4006 start of a run of characters with box, i.e. it has a
4007 shadow on the left side. */
4008 it->start_of_box_run_p
4009 = new_face->box && (old_face == NULL || !old_face->box);
4010 it->face_box_p = new_face->box != FACE_NO_BOX;
4011 }
4012 }
4013
4014 it->face_id = new_face_id;
4015 return HANDLED_NORMALLY;
4016 }
4017
4018
4019 /* Return the ID of the face ``underlying'' IT's current position,
4020 which is in a string. If the iterator is associated with a
4021 buffer, return the face at IT's current buffer position.
4022 Otherwise, use the iterator's base_face_id. */
4023
4024 static int
4025 underlying_face_id (struct it *it)
4026 {
4027 int face_id = it->base_face_id, i;
4028
4029 eassert (STRINGP (it->string));
4030
4031 for (i = it->sp - 1; i >= 0; --i)
4032 if (NILP (it->stack[i].string))
4033 face_id = it->stack[i].face_id;
4034
4035 return face_id;
4036 }
4037
4038
4039 /* Compute the face one character before or after the current position
4040 of IT, in the visual order. BEFORE_P non-zero means get the face
4041 in front (to the left in L2R paragraphs, to the right in R2L
4042 paragraphs) of IT's screen position. Value is the ID of the face. */
4043
4044 static int
4045 face_before_or_after_it_pos (struct it *it, int before_p)
4046 {
4047 int face_id, limit;
4048 ptrdiff_t next_check_charpos;
4049 struct it it_copy;
4050 void *it_copy_data = NULL;
4051
4052 eassert (it->s == NULL);
4053
4054 if (STRINGP (it->string))
4055 {
4056 ptrdiff_t bufpos, charpos;
4057 int base_face_id;
4058
4059 /* No face change past the end of the string (for the case
4060 we are padding with spaces). No face change before the
4061 string start. */
4062 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string)
4063 || (IT_STRING_CHARPOS (*it) == 0 && before_p))
4064 return it->face_id;
4065
4066 if (!it->bidi_p)
4067 {
4068 /* Set charpos to the position before or after IT's current
4069 position, in the logical order, which in the non-bidi
4070 case is the same as the visual order. */
4071 if (before_p)
4072 charpos = IT_STRING_CHARPOS (*it) - 1;
4073 else if (it->what == IT_COMPOSITION)
4074 /* For composition, we must check the character after the
4075 composition. */
4076 charpos = IT_STRING_CHARPOS (*it) + it->cmp_it.nchars;
4077 else
4078 charpos = IT_STRING_CHARPOS (*it) + 1;
4079 }
4080 else
4081 {
4082 if (before_p)
4083 {
4084 /* With bidi iteration, the character before the current
4085 in the visual order cannot be found by simple
4086 iteration, because "reverse" reordering is not
4087 supported. Instead, we need to use the move_it_*
4088 family of functions. */
4089 /* Ignore face changes before the first visible
4090 character on this display line. */
4091 if (it->current_x <= it->first_visible_x)
4092 return it->face_id;
4093 SAVE_IT (it_copy, *it, it_copy_data);
4094 /* Implementation note: Since move_it_in_display_line
4095 works in the iterator geometry, and thinks the first
4096 character is always the leftmost, even in R2L lines,
4097 we don't need to distinguish between the R2L and L2R
4098 cases here. */
4099 move_it_in_display_line (&it_copy, SCHARS (it_copy.string),
4100 it_copy.current_x - 1, MOVE_TO_X);
4101 charpos = IT_STRING_CHARPOS (it_copy);
4102 RESTORE_IT (it, it, it_copy_data);
4103 }
4104 else
4105 {
4106 /* Set charpos to the string position of the character
4107 that comes after IT's current position in the visual
4108 order. */
4109 int n = (it->what == IT_COMPOSITION ? it->cmp_it.nchars : 1);
4110
4111 it_copy = *it;
4112 while (n--)
4113 bidi_move_to_visually_next (&it_copy.bidi_it);
4114
4115 charpos = it_copy.bidi_it.charpos;
4116 }
4117 }
4118 eassert (0 <= charpos && charpos <= SCHARS (it->string));
4119
4120 if (it->current.overlay_string_index >= 0)
4121 bufpos = IT_CHARPOS (*it);
4122 else
4123 bufpos = 0;
4124
4125 base_face_id = underlying_face_id (it);
4126
4127 /* Get the face for ASCII, or unibyte. */
4128 face_id = face_at_string_position (it->w,
4129 it->string,
4130 charpos,
4131 bufpos,
4132 &next_check_charpos,
4133 base_face_id, false);
4134
4135 /* Correct the face for charsets different from ASCII. Do it
4136 for the multibyte case only. The face returned above is
4137 suitable for unibyte text if IT->string is unibyte. */
4138 if (STRING_MULTIBYTE (it->string))
4139 {
4140 struct text_pos pos1 = string_pos (charpos, it->string);
4141 const unsigned char *p = SDATA (it->string) + BYTEPOS (pos1);
4142 int c, len;
4143 struct face *face = FACE_FROM_ID (it->f, face_id);
4144
4145 c = string_char_and_length (p, &len);
4146 face_id = FACE_FOR_CHAR (it->f, face, c, charpos, it->string);
4147 }
4148 }
4149 else
4150 {
4151 struct text_pos pos;
4152
4153 if ((IT_CHARPOS (*it) >= ZV && !before_p)
4154 || (IT_CHARPOS (*it) <= BEGV && before_p))
4155 return it->face_id;
4156
4157 limit = IT_CHARPOS (*it) + TEXT_PROP_DISTANCE_LIMIT;
4158 pos = it->current.pos;
4159
4160 if (!it->bidi_p)
4161 {
4162 if (before_p)
4163 DEC_TEXT_POS (pos, it->multibyte_p);
4164 else
4165 {
4166 if (it->what == IT_COMPOSITION)
4167 {
4168 /* For composition, we must check the position after
4169 the composition. */
4170 pos.charpos += it->cmp_it.nchars;
4171 pos.bytepos += it->len;
4172 }
4173 else
4174 INC_TEXT_POS (pos, it->multibyte_p);
4175 }
4176 }
4177 else
4178 {
4179 if (before_p)
4180 {
4181 /* With bidi iteration, the character before the current
4182 in the visual order cannot be found by simple
4183 iteration, because "reverse" reordering is not
4184 supported. Instead, we need to use the move_it_*
4185 family of functions. */
4186 /* Ignore face changes before the first visible
4187 character on this display line. */
4188 if (it->current_x <= it->first_visible_x)
4189 return it->face_id;
4190 SAVE_IT (it_copy, *it, it_copy_data);
4191 /* Implementation note: Since move_it_in_display_line
4192 works in the iterator geometry, and thinks the first
4193 character is always the leftmost, even in R2L lines,
4194 we don't need to distinguish between the R2L and L2R
4195 cases here. */
4196 move_it_in_display_line (&it_copy, ZV,
4197 it_copy.current_x - 1, MOVE_TO_X);
4198 pos = it_copy.current.pos;
4199 RESTORE_IT (it, it, it_copy_data);
4200 }
4201 else
4202 {
4203 /* Set charpos to the buffer position of the character
4204 that comes after IT's current position in the visual
4205 order. */
4206 int n = (it->what == IT_COMPOSITION ? it->cmp_it.nchars : 1);
4207
4208 it_copy = *it;
4209 while (n--)
4210 bidi_move_to_visually_next (&it_copy.bidi_it);
4211
4212 SET_TEXT_POS (pos,
4213 it_copy.bidi_it.charpos, it_copy.bidi_it.bytepos);
4214 }
4215 }
4216 eassert (BEGV <= CHARPOS (pos) && CHARPOS (pos) <= ZV);
4217
4218 /* Determine face for CHARSET_ASCII, or unibyte. */
4219 face_id = face_at_buffer_position (it->w,
4220 CHARPOS (pos),
4221 &next_check_charpos,
4222 limit, false, -1);
4223
4224 /* Correct the face for charsets different from ASCII. Do it
4225 for the multibyte case only. The face returned above is
4226 suitable for unibyte text if current_buffer is unibyte. */
4227 if (it->multibyte_p)
4228 {
4229 int c = FETCH_MULTIBYTE_CHAR (BYTEPOS (pos));
4230 struct face *face = FACE_FROM_ID (it->f, face_id);
4231 face_id = FACE_FOR_CHAR (it->f, face, c, CHARPOS (pos), Qnil);
4232 }
4233 }
4234
4235 return face_id;
4236 }
4237
4238
4239 \f
4240 /***********************************************************************
4241 Invisible text
4242 ***********************************************************************/
4243
4244 /* Set up iterator IT from invisible properties at its current
4245 position. Called from handle_stop. */
4246
4247 static enum prop_handled
4248 handle_invisible_prop (struct it *it)
4249 {
4250 enum prop_handled handled = HANDLED_NORMALLY;
4251 int invis_p;
4252 Lisp_Object prop;
4253
4254 if (STRINGP (it->string))
4255 {
4256 Lisp_Object end_charpos, limit, charpos;
4257
4258 /* Get the value of the invisible text property at the
4259 current position. Value will be nil if there is no such
4260 property. */
4261 charpos = make_number (IT_STRING_CHARPOS (*it));
4262 prop = Fget_text_property (charpos, Qinvisible, it->string);
4263 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
4264
4265 if (invis_p && IT_STRING_CHARPOS (*it) < it->end_charpos)
4266 {
4267 /* Record whether we have to display an ellipsis for the
4268 invisible text. */
4269 int display_ellipsis_p = (invis_p == 2);
4270 ptrdiff_t len, endpos;
4271
4272 handled = HANDLED_RECOMPUTE_PROPS;
4273
4274 /* Get the position at which the next visible text can be
4275 found in IT->string, if any. */
4276 endpos = len = SCHARS (it->string);
4277 XSETINT (limit, len);
4278 do
4279 {
4280 end_charpos = Fnext_single_property_change (charpos, Qinvisible,
4281 it->string, limit);
4282 if (INTEGERP (end_charpos))
4283 {
4284 endpos = XFASTINT (end_charpos);
4285 prop = Fget_text_property (end_charpos, Qinvisible, it->string);
4286 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
4287 if (invis_p == 2)
4288 display_ellipsis_p = true;
4289 }
4290 }
4291 while (invis_p && endpos < len);
4292
4293 if (display_ellipsis_p)
4294 it->ellipsis_p = true;
4295
4296 if (endpos < len)
4297 {
4298 /* Text at END_CHARPOS is visible. Move IT there. */
4299 struct text_pos old;
4300 ptrdiff_t oldpos;
4301
4302 old = it->current.string_pos;
4303 oldpos = CHARPOS (old);
4304 if (it->bidi_p)
4305 {
4306 if (it->bidi_it.first_elt
4307 && it->bidi_it.charpos < SCHARS (it->string))
4308 bidi_paragraph_init (it->paragraph_embedding,
4309 &it->bidi_it, 1);
4310 /* Bidi-iterate out of the invisible text. */
4311 do
4312 {
4313 bidi_move_to_visually_next (&it->bidi_it);
4314 }
4315 while (oldpos <= it->bidi_it.charpos
4316 && it->bidi_it.charpos < endpos);
4317
4318 IT_STRING_CHARPOS (*it) = it->bidi_it.charpos;
4319 IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos;
4320 if (IT_CHARPOS (*it) >= endpos)
4321 it->prev_stop = endpos;
4322 }
4323 else
4324 {
4325 IT_STRING_CHARPOS (*it) = XFASTINT (end_charpos);
4326 compute_string_pos (&it->current.string_pos, old, it->string);
4327 }
4328 }
4329 else
4330 {
4331 /* The rest of the string is invisible. If this is an
4332 overlay string, proceed with the next overlay string
4333 or whatever comes and return a character from there. */
4334 if (it->current.overlay_string_index >= 0
4335 && !display_ellipsis_p)
4336 {
4337 next_overlay_string (it);
4338 /* Don't check for overlay strings when we just
4339 finished processing them. */
4340 handled = HANDLED_OVERLAY_STRING_CONSUMED;
4341 }
4342 else
4343 {
4344 IT_STRING_CHARPOS (*it) = SCHARS (it->string);
4345 IT_STRING_BYTEPOS (*it) = SBYTES (it->string);
4346 }
4347 }
4348 }
4349 }
4350 else
4351 {
4352 ptrdiff_t newpos, next_stop, start_charpos, tem;
4353 Lisp_Object pos, overlay;
4354
4355 /* First of all, is there invisible text at this position? */
4356 tem = start_charpos = IT_CHARPOS (*it);
4357 pos = make_number (tem);
4358 prop = get_char_property_and_overlay (pos, Qinvisible, it->window,
4359 &overlay);
4360 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
4361
4362 /* If we are on invisible text, skip over it. */
4363 if (invis_p && start_charpos < it->end_charpos)
4364 {
4365 /* Record whether we have to display an ellipsis for the
4366 invisible text. */
4367 int display_ellipsis_p = invis_p == 2;
4368
4369 handled = HANDLED_RECOMPUTE_PROPS;
4370
4371 /* Loop skipping over invisible text. The loop is left at
4372 ZV or with IT on the first char being visible again. */
4373 do
4374 {
4375 /* Try to skip some invisible text. Return value is the
4376 position reached which can be equal to where we start
4377 if there is nothing invisible there. This skips both
4378 over invisible text properties and overlays with
4379 invisible property. */
4380 newpos = skip_invisible (tem, &next_stop, ZV, it->window);
4381
4382 /* If we skipped nothing at all we weren't at invisible
4383 text in the first place. If everything to the end of
4384 the buffer was skipped, end the loop. */
4385 if (newpos == tem || newpos >= ZV)
4386 invis_p = 0;
4387 else
4388 {
4389 /* We skipped some characters but not necessarily
4390 all there are. Check if we ended up on visible
4391 text. Fget_char_property returns the property of
4392 the char before the given position, i.e. if we
4393 get invis_p = 0, this means that the char at
4394 newpos is visible. */
4395 pos = make_number (newpos);
4396 prop = Fget_char_property (pos, Qinvisible, it->window);
4397 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
4398 }
4399
4400 /* If we ended up on invisible text, proceed to
4401 skip starting with next_stop. */
4402 if (invis_p)
4403 tem = next_stop;
4404
4405 /* If there are adjacent invisible texts, don't lose the
4406 second one's ellipsis. */
4407 if (invis_p == 2)
4408 display_ellipsis_p = true;
4409 }
4410 while (invis_p);
4411
4412 /* The position newpos is now either ZV or on visible text. */
4413 if (it->bidi_p)
4414 {
4415 ptrdiff_t bpos = CHAR_TO_BYTE (newpos);
4416 int on_newline
4417 = bpos == ZV_BYTE || FETCH_BYTE (bpos) == '\n';
4418 int after_newline
4419 = newpos <= BEGV || FETCH_BYTE (bpos - 1) == '\n';
4420
4421 /* If the invisible text ends on a newline or on a
4422 character after a newline, we can avoid the costly,
4423 character by character, bidi iteration to NEWPOS, and
4424 instead simply reseat the iterator there. That's
4425 because all bidi reordering information is tossed at
4426 the newline. This is a big win for modes that hide
4427 complete lines, like Outline, Org, etc. */
4428 if (on_newline || after_newline)
4429 {
4430 struct text_pos tpos;
4431 bidi_dir_t pdir = it->bidi_it.paragraph_dir;
4432
4433 SET_TEXT_POS (tpos, newpos, bpos);
4434 reseat_1 (it, tpos, 0);
4435 /* If we reseat on a newline/ZV, we need to prep the
4436 bidi iterator for advancing to the next character
4437 after the newline/EOB, keeping the current paragraph
4438 direction (so that PRODUCE_GLYPHS does TRT wrt
4439 prepending/appending glyphs to a glyph row). */
4440 if (on_newline)
4441 {
4442 it->bidi_it.first_elt = 0;
4443 it->bidi_it.paragraph_dir = pdir;
4444 it->bidi_it.ch = (bpos == ZV_BYTE) ? -1 : '\n';
4445 it->bidi_it.nchars = 1;
4446 it->bidi_it.ch_len = 1;
4447 }
4448 }
4449 else /* Must use the slow method. */
4450 {
4451 /* With bidi iteration, the region of invisible text
4452 could start and/or end in the middle of a
4453 non-base embedding level. Therefore, we need to
4454 skip invisible text using the bidi iterator,
4455 starting at IT's current position, until we find
4456 ourselves outside of the invisible text.
4457 Skipping invisible text _after_ bidi iteration
4458 avoids affecting the visual order of the
4459 displayed text when invisible properties are
4460 added or removed. */
4461 if (it->bidi_it.first_elt && it->bidi_it.charpos < ZV)
4462 {
4463 /* If we were `reseat'ed to a new paragraph,
4464 determine the paragraph base direction. We
4465 need to do it now because
4466 next_element_from_buffer may not have a
4467 chance to do it, if we are going to skip any
4468 text at the beginning, which resets the
4469 FIRST_ELT flag. */
4470 bidi_paragraph_init (it->paragraph_embedding,
4471 &it->bidi_it, 1);
4472 }
4473 do
4474 {
4475 bidi_move_to_visually_next (&it->bidi_it);
4476 }
4477 while (it->stop_charpos <= it->bidi_it.charpos
4478 && it->bidi_it.charpos < newpos);
4479 IT_CHARPOS (*it) = it->bidi_it.charpos;
4480 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
4481 /* If we overstepped NEWPOS, record its position in
4482 the iterator, so that we skip invisible text if
4483 later the bidi iteration lands us in the
4484 invisible region again. */
4485 if (IT_CHARPOS (*it) >= newpos)
4486 it->prev_stop = newpos;
4487 }
4488 }
4489 else
4490 {
4491 IT_CHARPOS (*it) = newpos;
4492 IT_BYTEPOS (*it) = CHAR_TO_BYTE (newpos);
4493 }
4494
4495 /* If there are before-strings at the start of invisible
4496 text, and the text is invisible because of a text
4497 property, arrange to show before-strings because 20.x did
4498 it that way. (If the text is invisible because of an
4499 overlay property instead of a text property, this is
4500 already handled in the overlay code.) */
4501 if (NILP (overlay)
4502 && get_overlay_strings (it, it->stop_charpos))
4503 {
4504 handled = HANDLED_RECOMPUTE_PROPS;
4505 if (it->sp > 0)
4506 {
4507 it->stack[it->sp - 1].display_ellipsis_p = display_ellipsis_p;
4508 /* The call to get_overlay_strings above recomputes
4509 it->stop_charpos, but it only considers changes
4510 in properties and overlays beyond iterator's
4511 current position. This causes us to miss changes
4512 that happen exactly where the invisible property
4513 ended. So we play it safe here and force the
4514 iterator to check for potential stop positions
4515 immediately after the invisible text. Note that
4516 if get_overlay_strings returns non-zero, it
4517 normally also pushed the iterator stack, so we
4518 need to update the stop position in the slot
4519 below the current one. */
4520 it->stack[it->sp - 1].stop_charpos
4521 = CHARPOS (it->stack[it->sp - 1].current.pos);
4522 }
4523 }
4524 else if (display_ellipsis_p)
4525 {
4526 /* Make sure that the glyphs of the ellipsis will get
4527 correct `charpos' values. If we would not update
4528 it->position here, the glyphs would belong to the
4529 last visible character _before_ the invisible
4530 text, which confuses `set_cursor_from_row'.
4531
4532 We use the last invisible position instead of the
4533 first because this way the cursor is always drawn on
4534 the first "." of the ellipsis, whenever PT is inside
4535 the invisible text. Otherwise the cursor would be
4536 placed _after_ the ellipsis when the point is after the
4537 first invisible character. */
4538 if (!STRINGP (it->object))
4539 {
4540 it->position.charpos = newpos - 1;
4541 it->position.bytepos = CHAR_TO_BYTE (it->position.charpos);
4542 }
4543 it->ellipsis_p = true;
4544 /* Let the ellipsis display before
4545 considering any properties of the following char.
4546 Fixes jasonr@gnu.org 01 Oct 07 bug. */
4547 handled = HANDLED_RETURN;
4548 }
4549 }
4550 }
4551
4552 return handled;
4553 }
4554
4555
4556 /* Make iterator IT return `...' next.
4557 Replaces LEN characters from buffer. */
4558
4559 static void
4560 setup_for_ellipsis (struct it *it, int len)
4561 {
4562 /* Use the display table definition for `...'. Invalid glyphs
4563 will be handled by the method returning elements from dpvec. */
4564 if (it->dp && VECTORP (DISP_INVIS_VECTOR (it->dp)))
4565 {
4566 struct Lisp_Vector *v = XVECTOR (DISP_INVIS_VECTOR (it->dp));
4567 it->dpvec = v->contents;
4568 it->dpend = v->contents + v->header.size;
4569 }
4570 else
4571 {
4572 /* Default `...'. */
4573 it->dpvec = default_invis_vector;
4574 it->dpend = default_invis_vector + 3;
4575 }
4576
4577 it->dpvec_char_len = len;
4578 it->current.dpvec_index = 0;
4579 it->dpvec_face_id = -1;
4580
4581 /* Remember the current face id in case glyphs specify faces.
4582 IT's face is restored in set_iterator_to_next.
4583 saved_face_id was set to preceding char's face in handle_stop. */
4584 if (it->saved_face_id < 0 || it->saved_face_id != it->face_id)
4585 it->saved_face_id = it->face_id = DEFAULT_FACE_ID;
4586
4587 it->method = GET_FROM_DISPLAY_VECTOR;
4588 it->ellipsis_p = true;
4589 }
4590
4591
4592 \f
4593 /***********************************************************************
4594 'display' property
4595 ***********************************************************************/
4596
4597 /* Set up iterator IT from `display' property at its current position.
4598 Called from handle_stop.
4599 We return HANDLED_RETURN if some part of the display property
4600 overrides the display of the buffer text itself.
4601 Otherwise we return HANDLED_NORMALLY. */
4602
4603 static enum prop_handled
4604 handle_display_prop (struct it *it)
4605 {
4606 Lisp_Object propval, object, overlay;
4607 struct text_pos *position;
4608 ptrdiff_t bufpos;
4609 /* Nonzero if some property replaces the display of the text itself. */
4610 int display_replaced_p = 0;
4611
4612 if (STRINGP (it->string))
4613 {
4614 object = it->string;
4615 position = &it->current.string_pos;
4616 bufpos = CHARPOS (it->current.pos);
4617 }
4618 else
4619 {
4620 XSETWINDOW (object, it->w);
4621 position = &it->current.pos;
4622 bufpos = CHARPOS (*position);
4623 }
4624
4625 /* Reset those iterator values set from display property values. */
4626 it->slice.x = it->slice.y = it->slice.width = it->slice.height = Qnil;
4627 it->space_width = Qnil;
4628 it->font_height = Qnil;
4629 it->voffset = 0;
4630
4631 /* We don't support recursive `display' properties, i.e. string
4632 values that have a string `display' property, that have a string
4633 `display' property etc. */
4634 if (!it->string_from_display_prop_p)
4635 it->area = TEXT_AREA;
4636
4637 propval = get_char_property_and_overlay (make_number (position->charpos),
4638 Qdisplay, object, &overlay);
4639 if (NILP (propval))
4640 return HANDLED_NORMALLY;
4641 /* Now OVERLAY is the overlay that gave us this property, or nil
4642 if it was a text property. */
4643
4644 if (!STRINGP (it->string))
4645 object = it->w->contents;
4646
4647 display_replaced_p = handle_display_spec (it, propval, object, overlay,
4648 position, bufpos,
4649 FRAME_WINDOW_P (it->f));
4650
4651 return display_replaced_p ? HANDLED_RETURN : HANDLED_NORMALLY;
4652 }
4653
4654 /* Subroutine of handle_display_prop. Returns non-zero if the display
4655 specification in SPEC is a replacing specification, i.e. it would
4656 replace the text covered by `display' property with something else,
4657 such as an image or a display string. If SPEC includes any kind or
4658 `(space ...) specification, the value is 2; this is used by
4659 compute_display_string_pos, which see.
4660
4661 See handle_single_display_spec for documentation of arguments.
4662 frame_window_p is non-zero if the window being redisplayed is on a
4663 GUI frame; this argument is used only if IT is NULL, see below.
4664
4665 IT can be NULL, if this is called by the bidi reordering code
4666 through compute_display_string_pos, which see. In that case, this
4667 function only examines SPEC, but does not otherwise "handle" it, in
4668 the sense that it doesn't set up members of IT from the display
4669 spec. */
4670 static int
4671 handle_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object,
4672 Lisp_Object overlay, struct text_pos *position,
4673 ptrdiff_t bufpos, int frame_window_p)
4674 {
4675 int replacing_p = 0;
4676 int rv;
4677
4678 if (CONSP (spec)
4679 /* Simple specifications. */
4680 && !EQ (XCAR (spec), Qimage)
4681 && !EQ (XCAR (spec), Qspace)
4682 && !EQ (XCAR (spec), Qwhen)
4683 && !EQ (XCAR (spec), Qslice)
4684 && !EQ (XCAR (spec), Qspace_width)
4685 && !EQ (XCAR (spec), Qheight)
4686 && !EQ (XCAR (spec), Qraise)
4687 /* Marginal area specifications. */
4688 && !(CONSP (XCAR (spec)) && EQ (XCAR (XCAR (spec)), Qmargin))
4689 && !EQ (XCAR (spec), Qleft_fringe)
4690 && !EQ (XCAR (spec), Qright_fringe)
4691 && !NILP (XCAR (spec)))
4692 {
4693 for (; CONSP (spec); spec = XCDR (spec))
4694 {
4695 if ((rv = handle_single_display_spec (it, XCAR (spec), object,
4696 overlay, position, bufpos,
4697 replacing_p, frame_window_p)))
4698 {
4699 replacing_p = rv;
4700 /* If some text in a string is replaced, `position' no
4701 longer points to the position of `object'. */
4702 if (!it || STRINGP (object))
4703 break;
4704 }
4705 }
4706 }
4707 else if (VECTORP (spec))
4708 {
4709 ptrdiff_t i;
4710 for (i = 0; i < ASIZE (spec); ++i)
4711 if ((rv = handle_single_display_spec (it, AREF (spec, i), object,
4712 overlay, position, bufpos,
4713 replacing_p, frame_window_p)))
4714 {
4715 replacing_p = rv;
4716 /* If some text in a string is replaced, `position' no
4717 longer points to the position of `object'. */
4718 if (!it || STRINGP (object))
4719 break;
4720 }
4721 }
4722 else
4723 {
4724 if ((rv = handle_single_display_spec (it, spec, object, overlay,
4725 position, bufpos, 0,
4726 frame_window_p)))
4727 replacing_p = rv;
4728 }
4729
4730 return replacing_p;
4731 }
4732
4733 /* Value is the position of the end of the `display' property starting
4734 at START_POS in OBJECT. */
4735
4736 static struct text_pos
4737 display_prop_end (struct it *it, Lisp_Object object, struct text_pos start_pos)
4738 {
4739 Lisp_Object end;
4740 struct text_pos end_pos;
4741
4742 end = Fnext_single_char_property_change (make_number (CHARPOS (start_pos)),
4743 Qdisplay, object, Qnil);
4744 CHARPOS (end_pos) = XFASTINT (end);
4745 if (STRINGP (object))
4746 compute_string_pos (&end_pos, start_pos, it->string);
4747 else
4748 BYTEPOS (end_pos) = CHAR_TO_BYTE (XFASTINT (end));
4749
4750 return end_pos;
4751 }
4752
4753
4754 /* Set up IT from a single `display' property specification SPEC. OBJECT
4755 is the object in which the `display' property was found. *POSITION
4756 is the position in OBJECT at which the `display' property was found.
4757 BUFPOS is the buffer position of OBJECT (different from POSITION if
4758 OBJECT is not a buffer). DISPLAY_REPLACED_P non-zero means that we
4759 previously saw a display specification which already replaced text
4760 display with something else, for example an image; we ignore such
4761 properties after the first one has been processed.
4762
4763 OVERLAY is the overlay this `display' property came from,
4764 or nil if it was a text property.
4765
4766 If SPEC is a `space' or `image' specification, and in some other
4767 cases too, set *POSITION to the position where the `display'
4768 property ends.
4769
4770 If IT is NULL, only examine the property specification in SPEC, but
4771 don't set up IT. In that case, FRAME_WINDOW_P non-zero means SPEC
4772 is intended to be displayed in a window on a GUI frame.
4773
4774 Value is non-zero if something was found which replaces the display
4775 of buffer or string text. */
4776
4777 static int
4778 handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object,
4779 Lisp_Object overlay, struct text_pos *position,
4780 ptrdiff_t bufpos, int display_replaced_p,
4781 int frame_window_p)
4782 {
4783 Lisp_Object form;
4784 Lisp_Object location, value;
4785 struct text_pos start_pos = *position;
4786 int valid_p;
4787
4788 /* If SPEC is a list of the form `(when FORM . VALUE)', evaluate FORM.
4789 If the result is non-nil, use VALUE instead of SPEC. */
4790 form = Qt;
4791 if (CONSP (spec) && EQ (XCAR (spec), Qwhen))
4792 {
4793 spec = XCDR (spec);
4794 if (!CONSP (spec))
4795 return 0;
4796 form = XCAR (spec);
4797 spec = XCDR (spec);
4798 }
4799
4800 if (!NILP (form) && !EQ (form, Qt))
4801 {
4802 ptrdiff_t count = SPECPDL_INDEX ();
4803 struct gcpro gcpro1;
4804
4805 /* Bind `object' to the object having the `display' property, a
4806 buffer or string. Bind `position' to the position in the
4807 object where the property was found, and `buffer-position'
4808 to the current position in the buffer. */
4809
4810 if (NILP (object))
4811 XSETBUFFER (object, current_buffer);
4812 specbind (Qobject, object);
4813 specbind (Qposition, make_number (CHARPOS (*position)));
4814 specbind (Qbuffer_position, make_number (bufpos));
4815 GCPRO1 (form);
4816 form = safe_eval (form);
4817 UNGCPRO;
4818 unbind_to (count, Qnil);
4819 }
4820
4821 if (NILP (form))
4822 return 0;
4823
4824 /* Handle `(height HEIGHT)' specifications. */
4825 if (CONSP (spec)
4826 && EQ (XCAR (spec), Qheight)
4827 && CONSP (XCDR (spec)))
4828 {
4829 if (it)
4830 {
4831 if (!FRAME_WINDOW_P (it->f))
4832 return 0;
4833
4834 it->font_height = XCAR (XCDR (spec));
4835 if (!NILP (it->font_height))
4836 {
4837 struct face *face = FACE_FROM_ID (it->f, it->face_id);
4838 int new_height = -1;
4839
4840 if (CONSP (it->font_height)
4841 && (EQ (XCAR (it->font_height), Qplus)
4842 || EQ (XCAR (it->font_height), Qminus))
4843 && CONSP (XCDR (it->font_height))
4844 && RANGED_INTEGERP (0, XCAR (XCDR (it->font_height)), INT_MAX))
4845 {
4846 /* `(+ N)' or `(- N)' where N is an integer. */
4847 int steps = XINT (XCAR (XCDR (it->font_height)));
4848 if (EQ (XCAR (it->font_height), Qplus))
4849 steps = - steps;
4850 it->face_id = smaller_face (it->f, it->face_id, steps);
4851 }
4852 else if (FUNCTIONP (it->font_height))
4853 {
4854 /* Call function with current height as argument.
4855 Value is the new height. */
4856 Lisp_Object height;
4857 height = safe_call1 (it->font_height,
4858 face->lface[LFACE_HEIGHT_INDEX]);
4859 if (NUMBERP (height))
4860 new_height = XFLOATINT (height);
4861 }
4862 else if (NUMBERP (it->font_height))
4863 {
4864 /* Value is a multiple of the canonical char height. */
4865 struct face *f;
4866
4867 f = FACE_FROM_ID (it->f,
4868 lookup_basic_face (it->f, DEFAULT_FACE_ID));
4869 new_height = (XFLOATINT (it->font_height)
4870 * XINT (f->lface[LFACE_HEIGHT_INDEX]));
4871 }
4872 else
4873 {
4874 /* Evaluate IT->font_height with `height' bound to the
4875 current specified height to get the new height. */
4876 ptrdiff_t count = SPECPDL_INDEX ();
4877
4878 specbind (Qheight, face->lface[LFACE_HEIGHT_INDEX]);
4879 value = safe_eval (it->font_height);
4880 unbind_to (count, Qnil);
4881
4882 if (NUMBERP (value))
4883 new_height = XFLOATINT (value);
4884 }
4885
4886 if (new_height > 0)
4887 it->face_id = face_with_height (it->f, it->face_id, new_height);
4888 }
4889 }
4890
4891 return 0;
4892 }
4893
4894 /* Handle `(space-width WIDTH)'. */
4895 if (CONSP (spec)
4896 && EQ (XCAR (spec), Qspace_width)
4897 && CONSP (XCDR (spec)))
4898 {
4899 if (it)
4900 {
4901 if (!FRAME_WINDOW_P (it->f))
4902 return 0;
4903
4904 value = XCAR (XCDR (spec));
4905 if (NUMBERP (value) && XFLOATINT (value) > 0)
4906 it->space_width = value;
4907 }
4908
4909 return 0;
4910 }
4911
4912 /* Handle `(slice X Y WIDTH HEIGHT)'. */
4913 if (CONSP (spec)
4914 && EQ (XCAR (spec), Qslice))
4915 {
4916 Lisp_Object tem;
4917
4918 if (it)
4919 {
4920 if (!FRAME_WINDOW_P (it->f))
4921 return 0;
4922
4923 if (tem = XCDR (spec), CONSP (tem))
4924 {
4925 it->slice.x = XCAR (tem);
4926 if (tem = XCDR (tem), CONSP (tem))
4927 {
4928 it->slice.y = XCAR (tem);
4929 if (tem = XCDR (tem), CONSP (tem))
4930 {
4931 it->slice.width = XCAR (tem);
4932 if (tem = XCDR (tem), CONSP (tem))
4933 it->slice.height = XCAR (tem);
4934 }
4935 }
4936 }
4937 }
4938
4939 return 0;
4940 }
4941
4942 /* Handle `(raise FACTOR)'. */
4943 if (CONSP (spec)
4944 && EQ (XCAR (spec), Qraise)
4945 && CONSP (XCDR (spec)))
4946 {
4947 if (it)
4948 {
4949 if (!FRAME_WINDOW_P (it->f))
4950 return 0;
4951
4952 #ifdef HAVE_WINDOW_SYSTEM
4953 value = XCAR (XCDR (spec));
4954 if (NUMBERP (value))
4955 {
4956 struct face *face = FACE_FROM_ID (it->f, it->face_id);
4957 it->voffset = - (XFLOATINT (value)
4958 * (FONT_HEIGHT (face->font)));
4959 }
4960 #endif /* HAVE_WINDOW_SYSTEM */
4961 }
4962
4963 return 0;
4964 }
4965
4966 /* Don't handle the other kinds of display specifications
4967 inside a string that we got from a `display' property. */
4968 if (it && it->string_from_display_prop_p)
4969 return 0;
4970
4971 /* Characters having this form of property are not displayed, so
4972 we have to find the end of the property. */
4973 if (it)
4974 {
4975 start_pos = *position;
4976 *position = display_prop_end (it, object, start_pos);
4977 }
4978 value = Qnil;
4979
4980 /* Stop the scan at that end position--we assume that all
4981 text properties change there. */
4982 if (it)
4983 it->stop_charpos = position->charpos;
4984
4985 /* Handle `(left-fringe BITMAP [FACE])'
4986 and `(right-fringe BITMAP [FACE])'. */
4987 if (CONSP (spec)
4988 && (EQ (XCAR (spec), Qleft_fringe)
4989 || EQ (XCAR (spec), Qright_fringe))
4990 && CONSP (XCDR (spec)))
4991 {
4992 int fringe_bitmap;
4993
4994 if (it)
4995 {
4996 if (!FRAME_WINDOW_P (it->f))
4997 /* If we return here, POSITION has been advanced
4998 across the text with this property. */
4999 {
5000 /* Synchronize the bidi iterator with POSITION. This is
5001 needed because we are not going to push the iterator
5002 on behalf of this display property, so there will be
5003 no pop_it call to do this synchronization for us. */
5004 if (it->bidi_p)
5005 {
5006 it->position = *position;
5007 iterate_out_of_display_property (it);
5008 *position = it->position;
5009 }
5010 /* If we were to display this fringe bitmap,
5011 next_element_from_image would have reset this flag.
5012 Do the same, to avoid affecting overlays that
5013 follow. */
5014 it->ignore_overlay_strings_at_pos_p = 0;
5015 return 1;
5016 }
5017 }
5018 else if (!frame_window_p)
5019 return 1;
5020
5021 #ifdef HAVE_WINDOW_SYSTEM
5022 value = XCAR (XCDR (spec));
5023 if (!SYMBOLP (value)
5024 || !(fringe_bitmap = lookup_fringe_bitmap (value)))
5025 /* If we return here, POSITION has been advanced
5026 across the text with this property. */
5027 {
5028 if (it && it->bidi_p)
5029 {
5030 it->position = *position;
5031 iterate_out_of_display_property (it);
5032 *position = it->position;
5033 }
5034 if (it)
5035 /* Reset this flag like next_element_from_image would. */
5036 it->ignore_overlay_strings_at_pos_p = 0;
5037 return 1;
5038 }
5039
5040 if (it)
5041 {
5042 int face_id = lookup_basic_face (it->f, DEFAULT_FACE_ID);
5043
5044 if (CONSP (XCDR (XCDR (spec))))
5045 {
5046 Lisp_Object face_name = XCAR (XCDR (XCDR (spec)));
5047 int face_id2 = lookup_derived_face (it->f, face_name,
5048 FRINGE_FACE_ID, 0);
5049 if (face_id2 >= 0)
5050 face_id = face_id2;
5051 }
5052
5053 /* Save current settings of IT so that we can restore them
5054 when we are finished with the glyph property value. */
5055 push_it (it, position);
5056
5057 it->area = TEXT_AREA;
5058 it->what = IT_IMAGE;
5059 it->image_id = -1; /* no image */
5060 it->position = start_pos;
5061 it->object = NILP (object) ? it->w->contents : object;
5062 it->method = GET_FROM_IMAGE;
5063 it->from_overlay = Qnil;
5064 it->face_id = face_id;
5065 it->from_disp_prop_p = true;
5066
5067 /* Say that we haven't consumed the characters with
5068 `display' property yet. The call to pop_it in
5069 set_iterator_to_next will clean this up. */
5070 *position = start_pos;
5071
5072 if (EQ (XCAR (spec), Qleft_fringe))
5073 {
5074 it->left_user_fringe_bitmap = fringe_bitmap;
5075 it->left_user_fringe_face_id = face_id;
5076 }
5077 else
5078 {
5079 it->right_user_fringe_bitmap = fringe_bitmap;
5080 it->right_user_fringe_face_id = face_id;
5081 }
5082 }
5083 #endif /* HAVE_WINDOW_SYSTEM */
5084 return 1;
5085 }
5086
5087 /* Prepare to handle `((margin left-margin) ...)',
5088 `((margin right-margin) ...)' and `((margin nil) ...)'
5089 prefixes for display specifications. */
5090 location = Qunbound;
5091 if (CONSP (spec) && CONSP (XCAR (spec)))
5092 {
5093 Lisp_Object tem;
5094
5095 value = XCDR (spec);
5096 if (CONSP (value))
5097 value = XCAR (value);
5098
5099 tem = XCAR (spec);
5100 if (EQ (XCAR (tem), Qmargin)
5101 && (tem = XCDR (tem),
5102 tem = CONSP (tem) ? XCAR (tem) : Qnil,
5103 (NILP (tem)
5104 || EQ (tem, Qleft_margin)
5105 || EQ (tem, Qright_margin))))
5106 location = tem;
5107 }
5108
5109 if (EQ (location, Qunbound))
5110 {
5111 location = Qnil;
5112 value = spec;
5113 }
5114
5115 /* After this point, VALUE is the property after any
5116 margin prefix has been stripped. It must be a string,
5117 an image specification, or `(space ...)'.
5118
5119 LOCATION specifies where to display: `left-margin',
5120 `right-margin' or nil. */
5121
5122 valid_p = (STRINGP (value)
5123 #ifdef HAVE_WINDOW_SYSTEM
5124 || ((it ? FRAME_WINDOW_P (it->f) : frame_window_p)
5125 && valid_image_p (value))
5126 #endif /* not HAVE_WINDOW_SYSTEM */
5127 || (CONSP (value) && EQ (XCAR (value), Qspace)));
5128
5129 if (valid_p && !display_replaced_p)
5130 {
5131 int retval = 1;
5132
5133 if (!it)
5134 {
5135 /* Callers need to know whether the display spec is any kind
5136 of `(space ...)' spec that is about to affect text-area
5137 display. */
5138 if (CONSP (value) && EQ (XCAR (value), Qspace) && NILP (location))
5139 retval = 2;
5140 return retval;
5141 }
5142
5143 /* Save current settings of IT so that we can restore them
5144 when we are finished with the glyph property value. */
5145 push_it (it, position);
5146 it->from_overlay = overlay;
5147 it->from_disp_prop_p = true;
5148
5149 if (NILP (location))
5150 it->area = TEXT_AREA;
5151 else if (EQ (location, Qleft_margin))
5152 it->area = LEFT_MARGIN_AREA;
5153 else
5154 it->area = RIGHT_MARGIN_AREA;
5155
5156 if (STRINGP (value))
5157 {
5158 it->string = value;
5159 it->multibyte_p = STRING_MULTIBYTE (it->string);
5160 it->current.overlay_string_index = -1;
5161 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = 0;
5162 it->end_charpos = it->string_nchars = SCHARS (it->string);
5163 it->method = GET_FROM_STRING;
5164 it->stop_charpos = 0;
5165 it->prev_stop = 0;
5166 it->base_level_stop = 0;
5167 it->string_from_display_prop_p = true;
5168 /* Say that we haven't consumed the characters with
5169 `display' property yet. The call to pop_it in
5170 set_iterator_to_next will clean this up. */
5171 if (BUFFERP (object))
5172 *position = start_pos;
5173
5174 /* Force paragraph direction to be that of the parent
5175 object. If the parent object's paragraph direction is
5176 not yet determined, default to L2R. */
5177 if (it->bidi_p && it->bidi_it.paragraph_dir == R2L)
5178 it->paragraph_embedding = it->bidi_it.paragraph_dir;
5179 else
5180 it->paragraph_embedding = L2R;
5181
5182 /* Set up the bidi iterator for this display string. */
5183 if (it->bidi_p)
5184 {
5185 it->bidi_it.string.lstring = it->string;
5186 it->bidi_it.string.s = NULL;
5187 it->bidi_it.string.schars = it->end_charpos;
5188 it->bidi_it.string.bufpos = bufpos;
5189 it->bidi_it.string.from_disp_str = 1;
5190 it->bidi_it.string.unibyte = !it->multibyte_p;
5191 it->bidi_it.w = it->w;
5192 bidi_init_it (0, 0, FRAME_WINDOW_P (it->f), &it->bidi_it);
5193 }
5194 }
5195 else if (CONSP (value) && EQ (XCAR (value), Qspace))
5196 {
5197 it->method = GET_FROM_STRETCH;
5198 it->object = value;
5199 *position = it->position = start_pos;
5200 retval = 1 + (it->area == TEXT_AREA);
5201 }
5202 #ifdef HAVE_WINDOW_SYSTEM
5203 else
5204 {
5205 it->what = IT_IMAGE;
5206 it->image_id = lookup_image (it->f, value);
5207 it->position = start_pos;
5208 it->object = NILP (object) ? it->w->contents : object;
5209 it->method = GET_FROM_IMAGE;
5210
5211 /* Say that we haven't consumed the characters with
5212 `display' property yet. The call to pop_it in
5213 set_iterator_to_next will clean this up. */
5214 *position = start_pos;
5215 }
5216 #endif /* HAVE_WINDOW_SYSTEM */
5217
5218 return retval;
5219 }
5220
5221 /* Invalid property or property not supported. Restore
5222 POSITION to what it was before. */
5223 *position = start_pos;
5224 return 0;
5225 }
5226
5227 /* Check if PROP is a display property value whose text should be
5228 treated as intangible. OVERLAY is the overlay from which PROP
5229 came, or nil if it came from a text property. CHARPOS and BYTEPOS
5230 specify the buffer position covered by PROP. */
5231
5232 int
5233 display_prop_intangible_p (Lisp_Object prop, Lisp_Object overlay,
5234 ptrdiff_t charpos, ptrdiff_t bytepos)
5235 {
5236 int frame_window_p = FRAME_WINDOW_P (XFRAME (selected_frame));
5237 struct text_pos position;
5238
5239 SET_TEXT_POS (position, charpos, bytepos);
5240 return handle_display_spec (NULL, prop, Qnil, overlay,
5241 &position, charpos, frame_window_p);
5242 }
5243
5244
5245 /* Return 1 if PROP is a display sub-property value containing STRING.
5246
5247 Implementation note: this and the following function are really
5248 special cases of handle_display_spec and
5249 handle_single_display_spec, and should ideally use the same code.
5250 Until they do, these two pairs must be consistent and must be
5251 modified in sync. */
5252
5253 static int
5254 single_display_spec_string_p (Lisp_Object prop, Lisp_Object string)
5255 {
5256 if (EQ (string, prop))
5257 return 1;
5258
5259 /* Skip over `when FORM'. */
5260 if (CONSP (prop) && EQ (XCAR (prop), Qwhen))
5261 {
5262 prop = XCDR (prop);
5263 if (!CONSP (prop))
5264 return 0;
5265 /* Actually, the condition following `when' should be eval'ed,
5266 like handle_single_display_spec does, and we should return
5267 zero if it evaluates to nil. However, this function is
5268 called only when the buffer was already displayed and some
5269 glyph in the glyph matrix was found to come from a display
5270 string. Therefore, the condition was already evaluated, and
5271 the result was non-nil, otherwise the display string wouldn't
5272 have been displayed and we would have never been called for
5273 this property. Thus, we can skip the evaluation and assume
5274 its result is non-nil. */
5275 prop = XCDR (prop);
5276 }
5277
5278 if (CONSP (prop))
5279 /* Skip over `margin LOCATION'. */
5280 if (EQ (XCAR (prop), Qmargin))
5281 {
5282 prop = XCDR (prop);
5283 if (!CONSP (prop))
5284 return 0;
5285
5286 prop = XCDR (prop);
5287 if (!CONSP (prop))
5288 return 0;
5289 }
5290
5291 return EQ (prop, string) || (CONSP (prop) && EQ (XCAR (prop), string));
5292 }
5293
5294
5295 /* Return 1 if STRING appears in the `display' property PROP. */
5296
5297 static int
5298 display_prop_string_p (Lisp_Object prop, Lisp_Object string)
5299 {
5300 if (CONSP (prop)
5301 && !EQ (XCAR (prop), Qwhen)
5302 && !(CONSP (XCAR (prop)) && EQ (Qmargin, XCAR (XCAR (prop)))))
5303 {
5304 /* A list of sub-properties. */
5305 while (CONSP (prop))
5306 {
5307 if (single_display_spec_string_p (XCAR (prop), string))
5308 return 1;
5309 prop = XCDR (prop);
5310 }
5311 }
5312 else if (VECTORP (prop))
5313 {
5314 /* A vector of sub-properties. */
5315 ptrdiff_t i;
5316 for (i = 0; i < ASIZE (prop); ++i)
5317 if (single_display_spec_string_p (AREF (prop, i), string))
5318 return 1;
5319 }
5320 else
5321 return single_display_spec_string_p (prop, string);
5322
5323 return 0;
5324 }
5325
5326 /* Look for STRING in overlays and text properties in the current
5327 buffer, between character positions FROM and TO (excluding TO).
5328 BACK_P non-zero means look back (in this case, TO is supposed to be
5329 less than FROM).
5330 Value is the first character position where STRING was found, or
5331 zero if it wasn't found before hitting TO.
5332
5333 This function may only use code that doesn't eval because it is
5334 called asynchronously from note_mouse_highlight. */
5335
5336 static ptrdiff_t
5337 string_buffer_position_lim (Lisp_Object string,
5338 ptrdiff_t from, ptrdiff_t to, int back_p)
5339 {
5340 Lisp_Object limit, prop, pos;
5341 int found = 0;
5342
5343 pos = make_number (max (from, BEGV));
5344
5345 if (!back_p) /* looking forward */
5346 {
5347 limit = make_number (min (to, ZV));
5348 while (!found && !EQ (pos, limit))
5349 {
5350 prop = Fget_char_property (pos, Qdisplay, Qnil);
5351 if (!NILP (prop) && display_prop_string_p (prop, string))
5352 found = 1;
5353 else
5354 pos = Fnext_single_char_property_change (pos, Qdisplay, Qnil,
5355 limit);
5356 }
5357 }
5358 else /* looking back */
5359 {
5360 limit = make_number (max (to, BEGV));
5361 while (!found && !EQ (pos, limit))
5362 {
5363 prop = Fget_char_property (pos, Qdisplay, Qnil);
5364 if (!NILP (prop) && display_prop_string_p (prop, string))
5365 found = 1;
5366 else
5367 pos = Fprevious_single_char_property_change (pos, Qdisplay, Qnil,
5368 limit);
5369 }
5370 }
5371
5372 return found ? XINT (pos) : 0;
5373 }
5374
5375 /* Determine which buffer position in current buffer STRING comes from.
5376 AROUND_CHARPOS is an approximate position where it could come from.
5377 Value is the buffer position or 0 if it couldn't be determined.
5378
5379 This function is necessary because we don't record buffer positions
5380 in glyphs generated from strings (to keep struct glyph small).
5381 This function may only use code that doesn't eval because it is
5382 called asynchronously from note_mouse_highlight. */
5383
5384 static ptrdiff_t
5385 string_buffer_position (Lisp_Object string, ptrdiff_t around_charpos)
5386 {
5387 const int MAX_DISTANCE = 1000;
5388 ptrdiff_t found = string_buffer_position_lim (string, around_charpos,
5389 around_charpos + MAX_DISTANCE,
5390 0);
5391
5392 if (!found)
5393 found = string_buffer_position_lim (string, around_charpos,
5394 around_charpos - MAX_DISTANCE, 1);
5395 return found;
5396 }
5397
5398
5399 \f
5400 /***********************************************************************
5401 `composition' property
5402 ***********************************************************************/
5403
5404 /* Set up iterator IT from `composition' property at its current
5405 position. Called from handle_stop. */
5406
5407 static enum prop_handled
5408 handle_composition_prop (struct it *it)
5409 {
5410 Lisp_Object prop, string;
5411 ptrdiff_t pos, pos_byte, start, end;
5412
5413 if (STRINGP (it->string))
5414 {
5415 unsigned char *s;
5416
5417 pos = IT_STRING_CHARPOS (*it);
5418 pos_byte = IT_STRING_BYTEPOS (*it);
5419 string = it->string;
5420 s = SDATA (string) + pos_byte;
5421 it->c = STRING_CHAR (s);
5422 }
5423 else
5424 {
5425 pos = IT_CHARPOS (*it);
5426 pos_byte = IT_BYTEPOS (*it);
5427 string = Qnil;
5428 it->c = FETCH_CHAR (pos_byte);
5429 }
5430
5431 /* If there's a valid composition and point is not inside of the
5432 composition (in the case that the composition is from the current
5433 buffer), draw a glyph composed from the composition components. */
5434 if (find_composition (pos, -1, &start, &end, &prop, string)
5435 && composition_valid_p (start, end, prop)
5436 && (STRINGP (it->string) || (PT <= start || PT >= end)))
5437 {
5438 if (start < pos)
5439 /* As we can't handle this situation (perhaps font-lock added
5440 a new composition), we just return here hoping that next
5441 redisplay will detect this composition much earlier. */
5442 return HANDLED_NORMALLY;
5443 if (start != pos)
5444 {
5445 if (STRINGP (it->string))
5446 pos_byte = string_char_to_byte (it->string, start);
5447 else
5448 pos_byte = CHAR_TO_BYTE (start);
5449 }
5450 it->cmp_it.id = get_composition_id (start, pos_byte, end - start,
5451 prop, string);
5452
5453 if (it->cmp_it.id >= 0)
5454 {
5455 it->cmp_it.ch = -1;
5456 it->cmp_it.nchars = COMPOSITION_LENGTH (prop);
5457 it->cmp_it.nglyphs = -1;
5458 }
5459 }
5460
5461 return HANDLED_NORMALLY;
5462 }
5463
5464
5465 \f
5466 /***********************************************************************
5467 Overlay strings
5468 ***********************************************************************/
5469
5470 /* The following structure is used to record overlay strings for
5471 later sorting in load_overlay_strings. */
5472
5473 struct overlay_entry
5474 {
5475 Lisp_Object overlay;
5476 Lisp_Object string;
5477 EMACS_INT priority;
5478 int after_string_p;
5479 };
5480
5481
5482 /* Set up iterator IT from overlay strings at its current position.
5483 Called from handle_stop. */
5484
5485 static enum prop_handled
5486 handle_overlay_change (struct it *it)
5487 {
5488 if (!STRINGP (it->string) && get_overlay_strings (it, 0))
5489 return HANDLED_RECOMPUTE_PROPS;
5490 else
5491 return HANDLED_NORMALLY;
5492 }
5493
5494
5495 /* Set up the next overlay string for delivery by IT, if there is an
5496 overlay string to deliver. Called by set_iterator_to_next when the
5497 end of the current overlay string is reached. If there are more
5498 overlay strings to display, IT->string and
5499 IT->current.overlay_string_index are set appropriately here.
5500 Otherwise IT->string is set to nil. */
5501
5502 static void
5503 next_overlay_string (struct it *it)
5504 {
5505 ++it->current.overlay_string_index;
5506 if (it->current.overlay_string_index == it->n_overlay_strings)
5507 {
5508 /* No more overlay strings. Restore IT's settings to what
5509 they were before overlay strings were processed, and
5510 continue to deliver from current_buffer. */
5511
5512 it->ellipsis_p = (it->stack[it->sp - 1].display_ellipsis_p != 0);
5513 pop_it (it);
5514 eassert (it->sp > 0
5515 || (NILP (it->string)
5516 && it->method == GET_FROM_BUFFER
5517 && it->stop_charpos >= BEGV
5518 && it->stop_charpos <= it->end_charpos));
5519 it->current.overlay_string_index = -1;
5520 it->n_overlay_strings = 0;
5521 it->overlay_strings_charpos = -1;
5522 /* If there's an empty display string on the stack, pop the
5523 stack, to resync the bidi iterator with IT's position. Such
5524 empty strings are pushed onto the stack in
5525 get_overlay_strings_1. */
5526 if (it->sp > 0 && STRINGP (it->string) && !SCHARS (it->string))
5527 pop_it (it);
5528
5529 /* If we're at the end of the buffer, record that we have
5530 processed the overlay strings there already, so that
5531 next_element_from_buffer doesn't try it again. */
5532 if (NILP (it->string) && IT_CHARPOS (*it) >= it->end_charpos)
5533 it->overlay_strings_at_end_processed_p = true;
5534 }
5535 else
5536 {
5537 /* There are more overlay strings to process. If
5538 IT->current.overlay_string_index has advanced to a position
5539 where we must load IT->overlay_strings with more strings, do
5540 it. We must load at the IT->overlay_strings_charpos where
5541 IT->n_overlay_strings was originally computed; when invisible
5542 text is present, this might not be IT_CHARPOS (Bug#7016). */
5543 int i = it->current.overlay_string_index % OVERLAY_STRING_CHUNK_SIZE;
5544
5545 if (it->current.overlay_string_index && i == 0)
5546 load_overlay_strings (it, it->overlay_strings_charpos);
5547
5548 /* Initialize IT to deliver display elements from the overlay
5549 string. */
5550 it->string = it->overlay_strings[i];
5551 it->multibyte_p = STRING_MULTIBYTE (it->string);
5552 SET_TEXT_POS (it->current.string_pos, 0, 0);
5553 it->method = GET_FROM_STRING;
5554 it->stop_charpos = 0;
5555 it->end_charpos = SCHARS (it->string);
5556 if (it->cmp_it.stop_pos >= 0)
5557 it->cmp_it.stop_pos = 0;
5558 it->prev_stop = 0;
5559 it->base_level_stop = 0;
5560
5561 /* Set up the bidi iterator for this overlay string. */
5562 if (it->bidi_p)
5563 {
5564 it->bidi_it.string.lstring = it->string;
5565 it->bidi_it.string.s = NULL;
5566 it->bidi_it.string.schars = SCHARS (it->string);
5567 it->bidi_it.string.bufpos = it->overlay_strings_charpos;
5568 it->bidi_it.string.from_disp_str = it->string_from_display_prop_p;
5569 it->bidi_it.string.unibyte = !it->multibyte_p;
5570 it->bidi_it.w = it->w;
5571 bidi_init_it (0, 0, FRAME_WINDOW_P (it->f), &it->bidi_it);
5572 }
5573 }
5574
5575 CHECK_IT (it);
5576 }
5577
5578
5579 /* Compare two overlay_entry structures E1 and E2. Used as a
5580 comparison function for qsort in load_overlay_strings. Overlay
5581 strings for the same position are sorted so that
5582
5583 1. All after-strings come in front of before-strings, except
5584 when they come from the same overlay.
5585
5586 2. Within after-strings, strings are sorted so that overlay strings
5587 from overlays with higher priorities come first.
5588
5589 2. Within before-strings, strings are sorted so that overlay
5590 strings from overlays with higher priorities come last.
5591
5592 Value is analogous to strcmp. */
5593
5594
5595 static int
5596 compare_overlay_entries (const void *e1, const void *e2)
5597 {
5598 struct overlay_entry const *entry1 = e1;
5599 struct overlay_entry const *entry2 = e2;
5600 int result;
5601
5602 if (entry1->after_string_p != entry2->after_string_p)
5603 {
5604 /* Let after-strings appear in front of before-strings if
5605 they come from different overlays. */
5606 if (EQ (entry1->overlay, entry2->overlay))
5607 result = entry1->after_string_p ? 1 : -1;
5608 else
5609 result = entry1->after_string_p ? -1 : 1;
5610 }
5611 else if (entry1->priority != entry2->priority)
5612 {
5613 if (entry1->after_string_p)
5614 /* After-strings sorted in order of decreasing priority. */
5615 result = entry2->priority < entry1->priority ? -1 : 1;
5616 else
5617 /* Before-strings sorted in order of increasing priority. */
5618 result = entry1->priority < entry2->priority ? -1 : 1;
5619 }
5620 else
5621 result = 0;
5622
5623 return result;
5624 }
5625
5626
5627 /* Load the vector IT->overlay_strings with overlay strings from IT's
5628 current buffer position, or from CHARPOS if that is > 0. Set
5629 IT->n_overlays to the total number of overlay strings found.
5630
5631 Overlay strings are processed OVERLAY_STRING_CHUNK_SIZE strings at
5632 a time. On entry into load_overlay_strings,
5633 IT->current.overlay_string_index gives the number of overlay
5634 strings that have already been loaded by previous calls to this
5635 function.
5636
5637 IT->add_overlay_start contains an additional overlay start
5638 position to consider for taking overlay strings from, if non-zero.
5639 This position comes into play when the overlay has an `invisible'
5640 property, and both before and after-strings. When we've skipped to
5641 the end of the overlay, because of its `invisible' property, we
5642 nevertheless want its before-string to appear.
5643 IT->add_overlay_start will contain the overlay start position
5644 in this case.
5645
5646 Overlay strings are sorted so that after-string strings come in
5647 front of before-string strings. Within before and after-strings,
5648 strings are sorted by overlay priority. See also function
5649 compare_overlay_entries. */
5650
5651 static void
5652 load_overlay_strings (struct it *it, ptrdiff_t charpos)
5653 {
5654 Lisp_Object overlay, window, str, invisible;
5655 struct Lisp_Overlay *ov;
5656 ptrdiff_t start, end;
5657 ptrdiff_t n = 0, i, j;
5658 int invis_p;
5659 struct overlay_entry entriesbuf[20];
5660 ptrdiff_t size = ARRAYELTS (entriesbuf);
5661 struct overlay_entry *entries = entriesbuf;
5662 USE_SAFE_ALLOCA;
5663
5664 if (charpos <= 0)
5665 charpos = IT_CHARPOS (*it);
5666
5667 /* Append the overlay string STRING of overlay OVERLAY to vector
5668 `entries' which has size `size' and currently contains `n'
5669 elements. AFTER_P non-zero means STRING is an after-string of
5670 OVERLAY. */
5671 #define RECORD_OVERLAY_STRING(OVERLAY, STRING, AFTER_P) \
5672 do \
5673 { \
5674 Lisp_Object priority; \
5675 \
5676 if (n == size) \
5677 { \
5678 struct overlay_entry *old = entries; \
5679 SAFE_NALLOCA (entries, 2, size); \
5680 memcpy (entries, old, size * sizeof *entries); \
5681 size *= 2; \
5682 } \
5683 \
5684 entries[n].string = (STRING); \
5685 entries[n].overlay = (OVERLAY); \
5686 priority = Foverlay_get ((OVERLAY), Qpriority); \
5687 entries[n].priority = INTEGERP (priority) ? XINT (priority) : 0; \
5688 entries[n].after_string_p = (AFTER_P); \
5689 ++n; \
5690 } \
5691 while (0)
5692
5693 /* Process overlay before the overlay center. */
5694 for (ov = current_buffer->overlays_before; ov; ov = ov->next)
5695 {
5696 XSETMISC (overlay, ov);
5697 eassert (OVERLAYP (overlay));
5698 start = OVERLAY_POSITION (OVERLAY_START (overlay));
5699 end = OVERLAY_POSITION (OVERLAY_END (overlay));
5700
5701 if (end < charpos)
5702 break;
5703
5704 /* Skip this overlay if it doesn't start or end at IT's current
5705 position. */
5706 if (end != charpos && start != charpos)
5707 continue;
5708
5709 /* Skip this overlay if it doesn't apply to IT->w. */
5710 window = Foverlay_get (overlay, Qwindow);
5711 if (WINDOWP (window) && XWINDOW (window) != it->w)
5712 continue;
5713
5714 /* If the text ``under'' the overlay is invisible, both before-
5715 and after-strings from this overlay are visible; start and
5716 end position are indistinguishable. */
5717 invisible = Foverlay_get (overlay, Qinvisible);
5718 invis_p = TEXT_PROP_MEANS_INVISIBLE (invisible);
5719
5720 /* If overlay has a non-empty before-string, record it. */
5721 if ((start == charpos || (end == charpos && invis_p))
5722 && (str = Foverlay_get (overlay, Qbefore_string), STRINGP (str))
5723 && SCHARS (str))
5724 RECORD_OVERLAY_STRING (overlay, str, 0);
5725
5726 /* If overlay has a non-empty after-string, record it. */
5727 if ((end == charpos || (start == charpos && invis_p))
5728 && (str = Foverlay_get (overlay, Qafter_string), STRINGP (str))
5729 && SCHARS (str))
5730 RECORD_OVERLAY_STRING (overlay, str, 1);
5731 }
5732
5733 /* Process overlays after the overlay center. */
5734 for (ov = current_buffer->overlays_after; ov; ov = ov->next)
5735 {
5736 XSETMISC (overlay, ov);
5737 eassert (OVERLAYP (overlay));
5738 start = OVERLAY_POSITION (OVERLAY_START (overlay));
5739 end = OVERLAY_POSITION (OVERLAY_END (overlay));
5740
5741 if (start > charpos)
5742 break;
5743
5744 /* Skip this overlay if it doesn't start or end at IT's current
5745 position. */
5746 if (end != charpos && start != charpos)
5747 continue;
5748
5749 /* Skip this overlay if it doesn't apply to IT->w. */
5750 window = Foverlay_get (overlay, Qwindow);
5751 if (WINDOWP (window) && XWINDOW (window) != it->w)
5752 continue;
5753
5754 /* If the text ``under'' the overlay is invisible, it has a zero
5755 dimension, and both before- and after-strings apply. */
5756 invisible = Foverlay_get (overlay, Qinvisible);
5757 invis_p = TEXT_PROP_MEANS_INVISIBLE (invisible);
5758
5759 /* If overlay has a non-empty before-string, record it. */
5760 if ((start == charpos || (end == charpos && invis_p))
5761 && (str = Foverlay_get (overlay, Qbefore_string), STRINGP (str))
5762 && SCHARS (str))
5763 RECORD_OVERLAY_STRING (overlay, str, 0);
5764
5765 /* If overlay has a non-empty after-string, record it. */
5766 if ((end == charpos || (start == charpos && invis_p))
5767 && (str = Foverlay_get (overlay, Qafter_string), STRINGP (str))
5768 && SCHARS (str))
5769 RECORD_OVERLAY_STRING (overlay, str, 1);
5770 }
5771
5772 #undef RECORD_OVERLAY_STRING
5773
5774 /* Sort entries. */
5775 if (n > 1)
5776 qsort (entries, n, sizeof *entries, compare_overlay_entries);
5777
5778 /* Record number of overlay strings, and where we computed it. */
5779 it->n_overlay_strings = n;
5780 it->overlay_strings_charpos = charpos;
5781
5782 /* IT->current.overlay_string_index is the number of overlay strings
5783 that have already been consumed by IT. Copy some of the
5784 remaining overlay strings to IT->overlay_strings. */
5785 i = 0;
5786 j = it->current.overlay_string_index;
5787 while (i < OVERLAY_STRING_CHUNK_SIZE && j < n)
5788 {
5789 it->overlay_strings[i] = entries[j].string;
5790 it->string_overlays[i++] = entries[j++].overlay;
5791 }
5792
5793 CHECK_IT (it);
5794 SAFE_FREE ();
5795 }
5796
5797
5798 /* Get the first chunk of overlay strings at IT's current buffer
5799 position, or at CHARPOS if that is > 0. Value is non-zero if at
5800 least one overlay string was found. */
5801
5802 static int
5803 get_overlay_strings_1 (struct it *it, ptrdiff_t charpos, int compute_stop_p)
5804 {
5805 /* Get the first OVERLAY_STRING_CHUNK_SIZE overlay strings to
5806 process. This fills IT->overlay_strings with strings, and sets
5807 IT->n_overlay_strings to the total number of strings to process.
5808 IT->pos.overlay_string_index has to be set temporarily to zero
5809 because load_overlay_strings needs this; it must be set to -1
5810 when no overlay strings are found because a zero value would
5811 indicate a position in the first overlay string. */
5812 it->current.overlay_string_index = 0;
5813 load_overlay_strings (it, charpos);
5814
5815 /* If we found overlay strings, set up IT to deliver display
5816 elements from the first one. Otherwise set up IT to deliver
5817 from current_buffer. */
5818 if (it->n_overlay_strings)
5819 {
5820 /* Make sure we know settings in current_buffer, so that we can
5821 restore meaningful values when we're done with the overlay
5822 strings. */
5823 if (compute_stop_p)
5824 compute_stop_pos (it);
5825 eassert (it->face_id >= 0);
5826
5827 /* Save IT's settings. They are restored after all overlay
5828 strings have been processed. */
5829 eassert (!compute_stop_p || it->sp == 0);
5830
5831 /* When called from handle_stop, there might be an empty display
5832 string loaded. In that case, don't bother saving it. But
5833 don't use this optimization with the bidi iterator, since we
5834 need the corresponding pop_it call to resync the bidi
5835 iterator's position with IT's position, after we are done
5836 with the overlay strings. (The corresponding call to pop_it
5837 in case of an empty display string is in
5838 next_overlay_string.) */
5839 if (!(!it->bidi_p
5840 && STRINGP (it->string) && !SCHARS (it->string)))
5841 push_it (it, NULL);
5842
5843 /* Set up IT to deliver display elements from the first overlay
5844 string. */
5845 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = 0;
5846 it->string = it->overlay_strings[0];
5847 it->from_overlay = Qnil;
5848 it->stop_charpos = 0;
5849 eassert (STRINGP (it->string));
5850 it->end_charpos = SCHARS (it->string);
5851 it->prev_stop = 0;
5852 it->base_level_stop = 0;
5853 it->multibyte_p = STRING_MULTIBYTE (it->string);
5854 it->method = GET_FROM_STRING;
5855 it->from_disp_prop_p = 0;
5856
5857 /* Force paragraph direction to be that of the parent
5858 buffer. */
5859 if (it->bidi_p && it->bidi_it.paragraph_dir == R2L)
5860 it->paragraph_embedding = it->bidi_it.paragraph_dir;
5861 else
5862 it->paragraph_embedding = L2R;
5863
5864 /* Set up the bidi iterator for this overlay string. */
5865 if (it->bidi_p)
5866 {
5867 ptrdiff_t pos = (charpos > 0 ? charpos : IT_CHARPOS (*it));
5868
5869 it->bidi_it.string.lstring = it->string;
5870 it->bidi_it.string.s = NULL;
5871 it->bidi_it.string.schars = SCHARS (it->string);
5872 it->bidi_it.string.bufpos = pos;
5873 it->bidi_it.string.from_disp_str = it->string_from_display_prop_p;
5874 it->bidi_it.string.unibyte = !it->multibyte_p;
5875 it->bidi_it.w = it->w;
5876 bidi_init_it (0, 0, FRAME_WINDOW_P (it->f), &it->bidi_it);
5877 }
5878 return 1;
5879 }
5880
5881 it->current.overlay_string_index = -1;
5882 return 0;
5883 }
5884
5885 static int
5886 get_overlay_strings (struct it *it, ptrdiff_t charpos)
5887 {
5888 it->string = Qnil;
5889 it->method = GET_FROM_BUFFER;
5890
5891 (void) get_overlay_strings_1 (it, charpos, 1);
5892
5893 CHECK_IT (it);
5894
5895 /* Value is non-zero if we found at least one overlay string. */
5896 return STRINGP (it->string);
5897 }
5898
5899
5900 \f
5901 /***********************************************************************
5902 Saving and restoring state
5903 ***********************************************************************/
5904
5905 /* Save current settings of IT on IT->stack. Called, for example,
5906 before setting up IT for an overlay string, to be able to restore
5907 IT's settings to what they were after the overlay string has been
5908 processed. If POSITION is non-NULL, it is the position to save on
5909 the stack instead of IT->position. */
5910
5911 static void
5912 push_it (struct it *it, struct text_pos *position)
5913 {
5914 struct iterator_stack_entry *p;
5915
5916 eassert (it->sp < IT_STACK_SIZE);
5917 p = it->stack + it->sp;
5918
5919 p->stop_charpos = it->stop_charpos;
5920 p->prev_stop = it->prev_stop;
5921 p->base_level_stop = it->base_level_stop;
5922 p->cmp_it = it->cmp_it;
5923 eassert (it->face_id >= 0);
5924 p->face_id = it->face_id;
5925 p->string = it->string;
5926 p->method = it->method;
5927 p->from_overlay = it->from_overlay;
5928 switch (p->method)
5929 {
5930 case GET_FROM_IMAGE:
5931 p->u.image.object = it->object;
5932 p->u.image.image_id = it->image_id;
5933 p->u.image.slice = it->slice;
5934 break;
5935 case GET_FROM_STRETCH:
5936 p->u.stretch.object = it->object;
5937 break;
5938 }
5939 p->position = position ? *position : it->position;
5940 p->current = it->current;
5941 p->end_charpos = it->end_charpos;
5942 p->string_nchars = it->string_nchars;
5943 p->area = it->area;
5944 p->multibyte_p = it->multibyte_p;
5945 p->avoid_cursor_p = it->avoid_cursor_p;
5946 p->space_width = it->space_width;
5947 p->font_height = it->font_height;
5948 p->voffset = it->voffset;
5949 p->string_from_display_prop_p = it->string_from_display_prop_p;
5950 p->string_from_prefix_prop_p = it->string_from_prefix_prop_p;
5951 p->display_ellipsis_p = 0;
5952 p->line_wrap = it->line_wrap;
5953 p->bidi_p = it->bidi_p;
5954 p->paragraph_embedding = it->paragraph_embedding;
5955 p->from_disp_prop_p = it->from_disp_prop_p;
5956 ++it->sp;
5957
5958 /* Save the state of the bidi iterator as well. */
5959 if (it->bidi_p)
5960 bidi_push_it (&it->bidi_it);
5961 }
5962
5963 static void
5964 iterate_out_of_display_property (struct it *it)
5965 {
5966 int buffer_p = !STRINGP (it->string);
5967 ptrdiff_t eob = (buffer_p ? ZV : it->end_charpos);
5968 ptrdiff_t bob = (buffer_p ? BEGV : 0);
5969
5970 eassert (eob >= CHARPOS (it->position) && CHARPOS (it->position) >= bob);
5971
5972 /* Maybe initialize paragraph direction. If we are at the beginning
5973 of a new paragraph, next_element_from_buffer may not have a
5974 chance to do that. */
5975 if (it->bidi_it.first_elt && it->bidi_it.charpos < eob)
5976 bidi_paragraph_init (it->paragraph_embedding, &it->bidi_it, 1);
5977 /* prev_stop can be zero, so check against BEGV as well. */
5978 while (it->bidi_it.charpos >= bob
5979 && it->prev_stop <= it->bidi_it.charpos
5980 && it->bidi_it.charpos < CHARPOS (it->position)
5981 && it->bidi_it.charpos < eob)
5982 bidi_move_to_visually_next (&it->bidi_it);
5983 /* Record the stop_pos we just crossed, for when we cross it
5984 back, maybe. */
5985 if (it->bidi_it.charpos > CHARPOS (it->position))
5986 it->prev_stop = CHARPOS (it->position);
5987 /* If we ended up not where pop_it put us, resync IT's
5988 positional members with the bidi iterator. */
5989 if (it->bidi_it.charpos != CHARPOS (it->position))
5990 SET_TEXT_POS (it->position, it->bidi_it.charpos, it->bidi_it.bytepos);
5991 if (buffer_p)
5992 it->current.pos = it->position;
5993 else
5994 it->current.string_pos = it->position;
5995 }
5996
5997 /* Restore IT's settings from IT->stack. Called, for example, when no
5998 more overlay strings must be processed, and we return to delivering
5999 display elements from a buffer, or when the end of a string from a
6000 `display' property is reached and we return to delivering display
6001 elements from an overlay string, or from a buffer. */
6002
6003 static void
6004 pop_it (struct it *it)
6005 {
6006 struct iterator_stack_entry *p;
6007 int from_display_prop = it->from_disp_prop_p;
6008
6009 eassert (it->sp > 0);
6010 --it->sp;
6011 p = it->stack + it->sp;
6012 it->stop_charpos = p->stop_charpos;
6013 it->prev_stop = p->prev_stop;
6014 it->base_level_stop = p->base_level_stop;
6015 it->cmp_it = p->cmp_it;
6016 it->face_id = p->face_id;
6017 it->current = p->current;
6018 it->position = p->position;
6019 it->string = p->string;
6020 it->from_overlay = p->from_overlay;
6021 if (NILP (it->string))
6022 SET_TEXT_POS (it->current.string_pos, -1, -1);
6023 it->method = p->method;
6024 switch (it->method)
6025 {
6026 case GET_FROM_IMAGE:
6027 it->image_id = p->u.image.image_id;
6028 it->object = p->u.image.object;
6029 it->slice = p->u.image.slice;
6030 break;
6031 case GET_FROM_STRETCH:
6032 it->object = p->u.stretch.object;
6033 break;
6034 case GET_FROM_BUFFER:
6035 it->object = it->w->contents;
6036 break;
6037 case GET_FROM_STRING:
6038 {
6039 struct face *face = FACE_FROM_ID (it->f, it->face_id);
6040
6041 /* Restore the face_box_p flag, since it could have been
6042 overwritten by the face of the object that we just finished
6043 displaying. */
6044 if (face)
6045 it->face_box_p = face->box != FACE_NO_BOX;
6046 it->object = it->string;
6047 }
6048 break;
6049 case GET_FROM_DISPLAY_VECTOR:
6050 if (it->s)
6051 it->method = GET_FROM_C_STRING;
6052 else if (STRINGP (it->string))
6053 it->method = GET_FROM_STRING;
6054 else
6055 {
6056 it->method = GET_FROM_BUFFER;
6057 it->object = it->w->contents;
6058 }
6059 }
6060 it->end_charpos = p->end_charpos;
6061 it->string_nchars = p->string_nchars;
6062 it->area = p->area;
6063 it->multibyte_p = p->multibyte_p;
6064 it->avoid_cursor_p = p->avoid_cursor_p;
6065 it->space_width = p->space_width;
6066 it->font_height = p->font_height;
6067 it->voffset = p->voffset;
6068 it->string_from_display_prop_p = p->string_from_display_prop_p;
6069 it->string_from_prefix_prop_p = p->string_from_prefix_prop_p;
6070 it->line_wrap = p->line_wrap;
6071 it->bidi_p = p->bidi_p;
6072 it->paragraph_embedding = p->paragraph_embedding;
6073 it->from_disp_prop_p = p->from_disp_prop_p;
6074 if (it->bidi_p)
6075 {
6076 bidi_pop_it (&it->bidi_it);
6077 /* Bidi-iterate until we get out of the portion of text, if any,
6078 covered by a `display' text property or by an overlay with
6079 `display' property. (We cannot just jump there, because the
6080 internal coherency of the bidi iterator state can not be
6081 preserved across such jumps.) We also must determine the
6082 paragraph base direction if the overlay we just processed is
6083 at the beginning of a new paragraph. */
6084 if (from_display_prop
6085 && (it->method == GET_FROM_BUFFER || it->method == GET_FROM_STRING))
6086 iterate_out_of_display_property (it);
6087
6088 eassert ((BUFFERP (it->object)
6089 && IT_CHARPOS (*it) == it->bidi_it.charpos
6090 && IT_BYTEPOS (*it) == it->bidi_it.bytepos)
6091 || (STRINGP (it->object)
6092 && IT_STRING_CHARPOS (*it) == it->bidi_it.charpos
6093 && IT_STRING_BYTEPOS (*it) == it->bidi_it.bytepos)
6094 || (CONSP (it->object) && it->method == GET_FROM_STRETCH));
6095 }
6096 }
6097
6098
6099 \f
6100 /***********************************************************************
6101 Moving over lines
6102 ***********************************************************************/
6103
6104 /* Set IT's current position to the previous line start. */
6105
6106 static void
6107 back_to_previous_line_start (struct it *it)
6108 {
6109 ptrdiff_t cp = IT_CHARPOS (*it), bp = IT_BYTEPOS (*it);
6110
6111 DEC_BOTH (cp, bp);
6112 IT_CHARPOS (*it) = find_newline_no_quit (cp, bp, -1, &IT_BYTEPOS (*it));
6113 }
6114
6115
6116 /* Move IT to the next line start.
6117
6118 Value is non-zero if a newline was found. Set *SKIPPED_P to 1 if
6119 we skipped over part of the text (as opposed to moving the iterator
6120 continuously over the text). Otherwise, don't change the value
6121 of *SKIPPED_P.
6122
6123 If BIDI_IT_PREV is non-NULL, store into it the state of the bidi
6124 iterator on the newline, if it was found.
6125
6126 Newlines may come from buffer text, overlay strings, or strings
6127 displayed via the `display' property. That's the reason we can't
6128 simply use find_newline_no_quit.
6129
6130 Note that this function may not skip over invisible text that is so
6131 because of text properties and immediately follows a newline. If
6132 it would, function reseat_at_next_visible_line_start, when called
6133 from set_iterator_to_next, would effectively make invisible
6134 characters following a newline part of the wrong glyph row, which
6135 leads to wrong cursor motion. */
6136
6137 static int
6138 forward_to_next_line_start (struct it *it, int *skipped_p,
6139 struct bidi_it *bidi_it_prev)
6140 {
6141 ptrdiff_t old_selective;
6142 int newline_found_p, n;
6143 const int MAX_NEWLINE_DISTANCE = 500;
6144
6145 /* If already on a newline, just consume it to avoid unintended
6146 skipping over invisible text below. */
6147 if (it->what == IT_CHARACTER
6148 && it->c == '\n'
6149 && CHARPOS (it->position) == IT_CHARPOS (*it))
6150 {
6151 if (it->bidi_p && bidi_it_prev)
6152 *bidi_it_prev = it->bidi_it;
6153 set_iterator_to_next (it, 0);
6154 it->c = 0;
6155 return 1;
6156 }
6157
6158 /* Don't handle selective display in the following. It's (a)
6159 unnecessary because it's done by the caller, and (b) leads to an
6160 infinite recursion because next_element_from_ellipsis indirectly
6161 calls this function. */
6162 old_selective = it->selective;
6163 it->selective = 0;
6164
6165 /* Scan for a newline within MAX_NEWLINE_DISTANCE display elements
6166 from buffer text. */
6167 for (n = newline_found_p = 0;
6168 !newline_found_p && n < MAX_NEWLINE_DISTANCE;
6169 n += STRINGP (it->string) ? 0 : 1)
6170 {
6171 if (!get_next_display_element (it))
6172 return 0;
6173 newline_found_p = it->what == IT_CHARACTER && it->c == '\n';
6174 if (newline_found_p && it->bidi_p && bidi_it_prev)
6175 *bidi_it_prev = it->bidi_it;
6176 set_iterator_to_next (it, 0);
6177 }
6178
6179 /* If we didn't find a newline near enough, see if we can use a
6180 short-cut. */
6181 if (!newline_found_p)
6182 {
6183 ptrdiff_t bytepos, start = IT_CHARPOS (*it);
6184 ptrdiff_t limit = find_newline_no_quit (start, IT_BYTEPOS (*it),
6185 1, &bytepos);
6186 Lisp_Object pos;
6187
6188 eassert (!STRINGP (it->string));
6189
6190 /* If there isn't any `display' property in sight, and no
6191 overlays, we can just use the position of the newline in
6192 buffer text. */
6193 if (it->stop_charpos >= limit
6194 || ((pos = Fnext_single_property_change (make_number (start),
6195 Qdisplay, Qnil,
6196 make_number (limit)),
6197 NILP (pos))
6198 && next_overlay_change (start) == ZV))
6199 {
6200 if (!it->bidi_p)
6201 {
6202 IT_CHARPOS (*it) = limit;
6203 IT_BYTEPOS (*it) = bytepos;
6204 }
6205 else
6206 {
6207 struct bidi_it bprev;
6208
6209 /* Help bidi.c avoid expensive searches for display
6210 properties and overlays, by telling it that there are
6211 none up to `limit'. */
6212 if (it->bidi_it.disp_pos < limit)
6213 {
6214 it->bidi_it.disp_pos = limit;
6215 it->bidi_it.disp_prop = 0;
6216 }
6217 do {
6218 bprev = it->bidi_it;
6219 bidi_move_to_visually_next (&it->bidi_it);
6220 } while (it->bidi_it.charpos != limit);
6221 IT_CHARPOS (*it) = limit;
6222 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
6223 if (bidi_it_prev)
6224 *bidi_it_prev = bprev;
6225 }
6226 *skipped_p = newline_found_p = true;
6227 }
6228 else
6229 {
6230 while (get_next_display_element (it)
6231 && !newline_found_p)
6232 {
6233 newline_found_p = ITERATOR_AT_END_OF_LINE_P (it);
6234 if (newline_found_p && it->bidi_p && bidi_it_prev)
6235 *bidi_it_prev = it->bidi_it;
6236 set_iterator_to_next (it, 0);
6237 }
6238 }
6239 }
6240
6241 it->selective = old_selective;
6242 return newline_found_p;
6243 }
6244
6245
6246 /* Set IT's current position to the previous visible line start. Skip
6247 invisible text that is so either due to text properties or due to
6248 selective display. Caution: this does not change IT->current_x and
6249 IT->hpos. */
6250
6251 static void
6252 back_to_previous_visible_line_start (struct it *it)
6253 {
6254 while (IT_CHARPOS (*it) > BEGV)
6255 {
6256 back_to_previous_line_start (it);
6257
6258 if (IT_CHARPOS (*it) <= BEGV)
6259 break;
6260
6261 /* If selective > 0, then lines indented more than its value are
6262 invisible. */
6263 if (it->selective > 0
6264 && indented_beyond_p (IT_CHARPOS (*it), IT_BYTEPOS (*it),
6265 it->selective))
6266 continue;
6267
6268 /* Check the newline before point for invisibility. */
6269 {
6270 Lisp_Object prop;
6271 prop = Fget_char_property (make_number (IT_CHARPOS (*it) - 1),
6272 Qinvisible, it->window);
6273 if (TEXT_PROP_MEANS_INVISIBLE (prop))
6274 continue;
6275 }
6276
6277 if (IT_CHARPOS (*it) <= BEGV)
6278 break;
6279
6280 {
6281 struct it it2;
6282 void *it2data = NULL;
6283 ptrdiff_t pos;
6284 ptrdiff_t beg, end;
6285 Lisp_Object val, overlay;
6286
6287 SAVE_IT (it2, *it, it2data);
6288
6289 /* If newline is part of a composition, continue from start of composition */
6290 if (find_composition (IT_CHARPOS (*it), -1, &beg, &end, &val, Qnil)
6291 && beg < IT_CHARPOS (*it))
6292 goto replaced;
6293
6294 /* If newline is replaced by a display property, find start of overlay
6295 or interval and continue search from that point. */
6296 pos = --IT_CHARPOS (it2);
6297 --IT_BYTEPOS (it2);
6298 it2.sp = 0;
6299 bidi_unshelve_cache (NULL, 0);
6300 it2.string_from_display_prop_p = 0;
6301 it2.from_disp_prop_p = 0;
6302 if (handle_display_prop (&it2) == HANDLED_RETURN
6303 && !NILP (val = get_char_property_and_overlay
6304 (make_number (pos), Qdisplay, Qnil, &overlay))
6305 && (OVERLAYP (overlay)
6306 ? (beg = OVERLAY_POSITION (OVERLAY_START (overlay)))
6307 : get_property_and_range (pos, Qdisplay, &val, &beg, &end, Qnil)))
6308 {
6309 RESTORE_IT (it, it, it2data);
6310 goto replaced;
6311 }
6312
6313 /* Newline is not replaced by anything -- so we are done. */
6314 RESTORE_IT (it, it, it2data);
6315 break;
6316
6317 replaced:
6318 if (beg < BEGV)
6319 beg = BEGV;
6320 IT_CHARPOS (*it) = beg;
6321 IT_BYTEPOS (*it) = buf_charpos_to_bytepos (current_buffer, beg);
6322 }
6323 }
6324
6325 it->continuation_lines_width = 0;
6326
6327 eassert (IT_CHARPOS (*it) >= BEGV);
6328 eassert (IT_CHARPOS (*it) == BEGV
6329 || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
6330 CHECK_IT (it);
6331 }
6332
6333
6334 /* Reseat iterator IT at the previous visible line start. Skip
6335 invisible text that is so either due to text properties or due to
6336 selective display. At the end, update IT's overlay information,
6337 face information etc. */
6338
6339 void
6340 reseat_at_previous_visible_line_start (struct it *it)
6341 {
6342 back_to_previous_visible_line_start (it);
6343 reseat (it, it->current.pos, 1);
6344 CHECK_IT (it);
6345 }
6346
6347
6348 /* Reseat iterator IT on the next visible line start in the current
6349 buffer. ON_NEWLINE_P non-zero means position IT on the newline
6350 preceding the line start. Skip over invisible text that is so
6351 because of selective display. Compute faces, overlays etc at the
6352 new position. Note that this function does not skip over text that
6353 is invisible because of text properties. */
6354
6355 static void
6356 reseat_at_next_visible_line_start (struct it *it, int on_newline_p)
6357 {
6358 int newline_found_p, skipped_p = 0;
6359 struct bidi_it bidi_it_prev;
6360
6361 newline_found_p = forward_to_next_line_start (it, &skipped_p, &bidi_it_prev);
6362
6363 /* Skip over lines that are invisible because they are indented
6364 more than the value of IT->selective. */
6365 if (it->selective > 0)
6366 while (IT_CHARPOS (*it) < ZV
6367 && indented_beyond_p (IT_CHARPOS (*it), IT_BYTEPOS (*it),
6368 it->selective))
6369 {
6370 eassert (IT_BYTEPOS (*it) == BEGV
6371 || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
6372 newline_found_p =
6373 forward_to_next_line_start (it, &skipped_p, &bidi_it_prev);
6374 }
6375
6376 /* Position on the newline if that's what's requested. */
6377 if (on_newline_p && newline_found_p)
6378 {
6379 if (STRINGP (it->string))
6380 {
6381 if (IT_STRING_CHARPOS (*it) > 0)
6382 {
6383 if (!it->bidi_p)
6384 {
6385 --IT_STRING_CHARPOS (*it);
6386 --IT_STRING_BYTEPOS (*it);
6387 }
6388 else
6389 {
6390 /* We need to restore the bidi iterator to the state
6391 it had on the newline, and resync the IT's
6392 position with that. */
6393 it->bidi_it = bidi_it_prev;
6394 IT_STRING_CHARPOS (*it) = it->bidi_it.charpos;
6395 IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos;
6396 }
6397 }
6398 }
6399 else if (IT_CHARPOS (*it) > BEGV)
6400 {
6401 if (!it->bidi_p)
6402 {
6403 --IT_CHARPOS (*it);
6404 --IT_BYTEPOS (*it);
6405 }
6406 else
6407 {
6408 /* We need to restore the bidi iterator to the state it
6409 had on the newline and resync IT with that. */
6410 it->bidi_it = bidi_it_prev;
6411 IT_CHARPOS (*it) = it->bidi_it.charpos;
6412 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
6413 }
6414 reseat (it, it->current.pos, 0);
6415 }
6416 }
6417 else if (skipped_p)
6418 reseat (it, it->current.pos, 0);
6419
6420 CHECK_IT (it);
6421 }
6422
6423
6424 \f
6425 /***********************************************************************
6426 Changing an iterator's position
6427 ***********************************************************************/
6428
6429 /* Change IT's current position to POS in current_buffer. If FORCE_P
6430 is non-zero, always check for text properties at the new position.
6431 Otherwise, text properties are only looked up if POS >=
6432 IT->check_charpos of a property. */
6433
6434 static void
6435 reseat (struct it *it, struct text_pos pos, int force_p)
6436 {
6437 ptrdiff_t original_pos = IT_CHARPOS (*it);
6438
6439 reseat_1 (it, pos, 0);
6440
6441 /* Determine where to check text properties. Avoid doing it
6442 where possible because text property lookup is very expensive. */
6443 if (force_p
6444 || CHARPOS (pos) > it->stop_charpos
6445 || CHARPOS (pos) < original_pos)
6446 {
6447 if (it->bidi_p)
6448 {
6449 /* For bidi iteration, we need to prime prev_stop and
6450 base_level_stop with our best estimations. */
6451 /* Implementation note: Of course, POS is not necessarily a
6452 stop position, so assigning prev_pos to it is a lie; we
6453 should have called compute_stop_backwards. However, if
6454 the current buffer does not include any R2L characters,
6455 that call would be a waste of cycles, because the
6456 iterator will never move back, and thus never cross this
6457 "fake" stop position. So we delay that backward search
6458 until the time we really need it, in next_element_from_buffer. */
6459 if (CHARPOS (pos) != it->prev_stop)
6460 it->prev_stop = CHARPOS (pos);
6461 if (CHARPOS (pos) < it->base_level_stop)
6462 it->base_level_stop = 0; /* meaning it's unknown */
6463 handle_stop (it);
6464 }
6465 else
6466 {
6467 handle_stop (it);
6468 it->prev_stop = it->base_level_stop = 0;
6469 }
6470
6471 }
6472
6473 CHECK_IT (it);
6474 }
6475
6476
6477 /* Change IT's buffer position to POS. SET_STOP_P non-zero means set
6478 IT->stop_pos to POS, also. */
6479
6480 static void
6481 reseat_1 (struct it *it, struct text_pos pos, int set_stop_p)
6482 {
6483 /* Don't call this function when scanning a C string. */
6484 eassert (it->s == NULL);
6485
6486 /* POS must be a reasonable value. */
6487 eassert (CHARPOS (pos) >= BEGV && CHARPOS (pos) <= ZV);
6488
6489 it->current.pos = it->position = pos;
6490 it->end_charpos = ZV;
6491 it->dpvec = NULL;
6492 it->current.dpvec_index = -1;
6493 it->current.overlay_string_index = -1;
6494 IT_STRING_CHARPOS (*it) = -1;
6495 IT_STRING_BYTEPOS (*it) = -1;
6496 it->string = Qnil;
6497 it->method = GET_FROM_BUFFER;
6498 it->object = it->w->contents;
6499 it->area = TEXT_AREA;
6500 it->multibyte_p = !NILP (BVAR (current_buffer, enable_multibyte_characters));
6501 it->sp = 0;
6502 it->string_from_display_prop_p = 0;
6503 it->string_from_prefix_prop_p = 0;
6504
6505 it->from_disp_prop_p = 0;
6506 it->face_before_selective_p = 0;
6507 if (it->bidi_p)
6508 {
6509 bidi_init_it (IT_CHARPOS (*it), IT_BYTEPOS (*it), FRAME_WINDOW_P (it->f),
6510 &it->bidi_it);
6511 bidi_unshelve_cache (NULL, 0);
6512 it->bidi_it.paragraph_dir = NEUTRAL_DIR;
6513 it->bidi_it.string.s = NULL;
6514 it->bidi_it.string.lstring = Qnil;
6515 it->bidi_it.string.bufpos = 0;
6516 it->bidi_it.string.from_disp_str = 0;
6517 it->bidi_it.string.unibyte = 0;
6518 it->bidi_it.w = it->w;
6519 }
6520
6521 if (set_stop_p)
6522 {
6523 it->stop_charpos = CHARPOS (pos);
6524 it->base_level_stop = CHARPOS (pos);
6525 }
6526 /* This make the information stored in it->cmp_it invalidate. */
6527 it->cmp_it.id = -1;
6528 }
6529
6530
6531 /* Set up IT for displaying a string, starting at CHARPOS in window W.
6532 If S is non-null, it is a C string to iterate over. Otherwise,
6533 STRING gives a Lisp string to iterate over.
6534
6535 If PRECISION > 0, don't return more then PRECISION number of
6536 characters from the string.
6537
6538 If FIELD_WIDTH > 0, return padding spaces until FIELD_WIDTH
6539 characters have been returned. FIELD_WIDTH < 0 means an infinite
6540 field width.
6541
6542 MULTIBYTE = 0 means disable processing of multibyte characters,
6543 MULTIBYTE > 0 means enable it,
6544 MULTIBYTE < 0 means use IT->multibyte_p.
6545
6546 IT must be initialized via a prior call to init_iterator before
6547 calling this function. */
6548
6549 static void
6550 reseat_to_string (struct it *it, const char *s, Lisp_Object string,
6551 ptrdiff_t charpos, ptrdiff_t precision, int field_width,
6552 int multibyte)
6553 {
6554 /* No text property checks performed by default, but see below. */
6555 it->stop_charpos = -1;
6556
6557 /* Set iterator position and end position. */
6558 memset (&it->current, 0, sizeof it->current);
6559 it->current.overlay_string_index = -1;
6560 it->current.dpvec_index = -1;
6561 eassert (charpos >= 0);
6562
6563 /* If STRING is specified, use its multibyteness, otherwise use the
6564 setting of MULTIBYTE, if specified. */
6565 if (multibyte >= 0)
6566 it->multibyte_p = multibyte > 0;
6567
6568 /* Bidirectional reordering of strings is controlled by the default
6569 value of bidi-display-reordering. Don't try to reorder while
6570 loading loadup.el, as the necessary character property tables are
6571 not yet available. */
6572 it->bidi_p =
6573 NILP (Vpurify_flag)
6574 && !NILP (BVAR (&buffer_defaults, bidi_display_reordering));
6575
6576 if (s == NULL)
6577 {
6578 eassert (STRINGP (string));
6579 it->string = string;
6580 it->s = NULL;
6581 it->end_charpos = it->string_nchars = SCHARS (string);
6582 it->method = GET_FROM_STRING;
6583 it->current.string_pos = string_pos (charpos, string);
6584
6585 if (it->bidi_p)
6586 {
6587 it->bidi_it.string.lstring = string;
6588 it->bidi_it.string.s = NULL;
6589 it->bidi_it.string.schars = it->end_charpos;
6590 it->bidi_it.string.bufpos = 0;
6591 it->bidi_it.string.from_disp_str = 0;
6592 it->bidi_it.string.unibyte = !it->multibyte_p;
6593 it->bidi_it.w = it->w;
6594 bidi_init_it (charpos, IT_STRING_BYTEPOS (*it),
6595 FRAME_WINDOW_P (it->f), &it->bidi_it);
6596 }
6597 }
6598 else
6599 {
6600 it->s = (const unsigned char *) s;
6601 it->string = Qnil;
6602
6603 /* Note that we use IT->current.pos, not it->current.string_pos,
6604 for displaying C strings. */
6605 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = -1;
6606 if (it->multibyte_p)
6607 {
6608 it->current.pos = c_string_pos (charpos, s, 1);
6609 it->end_charpos = it->string_nchars = number_of_chars (s, 1);
6610 }
6611 else
6612 {
6613 IT_CHARPOS (*it) = IT_BYTEPOS (*it) = charpos;
6614 it->end_charpos = it->string_nchars = strlen (s);
6615 }
6616
6617 if (it->bidi_p)
6618 {
6619 it->bidi_it.string.lstring = Qnil;
6620 it->bidi_it.string.s = (const unsigned char *) s;
6621 it->bidi_it.string.schars = it->end_charpos;
6622 it->bidi_it.string.bufpos = 0;
6623 it->bidi_it.string.from_disp_str = 0;
6624 it->bidi_it.string.unibyte = !it->multibyte_p;
6625 it->bidi_it.w = it->w;
6626 bidi_init_it (charpos, IT_BYTEPOS (*it), FRAME_WINDOW_P (it->f),
6627 &it->bidi_it);
6628 }
6629 it->method = GET_FROM_C_STRING;
6630 }
6631
6632 /* PRECISION > 0 means don't return more than PRECISION characters
6633 from the string. */
6634 if (precision > 0 && it->end_charpos - charpos > precision)
6635 {
6636 it->end_charpos = it->string_nchars = charpos + precision;
6637 if (it->bidi_p)
6638 it->bidi_it.string.schars = it->end_charpos;
6639 }
6640
6641 /* FIELD_WIDTH > 0 means pad with spaces until FIELD_WIDTH
6642 characters have been returned. FIELD_WIDTH == 0 means don't pad,
6643 FIELD_WIDTH < 0 means infinite field width. This is useful for
6644 padding with `-' at the end of a mode line. */
6645 if (field_width < 0)
6646 field_width = INFINITY;
6647 /* Implementation note: We deliberately don't enlarge
6648 it->bidi_it.string.schars here to fit it->end_charpos, because
6649 the bidi iterator cannot produce characters out of thin air. */
6650 if (field_width > it->end_charpos - charpos)
6651 it->end_charpos = charpos + field_width;
6652
6653 /* Use the standard display table for displaying strings. */
6654 if (DISP_TABLE_P (Vstandard_display_table))
6655 it->dp = XCHAR_TABLE (Vstandard_display_table);
6656
6657 it->stop_charpos = charpos;
6658 it->prev_stop = charpos;
6659 it->base_level_stop = 0;
6660 if (it->bidi_p)
6661 {
6662 it->bidi_it.first_elt = 1;
6663 it->bidi_it.paragraph_dir = NEUTRAL_DIR;
6664 it->bidi_it.disp_pos = -1;
6665 }
6666 if (s == NULL && it->multibyte_p)
6667 {
6668 ptrdiff_t endpos = SCHARS (it->string);
6669 if (endpos > it->end_charpos)
6670 endpos = it->end_charpos;
6671 composition_compute_stop_pos (&it->cmp_it, charpos, -1, endpos,
6672 it->string);
6673 }
6674 CHECK_IT (it);
6675 }
6676
6677
6678 \f
6679 /***********************************************************************
6680 Iteration
6681 ***********************************************************************/
6682
6683 /* Map enum it_method value to corresponding next_element_from_* function. */
6684
6685 static int (* get_next_element[NUM_IT_METHODS]) (struct it *it) =
6686 {
6687 next_element_from_buffer,
6688 next_element_from_display_vector,
6689 next_element_from_string,
6690 next_element_from_c_string,
6691 next_element_from_image,
6692 next_element_from_stretch
6693 };
6694
6695 #define GET_NEXT_DISPLAY_ELEMENT(it) (*get_next_element[(it)->method]) (it)
6696
6697
6698 /* Return 1 iff a character at CHARPOS (and BYTEPOS) is composed
6699 (possibly with the following characters). */
6700
6701 #define CHAR_COMPOSED_P(IT,CHARPOS,BYTEPOS,END_CHARPOS) \
6702 ((IT)->cmp_it.id >= 0 \
6703 || ((IT)->cmp_it.stop_pos == (CHARPOS) \
6704 && composition_reseat_it (&(IT)->cmp_it, CHARPOS, BYTEPOS, \
6705 END_CHARPOS, (IT)->w, \
6706 FACE_FROM_ID ((IT)->f, (IT)->face_id), \
6707 (IT)->string)))
6708
6709
6710 /* Lookup the char-table Vglyphless_char_display for character C (-1
6711 if we want information for no-font case), and return the display
6712 method symbol. By side-effect, update it->what and
6713 it->glyphless_method. This function is called from
6714 get_next_display_element for each character element, and from
6715 x_produce_glyphs when no suitable font was found. */
6716
6717 Lisp_Object
6718 lookup_glyphless_char_display (int c, struct it *it)
6719 {
6720 Lisp_Object glyphless_method = Qnil;
6721
6722 if (CHAR_TABLE_P (Vglyphless_char_display)
6723 && CHAR_TABLE_EXTRA_SLOTS (XCHAR_TABLE (Vglyphless_char_display)) >= 1)
6724 {
6725 if (c >= 0)
6726 {
6727 glyphless_method = CHAR_TABLE_REF (Vglyphless_char_display, c);
6728 if (CONSP (glyphless_method))
6729 glyphless_method = FRAME_WINDOW_P (it->f)
6730 ? XCAR (glyphless_method)
6731 : XCDR (glyphless_method);
6732 }
6733 else
6734 glyphless_method = XCHAR_TABLE (Vglyphless_char_display)->extras[0];
6735 }
6736
6737 retry:
6738 if (NILP (glyphless_method))
6739 {
6740 if (c >= 0)
6741 /* The default is to display the character by a proper font. */
6742 return Qnil;
6743 /* The default for the no-font case is to display an empty box. */
6744 glyphless_method = Qempty_box;
6745 }
6746 if (EQ (glyphless_method, Qzero_width))
6747 {
6748 if (c >= 0)
6749 return glyphless_method;
6750 /* This method can't be used for the no-font case. */
6751 glyphless_method = Qempty_box;
6752 }
6753 if (EQ (glyphless_method, Qthin_space))
6754 it->glyphless_method = GLYPHLESS_DISPLAY_THIN_SPACE;
6755 else if (EQ (glyphless_method, Qempty_box))
6756 it->glyphless_method = GLYPHLESS_DISPLAY_EMPTY_BOX;
6757 else if (EQ (glyphless_method, Qhex_code))
6758 it->glyphless_method = GLYPHLESS_DISPLAY_HEX_CODE;
6759 else if (STRINGP (glyphless_method))
6760 it->glyphless_method = GLYPHLESS_DISPLAY_ACRONYM;
6761 else
6762 {
6763 /* Invalid value. We use the default method. */
6764 glyphless_method = Qnil;
6765 goto retry;
6766 }
6767 it->what = IT_GLYPHLESS;
6768 return glyphless_method;
6769 }
6770
6771 /* Merge escape glyph face and cache the result. */
6772
6773 static struct frame *last_escape_glyph_frame = NULL;
6774 static int last_escape_glyph_face_id = (1 << FACE_ID_BITS);
6775 static int last_escape_glyph_merged_face_id = 0;
6776
6777 static int
6778 merge_escape_glyph_face (struct it *it)
6779 {
6780 int face_id;
6781
6782 if (it->f == last_escape_glyph_frame
6783 && it->face_id == last_escape_glyph_face_id)
6784 face_id = last_escape_glyph_merged_face_id;
6785 else
6786 {
6787 /* Merge the `escape-glyph' face into the current face. */
6788 face_id = merge_faces (it->f, Qescape_glyph, 0, it->face_id);
6789 last_escape_glyph_frame = it->f;
6790 last_escape_glyph_face_id = it->face_id;
6791 last_escape_glyph_merged_face_id = face_id;
6792 }
6793 return face_id;
6794 }
6795
6796 /* Likewise for glyphless glyph face. */
6797
6798 static struct frame *last_glyphless_glyph_frame = NULL;
6799 static int last_glyphless_glyph_face_id = (1 << FACE_ID_BITS);
6800 static int last_glyphless_glyph_merged_face_id = 0;
6801
6802 int
6803 merge_glyphless_glyph_face (struct it *it)
6804 {
6805 int face_id;
6806
6807 if (it->f == last_glyphless_glyph_frame
6808 && it->face_id == last_glyphless_glyph_face_id)
6809 face_id = last_glyphless_glyph_merged_face_id;
6810 else
6811 {
6812 /* Merge the `glyphless-char' face into the current face. */
6813 face_id = merge_faces (it->f, Qglyphless_char, 0, it->face_id);
6814 last_glyphless_glyph_frame = it->f;
6815 last_glyphless_glyph_face_id = it->face_id;
6816 last_glyphless_glyph_merged_face_id = face_id;
6817 }
6818 return face_id;
6819 }
6820
6821 /* Load IT's display element fields with information about the next
6822 display element from the current position of IT. Value is zero if
6823 end of buffer (or C string) is reached. */
6824
6825 static int
6826 get_next_display_element (struct it *it)
6827 {
6828 /* Non-zero means that we found a display element. Zero means that
6829 we hit the end of what we iterate over. Performance note: the
6830 function pointer `method' used here turns out to be faster than
6831 using a sequence of if-statements. */
6832 int success_p;
6833
6834 get_next:
6835 success_p = GET_NEXT_DISPLAY_ELEMENT (it);
6836
6837 if (it->what == IT_CHARACTER)
6838 {
6839 /* UAX#9, L4: "A character is depicted by a mirrored glyph if
6840 and only if (a) the resolved directionality of that character
6841 is R..." */
6842 /* FIXME: Do we need an exception for characters from display
6843 tables? */
6844 if (it->bidi_p && it->bidi_it.type == STRONG_R
6845 && !inhibit_bidi_mirroring)
6846 it->c = bidi_mirror_char (it->c);
6847 /* Map via display table or translate control characters.
6848 IT->c, IT->len etc. have been set to the next character by
6849 the function call above. If we have a display table, and it
6850 contains an entry for IT->c, translate it. Don't do this if
6851 IT->c itself comes from a display table, otherwise we could
6852 end up in an infinite recursion. (An alternative could be to
6853 count the recursion depth of this function and signal an
6854 error when a certain maximum depth is reached.) Is it worth
6855 it? */
6856 if (success_p && it->dpvec == NULL)
6857 {
6858 Lisp_Object dv;
6859 struct charset *unibyte = CHARSET_FROM_ID (charset_unibyte);
6860 int nonascii_space_p = 0;
6861 int nonascii_hyphen_p = 0;
6862 int c = it->c; /* This is the character to display. */
6863
6864 if (! it->multibyte_p && ! ASCII_CHAR_P (c))
6865 {
6866 eassert (SINGLE_BYTE_CHAR_P (c));
6867 if (unibyte_display_via_language_environment)
6868 {
6869 c = DECODE_CHAR (unibyte, c);
6870 if (c < 0)
6871 c = BYTE8_TO_CHAR (it->c);
6872 }
6873 else
6874 c = BYTE8_TO_CHAR (it->c);
6875 }
6876
6877 if (it->dp
6878 && (dv = DISP_CHAR_VECTOR (it->dp, c),
6879 VECTORP (dv)))
6880 {
6881 struct Lisp_Vector *v = XVECTOR (dv);
6882
6883 /* Return the first character from the display table
6884 entry, if not empty. If empty, don't display the
6885 current character. */
6886 if (v->header.size)
6887 {
6888 it->dpvec_char_len = it->len;
6889 it->dpvec = v->contents;
6890 it->dpend = v->contents + v->header.size;
6891 it->current.dpvec_index = 0;
6892 it->dpvec_face_id = -1;
6893 it->saved_face_id = it->face_id;
6894 it->method = GET_FROM_DISPLAY_VECTOR;
6895 it->ellipsis_p = 0;
6896 }
6897 else
6898 {
6899 set_iterator_to_next (it, 0);
6900 }
6901 goto get_next;
6902 }
6903
6904 if (! NILP (lookup_glyphless_char_display (c, it)))
6905 {
6906 if (it->what == IT_GLYPHLESS)
6907 goto done;
6908 /* Don't display this character. */
6909 set_iterator_to_next (it, 0);
6910 goto get_next;
6911 }
6912
6913 /* If `nobreak-char-display' is non-nil, we display
6914 non-ASCII spaces and hyphens specially. */
6915 if (! ASCII_CHAR_P (c) && ! NILP (Vnobreak_char_display))
6916 {
6917 if (c == 0xA0)
6918 nonascii_space_p = true;
6919 else if (c == 0xAD || c == 0x2010 || c == 0x2011)
6920 nonascii_hyphen_p = true;
6921 }
6922
6923 /* Translate control characters into `\003' or `^C' form.
6924 Control characters coming from a display table entry are
6925 currently not translated because we use IT->dpvec to hold
6926 the translation. This could easily be changed but I
6927 don't believe that it is worth doing.
6928
6929 The characters handled by `nobreak-char-display' must be
6930 translated too.
6931
6932 Non-printable characters and raw-byte characters are also
6933 translated to octal form. */
6934 if (((c < ' ' || c == 127) /* ASCII control chars. */
6935 ? (it->area != TEXT_AREA
6936 /* In mode line, treat \n, \t like other crl chars. */
6937 || (c != '\t'
6938 && it->glyph_row
6939 && (it->glyph_row->mode_line_p || it->avoid_cursor_p))
6940 || (c != '\n' && c != '\t'))
6941 : (nonascii_space_p
6942 || nonascii_hyphen_p
6943 || CHAR_BYTE8_P (c)
6944 || ! CHAR_PRINTABLE_P (c))))
6945 {
6946 /* C is a control character, non-ASCII space/hyphen,
6947 raw-byte, or a non-printable character which must be
6948 displayed either as '\003' or as `^C' where the '\\'
6949 and '^' can be defined in the display table. Fill
6950 IT->ctl_chars with glyphs for what we have to
6951 display. Then, set IT->dpvec to these glyphs. */
6952 Lisp_Object gc;
6953 int ctl_len;
6954 int face_id;
6955 int lface_id = 0;
6956 int escape_glyph;
6957
6958 /* Handle control characters with ^. */
6959
6960 if (ASCII_CHAR_P (c) && it->ctl_arrow_p)
6961 {
6962 int g;
6963
6964 g = '^'; /* default glyph for Control */
6965 /* Set IT->ctl_chars[0] to the glyph for `^'. */
6966 if (it->dp
6967 && (gc = DISP_CTRL_GLYPH (it->dp), GLYPH_CODE_P (gc)))
6968 {
6969 g = GLYPH_CODE_CHAR (gc);
6970 lface_id = GLYPH_CODE_FACE (gc);
6971 }
6972
6973 face_id = (lface_id
6974 ? merge_faces (it->f, Qt, lface_id, it->face_id)
6975 : merge_escape_glyph_face (it));
6976
6977 XSETINT (it->ctl_chars[0], g);
6978 XSETINT (it->ctl_chars[1], c ^ 0100);
6979 ctl_len = 2;
6980 goto display_control;
6981 }
6982
6983 /* Handle non-ascii space in the mode where it only gets
6984 highlighting. */
6985
6986 if (nonascii_space_p && EQ (Vnobreak_char_display, Qt))
6987 {
6988 /* Merge `nobreak-space' into the current face. */
6989 face_id = merge_faces (it->f, Qnobreak_space, 0,
6990 it->face_id);
6991 XSETINT (it->ctl_chars[0], ' ');
6992 ctl_len = 1;
6993 goto display_control;
6994 }
6995
6996 /* Handle sequences that start with the "escape glyph". */
6997
6998 /* the default escape glyph is \. */
6999 escape_glyph = '\\';
7000
7001 if (it->dp
7002 && (gc = DISP_ESCAPE_GLYPH (it->dp), GLYPH_CODE_P (gc)))
7003 {
7004 escape_glyph = GLYPH_CODE_CHAR (gc);
7005 lface_id = GLYPH_CODE_FACE (gc);
7006 }
7007
7008 face_id = (lface_id
7009 ? merge_faces (it->f, Qt, lface_id, it->face_id)
7010 : merge_escape_glyph_face (it));
7011
7012 /* Draw non-ASCII hyphen with just highlighting: */
7013
7014 if (nonascii_hyphen_p && EQ (Vnobreak_char_display, Qt))
7015 {
7016 XSETINT (it->ctl_chars[0], '-');
7017 ctl_len = 1;
7018 goto display_control;
7019 }
7020
7021 /* Draw non-ASCII space/hyphen with escape glyph: */
7022
7023 if (nonascii_space_p || nonascii_hyphen_p)
7024 {
7025 XSETINT (it->ctl_chars[0], escape_glyph);
7026 XSETINT (it->ctl_chars[1], nonascii_space_p ? ' ' : '-');
7027 ctl_len = 2;
7028 goto display_control;
7029 }
7030
7031 {
7032 char str[10];
7033 int len, i;
7034
7035 if (CHAR_BYTE8_P (c))
7036 /* Display \200 instead of \17777600. */
7037 c = CHAR_TO_BYTE8 (c);
7038 len = sprintf (str, "%03o", c);
7039
7040 XSETINT (it->ctl_chars[0], escape_glyph);
7041 for (i = 0; i < len; i++)
7042 XSETINT (it->ctl_chars[i + 1], str[i]);
7043 ctl_len = len + 1;
7044 }
7045
7046 display_control:
7047 /* Set up IT->dpvec and return first character from it. */
7048 it->dpvec_char_len = it->len;
7049 it->dpvec = it->ctl_chars;
7050 it->dpend = it->dpvec + ctl_len;
7051 it->current.dpvec_index = 0;
7052 it->dpvec_face_id = face_id;
7053 it->saved_face_id = it->face_id;
7054 it->method = GET_FROM_DISPLAY_VECTOR;
7055 it->ellipsis_p = 0;
7056 goto get_next;
7057 }
7058 it->char_to_display = c;
7059 }
7060 else if (success_p)
7061 {
7062 it->char_to_display = it->c;
7063 }
7064 }
7065
7066 #ifdef HAVE_WINDOW_SYSTEM
7067 /* Adjust face id for a multibyte character. There are no multibyte
7068 character in unibyte text. */
7069 if ((it->what == IT_CHARACTER || it->what == IT_COMPOSITION)
7070 && it->multibyte_p
7071 && success_p
7072 && FRAME_WINDOW_P (it->f))
7073 {
7074 struct face *face = FACE_FROM_ID (it->f, it->face_id);
7075
7076 if (it->what == IT_COMPOSITION && it->cmp_it.ch >= 0)
7077 {
7078 /* Automatic composition with glyph-string. */
7079 Lisp_Object gstring = composition_gstring_from_id (it->cmp_it.id);
7080
7081 it->face_id = face_for_font (it->f, LGSTRING_FONT (gstring), face);
7082 }
7083 else
7084 {
7085 ptrdiff_t pos = (it->s ? -1
7086 : STRINGP (it->string) ? IT_STRING_CHARPOS (*it)
7087 : IT_CHARPOS (*it));
7088 int c;
7089
7090 if (it->what == IT_CHARACTER)
7091 c = it->char_to_display;
7092 else
7093 {
7094 struct composition *cmp = composition_table[it->cmp_it.id];
7095 int i;
7096
7097 c = ' ';
7098 for (i = 0; i < cmp->glyph_len; i++)
7099 /* TAB in a composition means display glyphs with
7100 padding space on the left or right. */
7101 if ((c = COMPOSITION_GLYPH (cmp, i)) != '\t')
7102 break;
7103 }
7104 it->face_id = FACE_FOR_CHAR (it->f, face, c, pos, it->string);
7105 }
7106 }
7107 #endif /* HAVE_WINDOW_SYSTEM */
7108
7109 done:
7110 /* Is this character the last one of a run of characters with
7111 box? If yes, set IT->end_of_box_run_p to 1. */
7112 if (it->face_box_p
7113 && it->s == NULL)
7114 {
7115 if (it->method == GET_FROM_STRING && it->sp)
7116 {
7117 int face_id = underlying_face_id (it);
7118 struct face *face = FACE_FROM_ID (it->f, face_id);
7119
7120 if (face)
7121 {
7122 if (face->box == FACE_NO_BOX)
7123 {
7124 /* If the box comes from face properties in a
7125 display string, check faces in that string. */
7126 int string_face_id = face_after_it_pos (it);
7127 it->end_of_box_run_p
7128 = (FACE_FROM_ID (it->f, string_face_id)->box
7129 == FACE_NO_BOX);
7130 }
7131 /* Otherwise, the box comes from the underlying face.
7132 If this is the last string character displayed, check
7133 the next buffer location. */
7134 else if ((IT_STRING_CHARPOS (*it) >= SCHARS (it->string) - 1)
7135 /* n_overlay_strings is unreliable unless
7136 overlay_string_index is non-negative. */
7137 && ((it->current.overlay_string_index >= 0
7138 && (it->current.overlay_string_index
7139 == it->n_overlay_strings - 1))
7140 /* A string from display property. */
7141 || it->from_disp_prop_p))
7142 {
7143 ptrdiff_t ignore;
7144 int next_face_id;
7145 struct text_pos pos = it->current.pos;
7146
7147 /* For a string from a display property, the next
7148 buffer position is stored in the 'position'
7149 member of the iteration stack slot below the
7150 current one, see handle_single_display_spec. By
7151 contrast, it->current.pos was is not yet updated
7152 to point to that buffer position; that will
7153 happen in pop_it, after we finish displaying the
7154 current string. Note that we already checked
7155 above that it->sp is positive, so subtracting one
7156 from it is safe. */
7157 if (it->from_disp_prop_p)
7158 pos = (it->stack + it->sp - 1)->position;
7159 else
7160 INC_TEXT_POS (pos, it->multibyte_p);
7161
7162 if (CHARPOS (pos) >= ZV)
7163 it->end_of_box_run_p = true;
7164 else
7165 {
7166 next_face_id = face_at_buffer_position
7167 (it->w, CHARPOS (pos), &ignore,
7168 CHARPOS (pos) + TEXT_PROP_DISTANCE_LIMIT, false, -1);
7169 it->end_of_box_run_p
7170 = (FACE_FROM_ID (it->f, next_face_id)->box
7171 == FACE_NO_BOX);
7172 }
7173 }
7174 }
7175 }
7176 /* next_element_from_display_vector sets this flag according to
7177 faces of the display vector glyphs, see there. */
7178 else if (it->method != GET_FROM_DISPLAY_VECTOR)
7179 {
7180 int face_id = face_after_it_pos (it);
7181 it->end_of_box_run_p
7182 = (face_id != it->face_id
7183 && FACE_FROM_ID (it->f, face_id)->box == FACE_NO_BOX);
7184 }
7185 }
7186 /* If we reached the end of the object we've been iterating (e.g., a
7187 display string or an overlay string), and there's something on
7188 IT->stack, proceed with what's on the stack. It doesn't make
7189 sense to return zero if there's unprocessed stuff on the stack,
7190 because otherwise that stuff will never be displayed. */
7191 if (!success_p && it->sp > 0)
7192 {
7193 set_iterator_to_next (it, 0);
7194 success_p = get_next_display_element (it);
7195 }
7196
7197 /* Value is 0 if end of buffer or string reached. */
7198 return success_p;
7199 }
7200
7201
7202 /* Move IT to the next display element.
7203
7204 RESEAT_P non-zero means if called on a newline in buffer text,
7205 skip to the next visible line start.
7206
7207 Functions get_next_display_element and set_iterator_to_next are
7208 separate because I find this arrangement easier to handle than a
7209 get_next_display_element function that also increments IT's
7210 position. The way it is we can first look at an iterator's current
7211 display element, decide whether it fits on a line, and if it does,
7212 increment the iterator position. The other way around we probably
7213 would either need a flag indicating whether the iterator has to be
7214 incremented the next time, or we would have to implement a
7215 decrement position function which would not be easy to write. */
7216
7217 void
7218 set_iterator_to_next (struct it *it, int reseat_p)
7219 {
7220 /* Reset flags indicating start and end of a sequence of characters
7221 with box. Reset them at the start of this function because
7222 moving the iterator to a new position might set them. */
7223 it->start_of_box_run_p = it->end_of_box_run_p = 0;
7224
7225 switch (it->method)
7226 {
7227 case GET_FROM_BUFFER:
7228 /* The current display element of IT is a character from
7229 current_buffer. Advance in the buffer, and maybe skip over
7230 invisible lines that are so because of selective display. */
7231 if (ITERATOR_AT_END_OF_LINE_P (it) && reseat_p)
7232 reseat_at_next_visible_line_start (it, 0);
7233 else if (it->cmp_it.id >= 0)
7234 {
7235 /* We are currently getting glyphs from a composition. */
7236 if (! it->bidi_p)
7237 {
7238 IT_CHARPOS (*it) += it->cmp_it.nchars;
7239 IT_BYTEPOS (*it) += it->cmp_it.nbytes;
7240 }
7241 else
7242 {
7243 int i;
7244
7245 /* Update IT's char/byte positions to point to the first
7246 character of the next grapheme cluster, or to the
7247 character visually after the current composition. */
7248 for (i = 0; i < it->cmp_it.nchars; i++)
7249 bidi_move_to_visually_next (&it->bidi_it);
7250 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
7251 IT_CHARPOS (*it) = it->bidi_it.charpos;
7252 }
7253
7254 if ((! it->bidi_p || ! it->cmp_it.reversed_p)
7255 && it->cmp_it.to < it->cmp_it.nglyphs)
7256 {
7257 /* Composition created while scanning forward. Proceed
7258 to the next grapheme cluster. */
7259 it->cmp_it.from = it->cmp_it.to;
7260 }
7261 else if ((it->bidi_p && it->cmp_it.reversed_p)
7262 && it->cmp_it.from > 0)
7263 {
7264 /* Composition created while scanning backward. Proceed
7265 to the previous grapheme cluster. */
7266 it->cmp_it.to = it->cmp_it.from;
7267 }
7268 else
7269 {
7270 /* No more grapheme clusters in this composition.
7271 Find the next stop position. */
7272 ptrdiff_t stop = it->end_charpos;
7273
7274 if (it->bidi_it.scan_dir < 0)
7275 /* Now we are scanning backward and don't know
7276 where to stop. */
7277 stop = -1;
7278 composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it),
7279 IT_BYTEPOS (*it), stop, Qnil);
7280 }
7281 }
7282 else
7283 {
7284 eassert (it->len != 0);
7285
7286 if (!it->bidi_p)
7287 {
7288 IT_BYTEPOS (*it) += it->len;
7289 IT_CHARPOS (*it) += 1;
7290 }
7291 else
7292 {
7293 int prev_scan_dir = it->bidi_it.scan_dir;
7294 /* If this is a new paragraph, determine its base
7295 direction (a.k.a. its base embedding level). */
7296 if (it->bidi_it.new_paragraph)
7297 bidi_paragraph_init (it->paragraph_embedding, &it->bidi_it, 0);
7298 bidi_move_to_visually_next (&it->bidi_it);
7299 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
7300 IT_CHARPOS (*it) = it->bidi_it.charpos;
7301 if (prev_scan_dir != it->bidi_it.scan_dir)
7302 {
7303 /* As the scan direction was changed, we must
7304 re-compute the stop position for composition. */
7305 ptrdiff_t stop = it->end_charpos;
7306 if (it->bidi_it.scan_dir < 0)
7307 stop = -1;
7308 composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it),
7309 IT_BYTEPOS (*it), stop, Qnil);
7310 }
7311 }
7312 eassert (IT_BYTEPOS (*it) == CHAR_TO_BYTE (IT_CHARPOS (*it)));
7313 }
7314 break;
7315
7316 case GET_FROM_C_STRING:
7317 /* Current display element of IT is from a C string. */
7318 if (!it->bidi_p
7319 /* If the string position is beyond string's end, it means
7320 next_element_from_c_string is padding the string with
7321 blanks, in which case we bypass the bidi iterator,
7322 because it cannot deal with such virtual characters. */
7323 || IT_CHARPOS (*it) >= it->bidi_it.string.schars)
7324 {
7325 IT_BYTEPOS (*it) += it->len;
7326 IT_CHARPOS (*it) += 1;
7327 }
7328 else
7329 {
7330 bidi_move_to_visually_next (&it->bidi_it);
7331 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
7332 IT_CHARPOS (*it) = it->bidi_it.charpos;
7333 }
7334 break;
7335
7336 case GET_FROM_DISPLAY_VECTOR:
7337 /* Current display element of IT is from a display table entry.
7338 Advance in the display table definition. Reset it to null if
7339 end reached, and continue with characters from buffers/
7340 strings. */
7341 ++it->current.dpvec_index;
7342
7343 /* Restore face of the iterator to what they were before the
7344 display vector entry (these entries may contain faces). */
7345 it->face_id = it->saved_face_id;
7346
7347 if (it->dpvec + it->current.dpvec_index >= it->dpend)
7348 {
7349 int recheck_faces = it->ellipsis_p;
7350
7351 if (it->s)
7352 it->method = GET_FROM_C_STRING;
7353 else if (STRINGP (it->string))
7354 it->method = GET_FROM_STRING;
7355 else
7356 {
7357 it->method = GET_FROM_BUFFER;
7358 it->object = it->w->contents;
7359 }
7360
7361 it->dpvec = NULL;
7362 it->current.dpvec_index = -1;
7363
7364 /* Skip over characters which were displayed via IT->dpvec. */
7365 if (it->dpvec_char_len < 0)
7366 reseat_at_next_visible_line_start (it, 1);
7367 else if (it->dpvec_char_len > 0)
7368 {
7369 if (it->method == GET_FROM_STRING
7370 && it->current.overlay_string_index >= 0
7371 && it->n_overlay_strings > 0)
7372 it->ignore_overlay_strings_at_pos_p = true;
7373 it->len = it->dpvec_char_len;
7374 set_iterator_to_next (it, reseat_p);
7375 }
7376
7377 /* Maybe recheck faces after display vector. */
7378 if (recheck_faces)
7379 it->stop_charpos = IT_CHARPOS (*it);
7380 }
7381 break;
7382
7383 case GET_FROM_STRING:
7384 /* Current display element is a character from a Lisp string. */
7385 eassert (it->s == NULL && STRINGP (it->string));
7386 /* Don't advance past string end. These conditions are true
7387 when set_iterator_to_next is called at the end of
7388 get_next_display_element, in which case the Lisp string is
7389 already exhausted, and all we want is pop the iterator
7390 stack. */
7391 if (it->current.overlay_string_index >= 0)
7392 {
7393 /* This is an overlay string, so there's no padding with
7394 spaces, and the number of characters in the string is
7395 where the string ends. */
7396 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string))
7397 goto consider_string_end;
7398 }
7399 else
7400 {
7401 /* Not an overlay string. There could be padding, so test
7402 against it->end_charpos. */
7403 if (IT_STRING_CHARPOS (*it) >= it->end_charpos)
7404 goto consider_string_end;
7405 }
7406 if (it->cmp_it.id >= 0)
7407 {
7408 /* We are delivering display elements from a composition.
7409 Update the string position past the grapheme cluster
7410 we've just processed. */
7411 if (! it->bidi_p)
7412 {
7413 IT_STRING_CHARPOS (*it) += it->cmp_it.nchars;
7414 IT_STRING_BYTEPOS (*it) += it->cmp_it.nbytes;
7415 }
7416 else
7417 {
7418 int i;
7419
7420 for (i = 0; i < it->cmp_it.nchars; i++)
7421 bidi_move_to_visually_next (&it->bidi_it);
7422 IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos;
7423 IT_STRING_CHARPOS (*it) = it->bidi_it.charpos;
7424 }
7425
7426 /* Did we exhaust all the grapheme clusters of this
7427 composition? */
7428 if ((! it->bidi_p || ! it->cmp_it.reversed_p)
7429 && (it->cmp_it.to < it->cmp_it.nglyphs))
7430 {
7431 /* Not all the grapheme clusters were processed yet;
7432 advance to the next cluster. */
7433 it->cmp_it.from = it->cmp_it.to;
7434 }
7435 else if ((it->bidi_p && it->cmp_it.reversed_p)
7436 && it->cmp_it.from > 0)
7437 {
7438 /* Likewise: advance to the next cluster, but going in
7439 the reverse direction. */
7440 it->cmp_it.to = it->cmp_it.from;
7441 }
7442 else
7443 {
7444 /* This composition was fully processed; find the next
7445 candidate place for checking for composed
7446 characters. */
7447 /* Always limit string searches to the string length;
7448 any padding spaces are not part of the string, and
7449 there cannot be any compositions in that padding. */
7450 ptrdiff_t stop = SCHARS (it->string);
7451
7452 if (it->bidi_p && it->bidi_it.scan_dir < 0)
7453 stop = -1;
7454 else if (it->end_charpos < stop)
7455 {
7456 /* Cf. PRECISION in reseat_to_string: we might be
7457 limited in how many of the string characters we
7458 need to deliver. */
7459 stop = it->end_charpos;
7460 }
7461 composition_compute_stop_pos (&it->cmp_it,
7462 IT_STRING_CHARPOS (*it),
7463 IT_STRING_BYTEPOS (*it), stop,
7464 it->string);
7465 }
7466 }
7467 else
7468 {
7469 if (!it->bidi_p
7470 /* If the string position is beyond string's end, it
7471 means next_element_from_string is padding the string
7472 with blanks, in which case we bypass the bidi
7473 iterator, because it cannot deal with such virtual
7474 characters. */
7475 || IT_STRING_CHARPOS (*it) >= it->bidi_it.string.schars)
7476 {
7477 IT_STRING_BYTEPOS (*it) += it->len;
7478 IT_STRING_CHARPOS (*it) += 1;
7479 }
7480 else
7481 {
7482 int prev_scan_dir = it->bidi_it.scan_dir;
7483
7484 bidi_move_to_visually_next (&it->bidi_it);
7485 IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos;
7486 IT_STRING_CHARPOS (*it) = it->bidi_it.charpos;
7487 /* If the scan direction changes, we may need to update
7488 the place where to check for composed characters. */
7489 if (prev_scan_dir != it->bidi_it.scan_dir)
7490 {
7491 ptrdiff_t stop = SCHARS (it->string);
7492
7493 if (it->bidi_it.scan_dir < 0)
7494 stop = -1;
7495 else if (it->end_charpos < stop)
7496 stop = it->end_charpos;
7497
7498 composition_compute_stop_pos (&it->cmp_it,
7499 IT_STRING_CHARPOS (*it),
7500 IT_STRING_BYTEPOS (*it), stop,
7501 it->string);
7502 }
7503 }
7504 }
7505
7506 consider_string_end:
7507
7508 if (it->current.overlay_string_index >= 0)
7509 {
7510 /* IT->string is an overlay string. Advance to the
7511 next, if there is one. */
7512 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string))
7513 {
7514 it->ellipsis_p = 0;
7515 next_overlay_string (it);
7516 if (it->ellipsis_p)
7517 setup_for_ellipsis (it, 0);
7518 }
7519 }
7520 else
7521 {
7522 /* IT->string is not an overlay string. If we reached
7523 its end, and there is something on IT->stack, proceed
7524 with what is on the stack. This can be either another
7525 string, this time an overlay string, or a buffer. */
7526 if (IT_STRING_CHARPOS (*it) == SCHARS (it->string)
7527 && it->sp > 0)
7528 {
7529 pop_it (it);
7530 if (it->method == GET_FROM_STRING)
7531 goto consider_string_end;
7532 }
7533 }
7534 break;
7535
7536 case GET_FROM_IMAGE:
7537 case GET_FROM_STRETCH:
7538 /* The position etc with which we have to proceed are on
7539 the stack. The position may be at the end of a string,
7540 if the `display' property takes up the whole string. */
7541 eassert (it->sp > 0);
7542 pop_it (it);
7543 if (it->method == GET_FROM_STRING)
7544 goto consider_string_end;
7545 break;
7546
7547 default:
7548 /* There are no other methods defined, so this should be a bug. */
7549 emacs_abort ();
7550 }
7551
7552 eassert (it->method != GET_FROM_STRING
7553 || (STRINGP (it->string)
7554 && IT_STRING_CHARPOS (*it) >= 0));
7555 }
7556
7557 /* Load IT's display element fields with information about the next
7558 display element which comes from a display table entry or from the
7559 result of translating a control character to one of the forms `^C'
7560 or `\003'.
7561
7562 IT->dpvec holds the glyphs to return as characters.
7563 IT->saved_face_id holds the face id before the display vector--it
7564 is restored into IT->face_id in set_iterator_to_next. */
7565
7566 static int
7567 next_element_from_display_vector (struct it *it)
7568 {
7569 Lisp_Object gc;
7570 int prev_face_id = it->face_id;
7571 int next_face_id;
7572
7573 /* Precondition. */
7574 eassert (it->dpvec && it->current.dpvec_index >= 0);
7575
7576 it->face_id = it->saved_face_id;
7577
7578 /* KFS: This code used to check ip->dpvec[0] instead of the current element.
7579 That seemed totally bogus - so I changed it... */
7580 gc = it->dpvec[it->current.dpvec_index];
7581
7582 if (GLYPH_CODE_P (gc))
7583 {
7584 struct face *this_face, *prev_face, *next_face;
7585
7586 it->c = GLYPH_CODE_CHAR (gc);
7587 it->len = CHAR_BYTES (it->c);
7588
7589 /* The entry may contain a face id to use. Such a face id is
7590 the id of a Lisp face, not a realized face. A face id of
7591 zero means no face is specified. */
7592 if (it->dpvec_face_id >= 0)
7593 it->face_id = it->dpvec_face_id;
7594 else
7595 {
7596 int lface_id = GLYPH_CODE_FACE (gc);
7597 if (lface_id > 0)
7598 it->face_id = merge_faces (it->f, Qt, lface_id,
7599 it->saved_face_id);
7600 }
7601
7602 /* Glyphs in the display vector could have the box face, so we
7603 need to set the related flags in the iterator, as
7604 appropriate. */
7605 this_face = FACE_FROM_ID (it->f, it->face_id);
7606 prev_face = FACE_FROM_ID (it->f, prev_face_id);
7607
7608 /* Is this character the first character of a box-face run? */
7609 it->start_of_box_run_p = (this_face && this_face->box != FACE_NO_BOX
7610 && (!prev_face
7611 || prev_face->box == FACE_NO_BOX));
7612
7613 /* For the last character of the box-face run, we need to look
7614 either at the next glyph from the display vector, or at the
7615 face we saw before the display vector. */
7616 next_face_id = it->saved_face_id;
7617 if (it->current.dpvec_index < it->dpend - it->dpvec - 1)
7618 {
7619 if (it->dpvec_face_id >= 0)
7620 next_face_id = it->dpvec_face_id;
7621 else
7622 {
7623 int lface_id =
7624 GLYPH_CODE_FACE (it->dpvec[it->current.dpvec_index + 1]);
7625
7626 if (lface_id > 0)
7627 next_face_id = merge_faces (it->f, Qt, lface_id,
7628 it->saved_face_id);
7629 }
7630 }
7631 next_face = FACE_FROM_ID (it->f, next_face_id);
7632 it->end_of_box_run_p = (this_face && this_face->box != FACE_NO_BOX
7633 && (!next_face
7634 || next_face->box == FACE_NO_BOX));
7635 it->face_box_p = this_face && this_face->box != FACE_NO_BOX;
7636 }
7637 else
7638 /* Display table entry is invalid. Return a space. */
7639 it->c = ' ', it->len = 1;
7640
7641 /* Don't change position and object of the iterator here. They are
7642 still the values of the character that had this display table
7643 entry or was translated, and that's what we want. */
7644 it->what = IT_CHARACTER;
7645 return 1;
7646 }
7647
7648 /* Get the first element of string/buffer in the visual order, after
7649 being reseated to a new position in a string or a buffer. */
7650 static void
7651 get_visually_first_element (struct it *it)
7652 {
7653 int string_p = STRINGP (it->string) || it->s;
7654 ptrdiff_t eob = (string_p ? it->bidi_it.string.schars : ZV);
7655 ptrdiff_t bob = (string_p ? 0 : BEGV);
7656
7657 if (STRINGP (it->string))
7658 {
7659 it->bidi_it.charpos = IT_STRING_CHARPOS (*it);
7660 it->bidi_it.bytepos = IT_STRING_BYTEPOS (*it);
7661 }
7662 else
7663 {
7664 it->bidi_it.charpos = IT_CHARPOS (*it);
7665 it->bidi_it.bytepos = IT_BYTEPOS (*it);
7666 }
7667
7668 if (it->bidi_it.charpos == eob)
7669 {
7670 /* Nothing to do, but reset the FIRST_ELT flag, like
7671 bidi_paragraph_init does, because we are not going to
7672 call it. */
7673 it->bidi_it.first_elt = 0;
7674 }
7675 else if (it->bidi_it.charpos == bob
7676 || (!string_p
7677 && (FETCH_CHAR (it->bidi_it.bytepos - 1) == '\n'
7678 || FETCH_CHAR (it->bidi_it.bytepos) == '\n')))
7679 {
7680 /* If we are at the beginning of a line/string, we can produce
7681 the next element right away. */
7682 bidi_paragraph_init (it->paragraph_embedding, &it->bidi_it, 1);
7683 bidi_move_to_visually_next (&it->bidi_it);
7684 }
7685 else
7686 {
7687 ptrdiff_t orig_bytepos = it->bidi_it.bytepos;
7688
7689 /* We need to prime the bidi iterator starting at the line's or
7690 string's beginning, before we will be able to produce the
7691 next element. */
7692 if (string_p)
7693 it->bidi_it.charpos = it->bidi_it.bytepos = 0;
7694 else
7695 it->bidi_it.charpos = find_newline_no_quit (IT_CHARPOS (*it),
7696 IT_BYTEPOS (*it), -1,
7697 &it->bidi_it.bytepos);
7698 bidi_paragraph_init (it->paragraph_embedding, &it->bidi_it, 1);
7699 do
7700 {
7701 /* Now return to buffer/string position where we were asked
7702 to get the next display element, and produce that. */
7703 bidi_move_to_visually_next (&it->bidi_it);
7704 }
7705 while (it->bidi_it.bytepos != orig_bytepos
7706 && it->bidi_it.charpos < eob);
7707 }
7708
7709 /* Adjust IT's position information to where we ended up. */
7710 if (STRINGP (it->string))
7711 {
7712 IT_STRING_CHARPOS (*it) = it->bidi_it.charpos;
7713 IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos;
7714 }
7715 else
7716 {
7717 IT_CHARPOS (*it) = it->bidi_it.charpos;
7718 IT_BYTEPOS (*it) = it->bidi_it.bytepos;
7719 }
7720
7721 if (STRINGP (it->string) || !it->s)
7722 {
7723 ptrdiff_t stop, charpos, bytepos;
7724
7725 if (STRINGP (it->string))
7726 {
7727 eassert (!it->s);
7728 stop = SCHARS (it->string);
7729 if (stop > it->end_charpos)
7730 stop = it->end_charpos;
7731 charpos = IT_STRING_CHARPOS (*it);
7732 bytepos = IT_STRING_BYTEPOS (*it);
7733 }
7734 else
7735 {
7736 stop = it->end_charpos;
7737 charpos = IT_CHARPOS (*it);
7738 bytepos = IT_BYTEPOS (*it);
7739 }
7740 if (it->bidi_it.scan_dir < 0)
7741 stop = -1;
7742 composition_compute_stop_pos (&it->cmp_it, charpos, bytepos, stop,
7743 it->string);
7744 }
7745 }
7746
7747 /* Load IT with the next display element from Lisp string IT->string.
7748 IT->current.string_pos is the current position within the string.
7749 If IT->current.overlay_string_index >= 0, the Lisp string is an
7750 overlay string. */
7751
7752 static int
7753 next_element_from_string (struct it *it)
7754 {
7755 struct text_pos position;
7756
7757 eassert (STRINGP (it->string));
7758 eassert (!it->bidi_p || EQ (it->string, it->bidi_it.string.lstring));
7759 eassert (IT_STRING_CHARPOS (*it) >= 0);
7760 position = it->current.string_pos;
7761
7762 /* With bidi reordering, the character to display might not be the
7763 character at IT_STRING_CHARPOS. BIDI_IT.FIRST_ELT non-zero means
7764 that we were reseat()ed to a new string, whose paragraph
7765 direction is not known. */
7766 if (it->bidi_p && it->bidi_it.first_elt)
7767 {
7768 get_visually_first_element (it);
7769 SET_TEXT_POS (position, IT_STRING_CHARPOS (*it), IT_STRING_BYTEPOS (*it));
7770 }
7771
7772 /* Time to check for invisible text? */
7773 if (IT_STRING_CHARPOS (*it) < it->end_charpos)
7774 {
7775 if (IT_STRING_CHARPOS (*it) >= it->stop_charpos)
7776 {
7777 if (!(!it->bidi_p
7778 || BIDI_AT_BASE_LEVEL (it->bidi_it)
7779 || IT_STRING_CHARPOS (*it) == it->stop_charpos))
7780 {
7781 /* With bidi non-linear iteration, we could find
7782 ourselves far beyond the last computed stop_charpos,
7783 with several other stop positions in between that we
7784 missed. Scan them all now, in buffer's logical
7785 order, until we find and handle the last stop_charpos
7786 that precedes our current position. */
7787 handle_stop_backwards (it, it->stop_charpos);
7788 return GET_NEXT_DISPLAY_ELEMENT (it);
7789 }
7790 else
7791 {
7792 if (it->bidi_p)
7793 {
7794 /* Take note of the stop position we just moved
7795 across, for when we will move back across it. */
7796 it->prev_stop = it->stop_charpos;
7797 /* If we are at base paragraph embedding level, take
7798 note of the last stop position seen at this
7799 level. */
7800 if (BIDI_AT_BASE_LEVEL (it->bidi_it))
7801 it->base_level_stop = it->stop_charpos;
7802 }
7803 handle_stop (it);
7804
7805 /* Since a handler may have changed IT->method, we must
7806 recurse here. */
7807 return GET_NEXT_DISPLAY_ELEMENT (it);
7808 }
7809 }
7810 else if (it->bidi_p
7811 /* If we are before prev_stop, we may have overstepped
7812 on our way backwards a stop_pos, and if so, we need
7813 to handle that stop_pos. */
7814 && IT_STRING_CHARPOS (*it) < it->prev_stop
7815 /* We can sometimes back up for reasons that have nothing
7816 to do with bidi reordering. E.g., compositions. The
7817 code below is only needed when we are above the base
7818 embedding level, so test for that explicitly. */
7819 && !BIDI_AT_BASE_LEVEL (it->bidi_it))
7820 {
7821 /* If we lost track of base_level_stop, we have no better
7822 place for handle_stop_backwards to start from than string
7823 beginning. This happens, e.g., when we were reseated to
7824 the previous screenful of text by vertical-motion. */
7825 if (it->base_level_stop <= 0
7826 || IT_STRING_CHARPOS (*it) < it->base_level_stop)
7827 it->base_level_stop = 0;
7828 handle_stop_backwards (it, it->base_level_stop);
7829 return GET_NEXT_DISPLAY_ELEMENT (it);
7830 }
7831 }
7832
7833 if (it->current.overlay_string_index >= 0)
7834 {
7835 /* Get the next character from an overlay string. In overlay
7836 strings, there is no field width or padding with spaces to
7837 do. */
7838 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string))
7839 {
7840 it->what = IT_EOB;
7841 return 0;
7842 }
7843 else if (CHAR_COMPOSED_P (it, IT_STRING_CHARPOS (*it),
7844 IT_STRING_BYTEPOS (*it),
7845 it->bidi_it.scan_dir < 0
7846 ? -1
7847 : SCHARS (it->string))
7848 && next_element_from_composition (it))
7849 {
7850 return 1;
7851 }
7852 else if (STRING_MULTIBYTE (it->string))
7853 {
7854 const unsigned char *s = (SDATA (it->string)
7855 + IT_STRING_BYTEPOS (*it));
7856 it->c = string_char_and_length (s, &it->len);
7857 }
7858 else
7859 {
7860 it->c = SREF (it->string, IT_STRING_BYTEPOS (*it));
7861 it->len = 1;
7862 }
7863 }
7864 else
7865 {
7866 /* Get the next character from a Lisp string that is not an
7867 overlay string. Such strings come from the mode line, for
7868 example. We may have to pad with spaces, or truncate the
7869 string. See also next_element_from_c_string. */
7870 if (IT_STRING_CHARPOS (*it) >= it->end_charpos)
7871 {
7872 it->what = IT_EOB;
7873 return 0;
7874 }
7875 else if (IT_STRING_CHARPOS (*it) >= it->string_nchars)
7876 {
7877 /* Pad with spaces. */
7878 it->c = ' ', it->len = 1;
7879 CHARPOS (position) = BYTEPOS (position) = -1;
7880 }
7881 else if (CHAR_COMPOSED_P (it, IT_STRING_CHARPOS (*it),
7882 IT_STRING_BYTEPOS (*it),
7883 it->bidi_it.scan_dir < 0
7884 ? -1
7885 : it->string_nchars)
7886 && next_element_from_composition (it))
7887 {
7888 return 1;
7889 }
7890 else if (STRING_MULTIBYTE (it->string))
7891 {
7892 const unsigned char *s = (SDATA (it->string)
7893 + IT_STRING_BYTEPOS (*it));
7894 it->c = string_char_and_length (s, &it->len);
7895 }
7896 else
7897 {
7898 it->c = SREF (it->string, IT_STRING_BYTEPOS (*it));
7899 it->len = 1;
7900 }
7901 }
7902
7903 /* Record what we have and where it came from. */
7904 it->what = IT_CHARACTER;
7905 it->object = it->string;
7906 it->position = position;
7907 return 1;
7908 }
7909
7910
7911 /* Load IT with next display element from C string IT->s.
7912 IT->string_nchars is the maximum number of characters to return
7913 from the string. IT->end_charpos may be greater than
7914 IT->string_nchars when this function is called, in which case we
7915 may have to return padding spaces. Value is zero if end of string
7916 reached, including padding spaces. */
7917
7918 static int
7919 next_element_from_c_string (struct it *it)
7920 {
7921 bool success_p = true;
7922
7923 eassert (it->s);
7924 eassert (!it->bidi_p || it->s == it->bidi_it.string.s);
7925 it->what = IT_CHARACTER;
7926 BYTEPOS (it->position) = CHARPOS (it->position) = 0;
7927 it->object = make_number (0);
7928
7929 /* With bidi reordering, the character to display might not be the
7930 character at IT_CHARPOS. BIDI_IT.FIRST_ELT non-zero means that
7931 we were reseated to a new string, whose paragraph direction is
7932 not known. */
7933 if (it->bidi_p && it->bidi_it.first_elt)
7934 get_visually_first_element (it);
7935
7936 /* IT's position can be greater than IT->string_nchars in case a
7937 field width or precision has been specified when the iterator was
7938 initialized. */
7939 if (IT_CHARPOS (*it) >= it->end_charpos)
7940 {
7941 /* End of the game. */
7942 it->what = IT_EOB;
7943 success_p = 0;
7944 }
7945 else if (IT_CHARPOS (*it) >= it->string_nchars)
7946 {
7947 /* Pad with spaces. */
7948 it->c = ' ', it->len = 1;
7949 BYTEPOS (it->position) = CHARPOS (it->position) = -1;
7950 }
7951 else if (it->multibyte_p)
7952 it->c = string_char_and_length (it->s + IT_BYTEPOS (*it), &it->len);
7953 else
7954 it->c = it->s[IT_BYTEPOS (*it)], it->len = 1;
7955
7956 return success_p;
7957 }
7958
7959
7960 /* Set up IT to return characters from an ellipsis, if appropriate.
7961 The definition of the ellipsis glyphs may come from a display table
7962 entry. This function fills IT with the first glyph from the
7963 ellipsis if an ellipsis is to be displayed. */
7964
7965 static int
7966 next_element_from_ellipsis (struct it *it)
7967 {
7968 if (it->selective_display_ellipsis_p)
7969 setup_for_ellipsis (it, it->len);
7970 else
7971 {
7972 /* The face at the current position may be different from the
7973 face we find after the invisible text. Remember what it
7974 was in IT->saved_face_id, and signal that it's there by
7975 setting face_before_selective_p. */
7976 it->saved_face_id = it->face_id;
7977 it->method = GET_FROM_BUFFER;
7978 it->object = it->w->contents;
7979 reseat_at_next_visible_line_start (it, 1);
7980 it->face_before_selective_p = true;
7981 }
7982
7983 return GET_NEXT_DISPLAY_ELEMENT (it);
7984 }
7985
7986
7987 /* Deliver an image display element. The iterator IT is already
7988 filled with image information (done in handle_display_prop). Value
7989 is always 1. */
7990
7991
7992 static int
7993 next_element_from_image (struct it *it)
7994 {
7995 it->what = IT_IMAGE;
7996 it->ignore_overlay_strings_at_pos_p = 0;
7997 return 1;
7998 }
7999
8000
8001 /* Fill iterator IT with next display element from a stretch glyph
8002 property. IT->object is the value of the text property. Value is
8003 always 1. */
8004
8005 static int
8006 next_element_from_stretch (struct it *it)
8007 {
8008 it->what = IT_STRETCH;
8009 return 1;
8010 }
8011
8012 /* Scan backwards from IT's current position until we find a stop
8013 position, or until BEGV. This is called when we find ourself
8014 before both the last known prev_stop and base_level_stop while
8015 reordering bidirectional text. */
8016
8017 static void
8018 compute_stop_pos_backwards (struct it *it)
8019 {
8020 const int SCAN_BACK_LIMIT = 1000;
8021 struct text_pos pos;
8022 struct display_pos save_current = it->current;
8023 struct text_pos save_position = it->position;
8024 ptrdiff_t charpos = IT_CHARPOS (*it);
8025 ptrdiff_t where_we_are = charpos;
8026 ptrdiff_t save_stop_pos = it->stop_charpos;
8027 ptrdiff_t save_end_pos = it->end_charpos;
8028
8029 eassert (NILP (it->string) && !it->s);
8030 eassert (it->bidi_p);
8031 it->bidi_p = 0;
8032 do
8033 {
8034 it->end_charpos = min (charpos + 1, ZV);
8035 charpos = max (charpos - SCAN_BACK_LIMIT, BEGV);
8036 SET_TEXT_POS (pos, charpos, CHAR_TO_BYTE (charpos));
8037 reseat_1 (it, pos, 0);
8038 compute_stop_pos (it);
8039 /* We must advance forward, right? */
8040 if (it->stop_charpos <= charpos)
8041 emacs_abort ();
8042 }
8043 while (charpos > BEGV && it->stop_charpos >= it->end_charpos);
8044
8045 if (it->stop_charpos <= where_we_are)
8046 it->prev_stop = it->stop_charpos;
8047 else
8048 it->prev_stop = BEGV;
8049 it->bidi_p = true;
8050 it->current = save_current;
8051 it->position = save_position;
8052 it->stop_charpos = save_stop_pos;
8053 it->end_charpos = save_end_pos;
8054 }
8055
8056 /* Scan forward from CHARPOS in the current buffer/string, until we
8057 find a stop position > current IT's position. Then handle the stop
8058 position before that. This is called when we bump into a stop
8059 position while reordering bidirectional text. CHARPOS should be
8060 the last previously processed stop_pos (or BEGV/0, if none were
8061 processed yet) whose position is less that IT's current
8062 position. */
8063
8064 static void
8065 handle_stop_backwards (struct it *it, ptrdiff_t charpos)
8066 {
8067 int bufp = !STRINGP (it->string);
8068 ptrdiff_t where_we_are = (bufp ? IT_CHARPOS (*it) : IT_STRING_CHARPOS (*it));
8069 struct display_pos save_current = it->current;
8070 struct text_pos save_position = it->position;
8071 struct text_pos pos1;
8072 ptrdiff_t next_stop;
8073
8074 /* Scan in strict logical order. */
8075 eassert (it->bidi_p);
8076 it->bidi_p = 0;
8077 do
8078 {
8079 it->prev_stop = charpos;
8080 if (bufp)
8081 {
8082 SET_TEXT_POS (pos1, charpos, CHAR_TO_BYTE (charpos));
8083 reseat_1 (it, pos1, 0);
8084 }
8085 else
8086 it->current.string_pos = string_pos (charpos, it->string);
8087 compute_stop_pos (it);
8088 /* We must advance forward, right? */
8089 if (it->stop_charpos <= it->prev_stop)
8090 emacs_abort ();
8091 charpos = it->stop_charpos;
8092 }
8093 while (charpos <= where_we_are);
8094
8095 it->bidi_p = true;
8096 it->current = save_current;
8097 it->position = save_position;
8098 next_stop = it->stop_charpos;
8099 it->stop_charpos = it->prev_stop;
8100 handle_stop (it);
8101 it->stop_charpos = next_stop;
8102 }
8103
8104 /* Load IT with the next display element from current_buffer. Value
8105 is zero if end of buffer reached. IT->stop_charpos is the next
8106 position at which to stop and check for text properties or buffer
8107 end. */
8108
8109 static int
8110 next_element_from_buffer (struct it *it)
8111 {
8112 bool success_p = true;
8113
8114 eassert (IT_CHARPOS (*it) >= BEGV);
8115 eassert (NILP (it->string) && !it->s);
8116 eassert (!it->bidi_p
8117 || (EQ (it->bidi_it.string.lstring, Qnil)
8118 && it->bidi_it.string.s == NULL));
8119
8120 /* With bidi reordering, the character to display might not be the
8121 character at IT_CHARPOS. BIDI_IT.FIRST_ELT non-zero means that
8122 we were reseat()ed to a new buffer position, which is potentially
8123 a different paragraph. */
8124 if (it->bidi_p && it->bidi_it.first_elt)
8125 {
8126 get_visually_first_element (it);
8127 SET_TEXT_POS (it->position, IT_CHARPOS (*it), IT_BYTEPOS (*it));
8128 }
8129
8130 if (IT_CHARPOS (*it) >= it->stop_charpos)
8131 {
8132 if (IT_CHARPOS (*it) >= it->end_charpos)
8133 {
8134 int overlay_strings_follow_p;
8135
8136 /* End of the game, except when overlay strings follow that
8137 haven't been returned yet. */
8138 if (it->overlay_strings_at_end_processed_p)
8139 overlay_strings_follow_p = 0;
8140 else
8141 {
8142 it->overlay_strings_at_end_processed_p = true;
8143 overlay_strings_follow_p = get_overlay_strings (it, 0);
8144 }
8145
8146 if (overlay_strings_follow_p)
8147 success_p = GET_NEXT_DISPLAY_ELEMENT (it);
8148 else
8149 {
8150 it->what = IT_EOB;
8151 it->position = it->current.pos;
8152 success_p = 0;
8153 }
8154 }
8155 else if (!(!it->bidi_p
8156 || BIDI_AT_BASE_LEVEL (it->bidi_it)
8157 || IT_CHARPOS (*it) == it->stop_charpos))
8158 {
8159 /* With bidi non-linear iteration, we could find ourselves
8160 far beyond the last computed stop_charpos, with several
8161 other stop positions in between that we missed. Scan
8162 them all now, in buffer's logical order, until we find
8163 and handle the last stop_charpos that precedes our
8164 current position. */
8165 handle_stop_backwards (it, it->stop_charpos);
8166 return GET_NEXT_DISPLAY_ELEMENT (it);
8167 }
8168 else
8169 {
8170 if (it->bidi_p)
8171 {
8172 /* Take note of the stop position we just moved across,
8173 for when we will move back across it. */
8174 it->prev_stop = it->stop_charpos;
8175 /* If we are at base paragraph embedding level, take
8176 note of the last stop position seen at this
8177 level. */
8178 if (BIDI_AT_BASE_LEVEL (it->bidi_it))
8179 it->base_level_stop = it->stop_charpos;
8180 }
8181 handle_stop (it);
8182 return GET_NEXT_DISPLAY_ELEMENT (it);
8183 }
8184 }
8185 else if (it->bidi_p
8186 /* If we are before prev_stop, we may have overstepped on
8187 our way backwards a stop_pos, and if so, we need to
8188 handle that stop_pos. */
8189 && IT_CHARPOS (*it) < it->prev_stop
8190 /* We can sometimes back up for reasons that have nothing
8191 to do with bidi reordering. E.g., compositions. The
8192 code below is only needed when we are above the base
8193 embedding level, so test for that explicitly. */
8194 && !BIDI_AT_BASE_LEVEL (it->bidi_it))
8195 {
8196 if (it->base_level_stop <= 0
8197 || IT_CHARPOS (*it) < it->base_level_stop)
8198 {
8199 /* If we lost track of base_level_stop, we need to find
8200 prev_stop by looking backwards. This happens, e.g., when
8201 we were reseated to the previous screenful of text by
8202 vertical-motion. */
8203 it->base_level_stop = BEGV;
8204 compute_stop_pos_backwards (it);
8205 handle_stop_backwards (it, it->prev_stop);
8206 }
8207 else
8208 handle_stop_backwards (it, it->base_level_stop);
8209 return GET_NEXT_DISPLAY_ELEMENT (it);
8210 }
8211 else
8212 {
8213 /* No face changes, overlays etc. in sight, so just return a
8214 character from current_buffer. */
8215 unsigned char *p;
8216 ptrdiff_t stop;
8217
8218 /* We moved to the next buffer position, so any info about
8219 previously seen overlays is no longer valid. */
8220 it->ignore_overlay_strings_at_pos_p = 0;
8221
8222 /* Maybe run the redisplay end trigger hook. Performance note:
8223 This doesn't seem to cost measurable time. */
8224 if (it->redisplay_end_trigger_charpos
8225 && it->glyph_row
8226 && IT_CHARPOS (*it) >= it->redisplay_end_trigger_charpos)
8227 run_redisplay_end_trigger_hook (it);
8228
8229 stop = it->bidi_it.scan_dir < 0 ? -1 : it->end_charpos;
8230 if (CHAR_COMPOSED_P (it, IT_CHARPOS (*it), IT_BYTEPOS (*it),
8231 stop)
8232 && next_element_from_composition (it))
8233 {
8234 return 1;
8235 }
8236
8237 /* Get the next character, maybe multibyte. */
8238 p = BYTE_POS_ADDR (IT_BYTEPOS (*it));
8239 if (it->multibyte_p && !ASCII_CHAR_P (*p))
8240 it->c = STRING_CHAR_AND_LENGTH (p, it->len);
8241 else
8242 it->c = *p, it->len = 1;
8243
8244 /* Record what we have and where it came from. */
8245 it->what = IT_CHARACTER;
8246 it->object = it->w->contents;
8247 it->position = it->current.pos;
8248
8249 /* Normally we return the character found above, except when we
8250 really want to return an ellipsis for selective display. */
8251 if (it->selective)
8252 {
8253 if (it->c == '\n')
8254 {
8255 /* A value of selective > 0 means hide lines indented more
8256 than that number of columns. */
8257 if (it->selective > 0
8258 && IT_CHARPOS (*it) + 1 < ZV
8259 && indented_beyond_p (IT_CHARPOS (*it) + 1,
8260 IT_BYTEPOS (*it) + 1,
8261 it->selective))
8262 {
8263 success_p = next_element_from_ellipsis (it);
8264 it->dpvec_char_len = -1;
8265 }
8266 }
8267 else if (it->c == '\r' && it->selective == -1)
8268 {
8269 /* A value of selective == -1 means that everything from the
8270 CR to the end of the line is invisible, with maybe an
8271 ellipsis displayed for it. */
8272 success_p = next_element_from_ellipsis (it);
8273 it->dpvec_char_len = -1;
8274 }
8275 }
8276 }
8277
8278 /* Value is zero if end of buffer reached. */
8279 eassert (!success_p || it->what != IT_CHARACTER || it->len > 0);
8280 return success_p;
8281 }
8282
8283
8284 /* Run the redisplay end trigger hook for IT. */
8285
8286 static void
8287 run_redisplay_end_trigger_hook (struct it *it)
8288 {
8289 /* IT->glyph_row should be non-null, i.e. we should be actually
8290 displaying something, or otherwise we should not run the hook. */
8291 eassert (it->glyph_row);
8292
8293 ptrdiff_t charpos = it->redisplay_end_trigger_charpos;
8294 it->redisplay_end_trigger_charpos = 0;
8295
8296 /* Since we are *trying* to run these functions, don't try to run
8297 them again, even if they get an error. */
8298 wset_redisplay_end_trigger (it->w, Qnil);
8299 CALLN (Frun_hook_with_args, Qredisplay_end_trigger_functions, it->window,
8300 make_number (charpos));
8301
8302 /* Notice if it changed the face of the character we are on. */
8303 handle_face_prop (it);
8304 }
8305
8306
8307 /* Deliver a composition display element. Unlike the other
8308 next_element_from_XXX, this function is not registered in the array
8309 get_next_element[]. It is called from next_element_from_buffer and
8310 next_element_from_string when necessary. */
8311
8312 static int
8313 next_element_from_composition (struct it *it)
8314 {
8315 it->what = IT_COMPOSITION;
8316 it->len = it->cmp_it.nbytes;
8317 if (STRINGP (it->string))
8318 {
8319 if (it->c < 0)
8320 {
8321 IT_STRING_CHARPOS (*it) += it->cmp_it.nchars;
8322 IT_STRING_BYTEPOS (*it) += it->cmp_it.nbytes;
8323 return 0;
8324 }
8325 it->position = it->current.string_pos;
8326 it->object = it->string;
8327 it->c = composition_update_it (&it->cmp_it, IT_STRING_CHARPOS (*it),
8328 IT_STRING_BYTEPOS (*it), it->string);
8329 }
8330 else
8331 {
8332 if (it->c < 0)
8333 {
8334 IT_CHARPOS (*it) += it->cmp_it.nchars;
8335 IT_BYTEPOS (*it) += it->cmp_it.nbytes;
8336 if (it->bidi_p)
8337 {
8338 if (it->bidi_it.new_paragraph)
8339 bidi_paragraph_init (it->paragraph_embedding, &it->bidi_it, 0);
8340 /* Resync the bidi iterator with IT's new position.
8341 FIXME: this doesn't support bidirectional text. */
8342 while (it->bidi_it.charpos < IT_CHARPOS (*it))
8343 bidi_move_to_visually_next (&it->bidi_it);
8344 }
8345 return 0;
8346 }
8347 it->position = it->current.pos;
8348 it->object = it->w->contents;
8349 it->c = composition_update_it (&it->cmp_it, IT_CHARPOS (*it),
8350 IT_BYTEPOS (*it), Qnil);
8351 }
8352 return 1;
8353 }
8354
8355
8356 \f
8357 /***********************************************************************
8358 Moving an iterator without producing glyphs
8359 ***********************************************************************/
8360
8361 /* Check if iterator is at a position corresponding to a valid buffer
8362 position after some move_it_ call. */
8363
8364 #define IT_POS_VALID_AFTER_MOVE_P(it) \
8365 ((it)->method == GET_FROM_STRING \
8366 ? IT_STRING_CHARPOS (*it) == 0 \
8367 : 1)
8368
8369
8370 /* Move iterator IT to a specified buffer or X position within one
8371 line on the display without producing glyphs.
8372
8373 OP should be a bit mask including some or all of these bits:
8374 MOVE_TO_X: Stop upon reaching x-position TO_X.
8375 MOVE_TO_POS: Stop upon reaching buffer or string position TO_CHARPOS.
8376 Regardless of OP's value, stop upon reaching the end of the display line.
8377
8378 TO_X is normally a value 0 <= TO_X <= IT->last_visible_x.
8379 This means, in particular, that TO_X includes window's horizontal
8380 scroll amount.
8381
8382 The return value has several possible values that
8383 say what condition caused the scan to stop:
8384
8385 MOVE_POS_MATCH_OR_ZV
8386 - when TO_POS or ZV was reached.
8387
8388 MOVE_X_REACHED
8389 -when TO_X was reached before TO_POS or ZV were reached.
8390
8391 MOVE_LINE_CONTINUED
8392 - when we reached the end of the display area and the line must
8393 be continued.
8394
8395 MOVE_LINE_TRUNCATED
8396 - when we reached the end of the display area and the line is
8397 truncated.
8398
8399 MOVE_NEWLINE_OR_CR
8400 - when we stopped at a line end, i.e. a newline or a CR and selective
8401 display is on. */
8402
8403 static enum move_it_result
8404 move_it_in_display_line_to (struct it *it,
8405 ptrdiff_t to_charpos, int to_x,
8406 enum move_operation_enum op)
8407 {
8408 enum move_it_result result = MOVE_UNDEFINED;
8409 struct glyph_row *saved_glyph_row;
8410 struct it wrap_it, atpos_it, atx_it, ppos_it;
8411 void *wrap_data = NULL, *atpos_data = NULL, *atx_data = NULL;
8412 void *ppos_data = NULL;
8413 int may_wrap = 0;
8414 enum it_method prev_method = it->method;
8415 ptrdiff_t closest_pos IF_LINT (= 0), prev_pos = IT_CHARPOS (*it);
8416 int saw_smaller_pos = prev_pos < to_charpos;
8417
8418 /* Don't produce glyphs in produce_glyphs. */
8419 saved_glyph_row = it->glyph_row;
8420 it->glyph_row = NULL;
8421
8422 /* Use wrap_it to save a copy of IT wherever a word wrap could
8423 occur. Use atpos_it to save a copy of IT at the desired buffer
8424 position, if found, so that we can scan ahead and check if the
8425 word later overshoots the window edge. Use atx_it similarly, for
8426 pixel positions. */
8427 wrap_it.sp = -1;
8428 atpos_it.sp = -1;
8429 atx_it.sp = -1;
8430
8431 /* Use ppos_it under bidi reordering to save a copy of IT for the
8432 initial position. We restore that position in IT when we have
8433 scanned the entire display line without finding a match for
8434 TO_CHARPOS and all the character positions are greater than
8435 TO_CHARPOS. We then restart the scan from the initial position,
8436 and stop at CLOSEST_POS, which is a position > TO_CHARPOS that is
8437 the closest to TO_CHARPOS. */
8438 if (it->bidi_p)
8439 {
8440 if ((op & MOVE_TO_POS) && IT_CHARPOS (*it) >= to_charpos)
8441 {
8442 SAVE_IT (ppos_it, *it, ppos_data);
8443 closest_pos = IT_CHARPOS (*it);
8444 }
8445 else
8446 closest_pos = ZV;
8447 }
8448
8449 #define BUFFER_POS_REACHED_P() \
8450 ((op & MOVE_TO_POS) != 0 \
8451 && BUFFERP (it->object) \
8452 && (IT_CHARPOS (*it) == to_charpos \
8453 || ((!it->bidi_p \
8454 || BIDI_AT_BASE_LEVEL (it->bidi_it)) \
8455 && IT_CHARPOS (*it) > to_charpos) \
8456 || (it->what == IT_COMPOSITION \
8457 && ((IT_CHARPOS (*it) > to_charpos \
8458 && to_charpos >= it->cmp_it.charpos) \
8459 || (IT_CHARPOS (*it) < to_charpos \
8460 && to_charpos <= it->cmp_it.charpos)))) \
8461 && (it->method == GET_FROM_BUFFER \
8462 || (it->method == GET_FROM_DISPLAY_VECTOR \
8463 && it->dpvec + it->current.dpvec_index + 1 >= it->dpend)))
8464
8465 /* If there's a line-/wrap-prefix, handle it. */
8466 if (it->hpos == 0 && it->method == GET_FROM_BUFFER
8467 && it->current_y < it->last_visible_y)
8468 handle_line_prefix (it);
8469
8470 if (IT_CHARPOS (*it) < CHARPOS (this_line_min_pos))
8471 SET_TEXT_POS (this_line_min_pos, IT_CHARPOS (*it), IT_BYTEPOS (*it));
8472
8473 while (1)
8474 {
8475 int x, i, ascent = 0, descent = 0;
8476
8477 /* Utility macro to reset an iterator with x, ascent, and descent. */
8478 #define IT_RESET_X_ASCENT_DESCENT(IT) \
8479 ((IT)->current_x = x, (IT)->max_ascent = ascent, \
8480 (IT)->max_descent = descent)
8481
8482 /* Stop if we move beyond TO_CHARPOS (after an image or a
8483 display string or stretch glyph). */
8484 if ((op & MOVE_TO_POS) != 0
8485 && BUFFERP (it->object)
8486 && it->method == GET_FROM_BUFFER
8487 && (((!it->bidi_p
8488 /* When the iterator is at base embedding level, we
8489 are guaranteed that characters are delivered for
8490 display in strictly increasing order of their
8491 buffer positions. */
8492 || BIDI_AT_BASE_LEVEL (it->bidi_it))
8493 && IT_CHARPOS (*it) > to_charpos)
8494 || (it->bidi_p
8495 && (prev_method == GET_FROM_IMAGE
8496 || prev_method == GET_FROM_STRETCH
8497 || prev_method == GET_FROM_STRING)
8498 /* Passed TO_CHARPOS from left to right. */
8499 && ((prev_pos < to_charpos
8500 && IT_CHARPOS (*it) > to_charpos)
8501 /* Passed TO_CHARPOS from right to left. */
8502 || (prev_pos > to_charpos
8503 && IT_CHARPOS (*it) < to_charpos)))))
8504 {
8505 if (it->line_wrap != WORD_WRAP || wrap_it.sp < 0)
8506 {
8507 result = MOVE_POS_MATCH_OR_ZV;
8508 break;
8509 }
8510 else if (it->line_wrap == WORD_WRAP && atpos_it.sp < 0)
8511 /* If wrap_it is valid, the current position might be in a
8512 word that is wrapped. So, save the iterator in
8513 atpos_it and continue to see if wrapping happens. */
8514 SAVE_IT (atpos_it, *it, atpos_data);
8515 }
8516
8517 /* Stop when ZV reached.
8518 We used to stop here when TO_CHARPOS reached as well, but that is
8519 too soon if this glyph does not fit on this line. So we handle it
8520 explicitly below. */
8521 if (!get_next_display_element (it))
8522 {
8523 result = MOVE_POS_MATCH_OR_ZV;
8524 break;
8525 }
8526
8527 if (it->line_wrap == TRUNCATE)
8528 {
8529 if (BUFFER_POS_REACHED_P ())
8530 {
8531 result = MOVE_POS_MATCH_OR_ZV;
8532 break;
8533 }
8534 }
8535 else
8536 {
8537 if (it->line_wrap == WORD_WRAP && it->area == TEXT_AREA)
8538 {
8539 if (IT_DISPLAYING_WHITESPACE (it))
8540 may_wrap = 1;
8541 else if (may_wrap)
8542 {
8543 /* We have reached a glyph that follows one or more
8544 whitespace characters. If the position is
8545 already found, we are done. */
8546 if (atpos_it.sp >= 0)
8547 {
8548 RESTORE_IT (it, &atpos_it, atpos_data);
8549 result = MOVE_POS_MATCH_OR_ZV;
8550 goto done;
8551 }
8552 if (atx_it.sp >= 0)
8553 {
8554 RESTORE_IT (it, &atx_it, atx_data);
8555 result = MOVE_X_REACHED;
8556 goto done;
8557 }
8558 /* Otherwise, we can wrap here. */
8559 SAVE_IT (wrap_it, *it, wrap_data);
8560 may_wrap = 0;
8561 }
8562 }
8563 }
8564
8565 /* Remember the line height for the current line, in case
8566 the next element doesn't fit on the line. */
8567 ascent = it->max_ascent;
8568 descent = it->max_descent;
8569
8570 /* The call to produce_glyphs will get the metrics of the
8571 display element IT is loaded with. Record the x-position
8572 before this display element, in case it doesn't fit on the
8573 line. */
8574 x = it->current_x;
8575
8576 PRODUCE_GLYPHS (it);
8577
8578 if (it->area != TEXT_AREA)
8579 {
8580 prev_method = it->method;
8581 if (it->method == GET_FROM_BUFFER)
8582 prev_pos = IT_CHARPOS (*it);
8583 set_iterator_to_next (it, 1);
8584 if (IT_CHARPOS (*it) < CHARPOS (this_line_min_pos))
8585 SET_TEXT_POS (this_line_min_pos,
8586 IT_CHARPOS (*it), IT_BYTEPOS (*it));
8587 if (it->bidi_p
8588 && (op & MOVE_TO_POS)
8589 && IT_CHARPOS (*it) > to_charpos
8590 && IT_CHARPOS (*it) < closest_pos)
8591 closest_pos = IT_CHARPOS (*it);
8592 continue;
8593 }
8594
8595 /* The number of glyphs we get back in IT->nglyphs will normally
8596 be 1 except when IT->c is (i) a TAB, or (ii) a multi-glyph
8597 character on a terminal frame, or (iii) a line end. For the
8598 second case, IT->nglyphs - 1 padding glyphs will be present.
8599 (On X frames, there is only one glyph produced for a
8600 composite character.)
8601
8602 The behavior implemented below means, for continuation lines,
8603 that as many spaces of a TAB as fit on the current line are
8604 displayed there. For terminal frames, as many glyphs of a
8605 multi-glyph character are displayed in the current line, too.
8606 This is what the old redisplay code did, and we keep it that
8607 way. Under X, the whole shape of a complex character must
8608 fit on the line or it will be completely displayed in the
8609 next line.
8610
8611 Note that both for tabs and padding glyphs, all glyphs have
8612 the same width. */
8613 if (it->nglyphs)
8614 {
8615 /* More than one glyph or glyph doesn't fit on line. All
8616 glyphs have the same width. */
8617 int single_glyph_width = it->pixel_width / it->nglyphs;
8618 int new_x;
8619 int x_before_this_char = x;
8620 int hpos_before_this_char = it->hpos;
8621
8622 for (i = 0; i < it->nglyphs; ++i, x = new_x)
8623 {
8624 new_x = x + single_glyph_width;
8625
8626 /* We want to leave anything reaching TO_X to the caller. */
8627 if ((op & MOVE_TO_X) && new_x > to_x)
8628 {
8629 if (BUFFER_POS_REACHED_P ())
8630 {
8631 if (it->line_wrap != WORD_WRAP || wrap_it.sp < 0)
8632 goto buffer_pos_reached;
8633 if (atpos_it.sp < 0)
8634 {
8635 SAVE_IT (atpos_it, *it, atpos_data);
8636 IT_RESET_X_ASCENT_DESCENT (&atpos_it);
8637 }
8638 }
8639 else
8640 {
8641 if (it->line_wrap != WORD_WRAP || wrap_it.sp < 0)
8642 {
8643 it->current_x = x;
8644 result = MOVE_X_REACHED;
8645 break;
8646 }
8647 if (atx_it.sp < 0)
8648 {
8649 SAVE_IT (atx_it, *it, atx_data);
8650 IT_RESET_X_ASCENT_DESCENT (&atx_it);
8651 }
8652 }
8653 }
8654
8655 if (/* Lines are continued. */
8656 it->line_wrap != TRUNCATE
8657 && (/* And glyph doesn't fit on the line. */
8658 new_x > it->last_visible_x
8659 /* Or it fits exactly and we're on a window
8660 system frame. */
8661 || (new_x == it->last_visible_x
8662 && FRAME_WINDOW_P (it->f)
8663 && ((it->bidi_p && it->bidi_it.paragraph_dir == R2L)
8664 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
8665 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)))))
8666 {
8667 if (/* IT->hpos == 0 means the very first glyph
8668 doesn't fit on the line, e.g. a wide image. */
8669 it->hpos == 0
8670 || (new_x == it->last_visible_x
8671 && FRAME_WINDOW_P (it->f)))
8672 {
8673 ++it->hpos;
8674 it->current_x = new_x;
8675
8676 /* The character's last glyph just barely fits
8677 in this row. */
8678 if (i == it->nglyphs - 1)
8679 {
8680 /* If this is the destination position,
8681 return a position *before* it in this row,
8682 now that we know it fits in this row. */
8683 if (BUFFER_POS_REACHED_P ())
8684 {
8685 if (it->line_wrap != WORD_WRAP
8686 || wrap_it.sp < 0)
8687 {
8688 it->hpos = hpos_before_this_char;
8689 it->current_x = x_before_this_char;
8690 result = MOVE_POS_MATCH_OR_ZV;
8691 break;
8692 }
8693 if (it->line_wrap == WORD_WRAP
8694 && atpos_it.sp < 0)
8695 {
8696 SAVE_IT (atpos_it, *it, atpos_data);
8697 atpos_it.current_x = x_before_this_char;
8698 atpos_it.hpos = hpos_before_this_char;
8699 }
8700 }
8701
8702 prev_method = it->method;
8703 if (it->method == GET_FROM_BUFFER)
8704 prev_pos = IT_CHARPOS (*it);
8705 set_iterator_to_next (it, 1);
8706 if (IT_CHARPOS (*it) < CHARPOS (this_line_min_pos))
8707 SET_TEXT_POS (this_line_min_pos,
8708 IT_CHARPOS (*it), IT_BYTEPOS (*it));
8709 /* On graphical terminals, newlines may
8710 "overflow" into the fringe if
8711 overflow-newline-into-fringe is non-nil.
8712 On text terminals, and on graphical
8713 terminals with no right margin, newlines
8714 may overflow into the last glyph on the
8715 display line.*/
8716 if (!FRAME_WINDOW_P (it->f)
8717 || ((it->bidi_p
8718 && it->bidi_it.paragraph_dir == R2L)
8719 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
8720 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)) == 0
8721 || IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
8722 {
8723 if (!get_next_display_element (it))
8724 {
8725 result = MOVE_POS_MATCH_OR_ZV;
8726 break;
8727 }
8728 if (BUFFER_POS_REACHED_P ())
8729 {
8730 if (ITERATOR_AT_END_OF_LINE_P (it))
8731 result = MOVE_POS_MATCH_OR_ZV;
8732 else
8733 result = MOVE_LINE_CONTINUED;
8734 break;
8735 }
8736 if (ITERATOR_AT_END_OF_LINE_P (it)
8737 && (it->line_wrap != WORD_WRAP
8738 || wrap_it.sp < 0
8739 || IT_OVERFLOW_NEWLINE_INTO_FRINGE (it)))
8740 {
8741 result = MOVE_NEWLINE_OR_CR;
8742 break;
8743 }
8744 }
8745 }
8746 }
8747 else
8748 IT_RESET_X_ASCENT_DESCENT (it);
8749
8750 if (wrap_it.sp >= 0)
8751 {
8752 RESTORE_IT (it, &wrap_it, wrap_data);
8753 atpos_it.sp = -1;
8754 atx_it.sp = -1;
8755 }
8756
8757 TRACE_MOVE ((stderr, "move_it_in: continued at %d\n",
8758 IT_CHARPOS (*it)));
8759 result = MOVE_LINE_CONTINUED;
8760 break;
8761 }
8762
8763 if (BUFFER_POS_REACHED_P ())
8764 {
8765 if (it->line_wrap != WORD_WRAP || wrap_it.sp < 0)
8766 goto buffer_pos_reached;
8767 if (it->line_wrap == WORD_WRAP && atpos_it.sp < 0)
8768 {
8769 SAVE_IT (atpos_it, *it, atpos_data);
8770 IT_RESET_X_ASCENT_DESCENT (&atpos_it);
8771 }
8772 }
8773
8774 if (new_x > it->first_visible_x)
8775 {
8776 /* Glyph is visible. Increment number of glyphs that
8777 would be displayed. */
8778 ++it->hpos;
8779 }
8780 }
8781
8782 if (result != MOVE_UNDEFINED)
8783 break;
8784 }
8785 else if (BUFFER_POS_REACHED_P ())
8786 {
8787 buffer_pos_reached:
8788 IT_RESET_X_ASCENT_DESCENT (it);
8789 result = MOVE_POS_MATCH_OR_ZV;
8790 break;
8791 }
8792 else if ((op & MOVE_TO_X) && it->current_x >= to_x)
8793 {
8794 /* Stop when TO_X specified and reached. This check is
8795 necessary here because of lines consisting of a line end,
8796 only. The line end will not produce any glyphs and we
8797 would never get MOVE_X_REACHED. */
8798 eassert (it->nglyphs == 0);
8799 result = MOVE_X_REACHED;
8800 break;
8801 }
8802
8803 /* Is this a line end? If yes, we're done. */
8804 if (ITERATOR_AT_END_OF_LINE_P (it))
8805 {
8806 /* If we are past TO_CHARPOS, but never saw any character
8807 positions smaller than TO_CHARPOS, return
8808 MOVE_POS_MATCH_OR_ZV, like the unidirectional display
8809 did. */
8810 if (it->bidi_p && (op & MOVE_TO_POS) != 0)
8811 {
8812 if (!saw_smaller_pos && IT_CHARPOS (*it) > to_charpos)
8813 {
8814 if (closest_pos < ZV)
8815 {
8816 RESTORE_IT (it, &ppos_it, ppos_data);
8817 /* Don't recurse if closest_pos is equal to
8818 to_charpos, since we have just tried that. */
8819 if (closest_pos != to_charpos)
8820 move_it_in_display_line_to (it, closest_pos, -1,
8821 MOVE_TO_POS);
8822 result = MOVE_POS_MATCH_OR_ZV;
8823 }
8824 else
8825 goto buffer_pos_reached;
8826 }
8827 else if (it->line_wrap == WORD_WRAP && atpos_it.sp >= 0
8828 && IT_CHARPOS (*it) > to_charpos)
8829 goto buffer_pos_reached;
8830 else
8831 result = MOVE_NEWLINE_OR_CR;
8832 }
8833 else
8834 result = MOVE_NEWLINE_OR_CR;
8835 break;
8836 }
8837
8838 prev_method = it->method;
8839 if (it->method == GET_FROM_BUFFER)
8840 prev_pos = IT_CHARPOS (*it);
8841 /* The current display element has been consumed. Advance
8842 to the next. */
8843 set_iterator_to_next (it, 1);
8844 if (IT_CHARPOS (*it) < CHARPOS (this_line_min_pos))
8845 SET_TEXT_POS (this_line_min_pos, IT_CHARPOS (*it), IT_BYTEPOS (*it));
8846 if (IT_CHARPOS (*it) < to_charpos)
8847 saw_smaller_pos = 1;
8848 if (it->bidi_p
8849 && (op & MOVE_TO_POS)
8850 && IT_CHARPOS (*it) >= to_charpos
8851 && IT_CHARPOS (*it) < closest_pos)
8852 closest_pos = IT_CHARPOS (*it);
8853
8854 /* Stop if lines are truncated and IT's current x-position is
8855 past the right edge of the window now. */
8856 if (it->line_wrap == TRUNCATE
8857 && it->current_x >= it->last_visible_x)
8858 {
8859 if (!FRAME_WINDOW_P (it->f)
8860 || ((it->bidi_p && it->bidi_it.paragraph_dir == R2L)
8861 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
8862 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)) == 0
8863 || IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
8864 {
8865 int at_eob_p = 0;
8866
8867 if ((at_eob_p = !get_next_display_element (it))
8868 || BUFFER_POS_REACHED_P ()
8869 /* If we are past TO_CHARPOS, but never saw any
8870 character positions smaller than TO_CHARPOS,
8871 return MOVE_POS_MATCH_OR_ZV, like the
8872 unidirectional display did. */
8873 || (it->bidi_p && (op & MOVE_TO_POS) != 0
8874 && !saw_smaller_pos
8875 && IT_CHARPOS (*it) > to_charpos))
8876 {
8877 if (it->bidi_p
8878 && !BUFFER_POS_REACHED_P ()
8879 && !at_eob_p && closest_pos < ZV)
8880 {
8881 RESTORE_IT (it, &ppos_it, ppos_data);
8882 if (closest_pos != to_charpos)
8883 move_it_in_display_line_to (it, closest_pos, -1,
8884 MOVE_TO_POS);
8885 }
8886 result = MOVE_POS_MATCH_OR_ZV;
8887 break;
8888 }
8889 if (ITERATOR_AT_END_OF_LINE_P (it))
8890 {
8891 result = MOVE_NEWLINE_OR_CR;
8892 break;
8893 }
8894 }
8895 else if (it->bidi_p && (op & MOVE_TO_POS) != 0
8896 && !saw_smaller_pos
8897 && IT_CHARPOS (*it) > to_charpos)
8898 {
8899 if (closest_pos < ZV)
8900 {
8901 RESTORE_IT (it, &ppos_it, ppos_data);
8902 if (closest_pos != to_charpos)
8903 move_it_in_display_line_to (it, closest_pos, -1,
8904 MOVE_TO_POS);
8905 }
8906 result = MOVE_POS_MATCH_OR_ZV;
8907 break;
8908 }
8909 result = MOVE_LINE_TRUNCATED;
8910 break;
8911 }
8912 #undef IT_RESET_X_ASCENT_DESCENT
8913 }
8914
8915 #undef BUFFER_POS_REACHED_P
8916
8917 /* If we scanned beyond to_pos and didn't find a point to wrap at,
8918 restore the saved iterator. */
8919 if (atpos_it.sp >= 0)
8920 RESTORE_IT (it, &atpos_it, atpos_data);
8921 else if (atx_it.sp >= 0)
8922 RESTORE_IT (it, &atx_it, atx_data);
8923
8924 done:
8925
8926 if (atpos_data)
8927 bidi_unshelve_cache (atpos_data, 1);
8928 if (atx_data)
8929 bidi_unshelve_cache (atx_data, 1);
8930 if (wrap_data)
8931 bidi_unshelve_cache (wrap_data, 1);
8932 if (ppos_data)
8933 bidi_unshelve_cache (ppos_data, 1);
8934
8935 /* Restore the iterator settings altered at the beginning of this
8936 function. */
8937 it->glyph_row = saved_glyph_row;
8938 return result;
8939 }
8940
8941 /* For external use. */
8942 void
8943 move_it_in_display_line (struct it *it,
8944 ptrdiff_t to_charpos, int to_x,
8945 enum move_operation_enum op)
8946 {
8947 if (it->line_wrap == WORD_WRAP
8948 && (op & MOVE_TO_X))
8949 {
8950 struct it save_it;
8951 void *save_data = NULL;
8952 int skip;
8953
8954 SAVE_IT (save_it, *it, save_data);
8955 skip = move_it_in_display_line_to (it, to_charpos, to_x, op);
8956 /* When word-wrap is on, TO_X may lie past the end
8957 of a wrapped line. Then it->current is the
8958 character on the next line, so backtrack to the
8959 space before the wrap point. */
8960 if (skip == MOVE_LINE_CONTINUED)
8961 {
8962 int prev_x = max (it->current_x - 1, 0);
8963 RESTORE_IT (it, &save_it, save_data);
8964 move_it_in_display_line_to
8965 (it, -1, prev_x, MOVE_TO_X);
8966 }
8967 else
8968 bidi_unshelve_cache (save_data, 1);
8969 }
8970 else
8971 move_it_in_display_line_to (it, to_charpos, to_x, op);
8972 }
8973
8974
8975 /* Move IT forward until it satisfies one or more of the criteria in
8976 TO_CHARPOS, TO_X, TO_Y, and TO_VPOS.
8977
8978 OP is a bit-mask that specifies where to stop, and in particular,
8979 which of those four position arguments makes a difference. See the
8980 description of enum move_operation_enum.
8981
8982 If TO_CHARPOS is in invisible text, e.g. a truncated part of a
8983 screen line, this function will set IT to the next position that is
8984 displayed to the right of TO_CHARPOS on the screen.
8985
8986 Return the maximum pixel length of any line scanned but never more
8987 than it.last_visible_x. */
8988
8989 int
8990 move_it_to (struct it *it, ptrdiff_t to_charpos, int to_x, int to_y, int to_vpos, int op)
8991 {
8992 enum move_it_result skip, skip2 = MOVE_X_REACHED;
8993 int line_height, line_start_x = 0, reached = 0;
8994 int max_current_x = 0;
8995 void *backup_data = NULL;
8996
8997 for (;;)
8998 {
8999 if (op & MOVE_TO_VPOS)
9000 {
9001 /* If no TO_CHARPOS and no TO_X specified, stop at the
9002 start of the line TO_VPOS. */
9003 if ((op & (MOVE_TO_X | MOVE_TO_POS)) == 0)
9004 {
9005 if (it->vpos == to_vpos)
9006 {
9007 reached = 1;
9008 break;
9009 }
9010 else
9011 skip = move_it_in_display_line_to (it, -1, -1, 0);
9012 }
9013 else
9014 {
9015 /* TO_VPOS >= 0 means stop at TO_X in the line at
9016 TO_VPOS, or at TO_POS, whichever comes first. */
9017 if (it->vpos == to_vpos)
9018 {
9019 reached = 2;
9020 break;
9021 }
9022
9023 skip = move_it_in_display_line_to (it, to_charpos, to_x, op);
9024
9025 if (skip == MOVE_POS_MATCH_OR_ZV || it->vpos == to_vpos)
9026 {
9027 reached = 3;
9028 break;
9029 }
9030 else if (skip == MOVE_X_REACHED && it->vpos != to_vpos)
9031 {
9032 /* We have reached TO_X but not in the line we want. */
9033 skip = move_it_in_display_line_to (it, to_charpos,
9034 -1, MOVE_TO_POS);
9035 if (skip == MOVE_POS_MATCH_OR_ZV)
9036 {
9037 reached = 4;
9038 break;
9039 }
9040 }
9041 }
9042 }
9043 else if (op & MOVE_TO_Y)
9044 {
9045 struct it it_backup;
9046
9047 if (it->line_wrap == WORD_WRAP)
9048 SAVE_IT (it_backup, *it, backup_data);
9049
9050 /* TO_Y specified means stop at TO_X in the line containing
9051 TO_Y---or at TO_CHARPOS if this is reached first. The
9052 problem is that we can't really tell whether the line
9053 contains TO_Y before we have completely scanned it, and
9054 this may skip past TO_X. What we do is to first scan to
9055 TO_X.
9056
9057 If TO_X is not specified, use a TO_X of zero. The reason
9058 is to make the outcome of this function more predictable.
9059 If we didn't use TO_X == 0, we would stop at the end of
9060 the line which is probably not what a caller would expect
9061 to happen. */
9062 skip = move_it_in_display_line_to
9063 (it, to_charpos, ((op & MOVE_TO_X) ? to_x : 0),
9064 (MOVE_TO_X | (op & MOVE_TO_POS)));
9065
9066 /* If TO_CHARPOS is reached or ZV, we don't have to do more. */
9067 if (skip == MOVE_POS_MATCH_OR_ZV)
9068 reached = 5;
9069 else if (skip == MOVE_X_REACHED)
9070 {
9071 /* If TO_X was reached, we want to know whether TO_Y is
9072 in the line. We know this is the case if the already
9073 scanned glyphs make the line tall enough. Otherwise,
9074 we must check by scanning the rest of the line. */
9075 line_height = it->max_ascent + it->max_descent;
9076 if (to_y >= it->current_y
9077 && to_y < it->current_y + line_height)
9078 {
9079 reached = 6;
9080 break;
9081 }
9082 SAVE_IT (it_backup, *it, backup_data);
9083 TRACE_MOVE ((stderr, "move_it: from %d\n", IT_CHARPOS (*it)));
9084 skip2 = move_it_in_display_line_to (it, to_charpos, -1,
9085 op & MOVE_TO_POS);
9086 TRACE_MOVE ((stderr, "move_it: to %d\n", IT_CHARPOS (*it)));
9087 line_height = it->max_ascent + it->max_descent;
9088 TRACE_MOVE ((stderr, "move_it: line_height = %d\n", line_height));
9089
9090 if (to_y >= it->current_y
9091 && to_y < it->current_y + line_height)
9092 {
9093 /* If TO_Y is in this line and TO_X was reached
9094 above, we scanned too far. We have to restore
9095 IT's settings to the ones before skipping. But
9096 keep the more accurate values of max_ascent and
9097 max_descent we've found while skipping the rest
9098 of the line, for the sake of callers, such as
9099 pos_visible_p, that need to know the line
9100 height. */
9101 int max_ascent = it->max_ascent;
9102 int max_descent = it->max_descent;
9103
9104 RESTORE_IT (it, &it_backup, backup_data);
9105 it->max_ascent = max_ascent;
9106 it->max_descent = max_descent;
9107 reached = 6;
9108 }
9109 else
9110 {
9111 skip = skip2;
9112 if (skip == MOVE_POS_MATCH_OR_ZV)
9113 reached = 7;
9114 }
9115 }
9116 else
9117 {
9118 /* Check whether TO_Y is in this line. */
9119 line_height = it->max_ascent + it->max_descent;
9120 TRACE_MOVE ((stderr, "move_it: line_height = %d\n", line_height));
9121
9122 if (to_y >= it->current_y
9123 && to_y < it->current_y + line_height)
9124 {
9125 if (to_y > it->current_y)
9126 max_current_x = max (it->current_x, max_current_x);
9127
9128 /* When word-wrap is on, TO_X may lie past the end
9129 of a wrapped line. Then it->current is the
9130 character on the next line, so backtrack to the
9131 space before the wrap point. */
9132 if (skip == MOVE_LINE_CONTINUED
9133 && it->line_wrap == WORD_WRAP)
9134 {
9135 int prev_x = max (it->current_x - 1, 0);
9136 RESTORE_IT (it, &it_backup, backup_data);
9137 skip = move_it_in_display_line_to
9138 (it, -1, prev_x, MOVE_TO_X);
9139 }
9140
9141 reached = 6;
9142 }
9143 }
9144
9145 if (reached)
9146 {
9147 max_current_x = max (it->current_x, max_current_x);
9148 break;
9149 }
9150 }
9151 else if (BUFFERP (it->object)
9152 && (it->method == GET_FROM_BUFFER
9153 || it->method == GET_FROM_STRETCH)
9154 && IT_CHARPOS (*it) >= to_charpos
9155 /* Under bidi iteration, a call to set_iterator_to_next
9156 can scan far beyond to_charpos if the initial
9157 portion of the next line needs to be reordered. In
9158 that case, give move_it_in_display_line_to another
9159 chance below. */
9160 && !(it->bidi_p
9161 && it->bidi_it.scan_dir == -1))
9162 skip = MOVE_POS_MATCH_OR_ZV;
9163 else
9164 skip = move_it_in_display_line_to (it, to_charpos, -1, MOVE_TO_POS);
9165
9166 switch (skip)
9167 {
9168 case MOVE_POS_MATCH_OR_ZV:
9169 max_current_x = max (it->current_x, max_current_x);
9170 reached = 8;
9171 goto out;
9172
9173 case MOVE_NEWLINE_OR_CR:
9174 max_current_x = max (it->current_x, max_current_x);
9175 set_iterator_to_next (it, 1);
9176 it->continuation_lines_width = 0;
9177 break;
9178
9179 case MOVE_LINE_TRUNCATED:
9180 max_current_x = it->last_visible_x;
9181 it->continuation_lines_width = 0;
9182 reseat_at_next_visible_line_start (it, 0);
9183 if ((op & MOVE_TO_POS) != 0
9184 && IT_CHARPOS (*it) > to_charpos)
9185 {
9186 reached = 9;
9187 goto out;
9188 }
9189 break;
9190
9191 case MOVE_LINE_CONTINUED:
9192 max_current_x = it->last_visible_x;
9193 /* For continued lines ending in a tab, some of the glyphs
9194 associated with the tab are displayed on the current
9195 line. Since it->current_x does not include these glyphs,
9196 we use it->last_visible_x instead. */
9197 if (it->c == '\t')
9198 {
9199 it->continuation_lines_width += it->last_visible_x;
9200 /* When moving by vpos, ensure that the iterator really
9201 advances to the next line (bug#847, bug#969). Fixme:
9202 do we need to do this in other circumstances? */
9203 if (it->current_x != it->last_visible_x
9204 && (op & MOVE_TO_VPOS)
9205 && !(op & (MOVE_TO_X | MOVE_TO_POS)))
9206 {
9207 line_start_x = it->current_x + it->pixel_width
9208 - it->last_visible_x;
9209 if (FRAME_WINDOW_P (it->f))
9210 {
9211 struct face *face = FACE_FROM_ID (it->f, it->face_id);
9212 struct font *face_font = face->font;
9213
9214 /* When display_line produces a continued line
9215 that ends in a TAB, it skips a tab stop that
9216 is closer than the font's space character
9217 width (see x_produce_glyphs where it produces
9218 the stretch glyph which represents a TAB).
9219 We need to reproduce the same logic here. */
9220 eassert (face_font);
9221 if (face_font)
9222 {
9223 if (line_start_x < face_font->space_width)
9224 line_start_x
9225 += it->tab_width * face_font->space_width;
9226 }
9227 }
9228 set_iterator_to_next (it, 0);
9229 }
9230 }
9231 else
9232 it->continuation_lines_width += it->current_x;
9233 break;
9234
9235 default:
9236 emacs_abort ();
9237 }
9238
9239 /* Reset/increment for the next run. */
9240 recenter_overlay_lists (current_buffer, IT_CHARPOS (*it));
9241 it->current_x = line_start_x;
9242 line_start_x = 0;
9243 it->hpos = 0;
9244 it->current_y += it->max_ascent + it->max_descent;
9245 ++it->vpos;
9246 last_height = it->max_ascent + it->max_descent;
9247 it->max_ascent = it->max_descent = 0;
9248 }
9249
9250 out:
9251
9252 /* On text terminals, we may stop at the end of a line in the middle
9253 of a multi-character glyph. If the glyph itself is continued,
9254 i.e. it is actually displayed on the next line, don't treat this
9255 stopping point as valid; move to the next line instead (unless
9256 that brings us offscreen). */
9257 if (!FRAME_WINDOW_P (it->f)
9258 && op & MOVE_TO_POS
9259 && IT_CHARPOS (*it) == to_charpos
9260 && it->what == IT_CHARACTER
9261 && it->nglyphs > 1
9262 && it->line_wrap == WINDOW_WRAP
9263 && it->current_x == it->last_visible_x - 1
9264 && it->c != '\n'
9265 && it->c != '\t'
9266 && it->w->window_end_valid
9267 && it->vpos < it->w->window_end_vpos)
9268 {
9269 it->continuation_lines_width += it->current_x;
9270 it->current_x = it->hpos = it->max_ascent = it->max_descent = 0;
9271 it->current_y += it->max_ascent + it->max_descent;
9272 ++it->vpos;
9273 last_height = it->max_ascent + it->max_descent;
9274 }
9275
9276 if (backup_data)
9277 bidi_unshelve_cache (backup_data, 1);
9278
9279 TRACE_MOVE ((stderr, "move_it_to: reached %d\n", reached));
9280
9281 return max_current_x;
9282 }
9283
9284
9285 /* Move iterator IT backward by a specified y-distance DY, DY >= 0.
9286
9287 If DY > 0, move IT backward at least that many pixels. DY = 0
9288 means move IT backward to the preceding line start or BEGV. This
9289 function may move over more than DY pixels if IT->current_y - DY
9290 ends up in the middle of a line; in this case IT->current_y will be
9291 set to the top of the line moved to. */
9292
9293 void
9294 move_it_vertically_backward (struct it *it, int dy)
9295 {
9296 int nlines, h;
9297 struct it it2, it3;
9298 void *it2data = NULL, *it3data = NULL;
9299 ptrdiff_t start_pos;
9300 int nchars_per_row
9301 = (it->last_visible_x - it->first_visible_x) / FRAME_COLUMN_WIDTH (it->f);
9302 ptrdiff_t pos_limit;
9303
9304 move_further_back:
9305 eassert (dy >= 0);
9306
9307 start_pos = IT_CHARPOS (*it);
9308
9309 /* Estimate how many newlines we must move back. */
9310 nlines = max (1, dy / default_line_pixel_height (it->w));
9311 if (it->line_wrap == TRUNCATE || nchars_per_row == 0)
9312 pos_limit = BEGV;
9313 else
9314 pos_limit = max (start_pos - nlines * nchars_per_row, BEGV);
9315
9316 /* Set the iterator's position that many lines back. But don't go
9317 back more than NLINES full screen lines -- this wins a day with
9318 buffers which have very long lines. */
9319 while (nlines-- && IT_CHARPOS (*it) > pos_limit)
9320 back_to_previous_visible_line_start (it);
9321
9322 /* Reseat the iterator here. When moving backward, we don't want
9323 reseat to skip forward over invisible text, set up the iterator
9324 to deliver from overlay strings at the new position etc. So,
9325 use reseat_1 here. */
9326 reseat_1 (it, it->current.pos, 1);
9327
9328 /* We are now surely at a line start. */
9329 it->current_x = it->hpos = 0; /* FIXME: this is incorrect when bidi
9330 reordering is in effect. */
9331 it->continuation_lines_width = 0;
9332
9333 /* Move forward and see what y-distance we moved. First move to the
9334 start of the next line so that we get its height. We need this
9335 height to be able to tell whether we reached the specified
9336 y-distance. */
9337 SAVE_IT (it2, *it, it2data);
9338 it2.max_ascent = it2.max_descent = 0;
9339 do
9340 {
9341 move_it_to (&it2, start_pos, -1, -1, it2.vpos + 1,
9342 MOVE_TO_POS | MOVE_TO_VPOS);
9343 }
9344 while (!(IT_POS_VALID_AFTER_MOVE_P (&it2)
9345 /* If we are in a display string which starts at START_POS,
9346 and that display string includes a newline, and we are
9347 right after that newline (i.e. at the beginning of a
9348 display line), exit the loop, because otherwise we will
9349 infloop, since move_it_to will see that it is already at
9350 START_POS and will not move. */
9351 || (it2.method == GET_FROM_STRING
9352 && IT_CHARPOS (it2) == start_pos
9353 && SREF (it2.string, IT_STRING_BYTEPOS (it2) - 1) == '\n')));
9354 eassert (IT_CHARPOS (*it) >= BEGV);
9355 SAVE_IT (it3, it2, it3data);
9356
9357 move_it_to (&it2, start_pos, -1, -1, -1, MOVE_TO_POS);
9358 eassert (IT_CHARPOS (*it) >= BEGV);
9359 /* H is the actual vertical distance from the position in *IT
9360 and the starting position. */
9361 h = it2.current_y - it->current_y;
9362 /* NLINES is the distance in number of lines. */
9363 nlines = it2.vpos - it->vpos;
9364
9365 /* Correct IT's y and vpos position
9366 so that they are relative to the starting point. */
9367 it->vpos -= nlines;
9368 it->current_y -= h;
9369
9370 if (dy == 0)
9371 {
9372 /* DY == 0 means move to the start of the screen line. The
9373 value of nlines is > 0 if continuation lines were involved,
9374 or if the original IT position was at start of a line. */
9375 RESTORE_IT (it, it, it2data);
9376 if (nlines > 0)
9377 move_it_by_lines (it, nlines);
9378 /* The above code moves us to some position NLINES down,
9379 usually to its first glyph (leftmost in an L2R line), but
9380 that's not necessarily the start of the line, under bidi
9381 reordering. We want to get to the character position
9382 that is immediately after the newline of the previous
9383 line. */
9384 if (it->bidi_p
9385 && !it->continuation_lines_width
9386 && !STRINGP (it->string)
9387 && IT_CHARPOS (*it) > BEGV
9388 && FETCH_BYTE (IT_BYTEPOS (*it) - 1) != '\n')
9389 {
9390 ptrdiff_t cp = IT_CHARPOS (*it), bp = IT_BYTEPOS (*it);
9391
9392 DEC_BOTH (cp, bp);
9393 cp = find_newline_no_quit (cp, bp, -1, NULL);
9394 move_it_to (it, cp, -1, -1, -1, MOVE_TO_POS);
9395 }
9396 bidi_unshelve_cache (it3data, 1);
9397 }
9398 else
9399 {
9400 /* The y-position we try to reach, relative to *IT.
9401 Note that H has been subtracted in front of the if-statement. */
9402 int target_y = it->current_y + h - dy;
9403 int y0 = it3.current_y;
9404 int y1;
9405 int line_height;
9406
9407 RESTORE_IT (&it3, &it3, it3data);
9408 y1 = line_bottom_y (&it3);
9409 line_height = y1 - y0;
9410 RESTORE_IT (it, it, it2data);
9411 /* If we did not reach target_y, try to move further backward if
9412 we can. If we moved too far backward, try to move forward. */
9413 if (target_y < it->current_y
9414 /* This is heuristic. In a window that's 3 lines high, with
9415 a line height of 13 pixels each, recentering with point
9416 on the bottom line will try to move -39/2 = 19 pixels
9417 backward. Try to avoid moving into the first line. */
9418 && (it->current_y - target_y
9419 > min (window_box_height (it->w), line_height * 2 / 3))
9420 && IT_CHARPOS (*it) > BEGV)
9421 {
9422 TRACE_MOVE ((stderr, " not far enough -> move_vert %d\n",
9423 target_y - it->current_y));
9424 dy = it->current_y - target_y;
9425 goto move_further_back;
9426 }
9427 else if (target_y >= it->current_y + line_height
9428 && IT_CHARPOS (*it) < ZV)
9429 {
9430 /* Should move forward by at least one line, maybe more.
9431
9432 Note: Calling move_it_by_lines can be expensive on
9433 terminal frames, where compute_motion is used (via
9434 vmotion) to do the job, when there are very long lines
9435 and truncate-lines is nil. That's the reason for
9436 treating terminal frames specially here. */
9437
9438 if (!FRAME_WINDOW_P (it->f))
9439 move_it_vertically (it, target_y - (it->current_y + line_height));
9440 else
9441 {
9442 do
9443 {
9444 move_it_by_lines (it, 1);
9445 }
9446 while (target_y >= line_bottom_y (it) && IT_CHARPOS (*it) < ZV);
9447 }
9448 }
9449 }
9450 }
9451
9452
9453 /* Move IT by a specified amount of pixel lines DY. DY negative means
9454 move backwards. DY = 0 means move to start of screen line. At the
9455 end, IT will be on the start of a screen line. */
9456
9457 void
9458 move_it_vertically (struct it *it, int dy)
9459 {
9460 if (dy <= 0)
9461 move_it_vertically_backward (it, -dy);
9462 else
9463 {
9464 TRACE_MOVE ((stderr, "move_it_v: from %d, %d\n", IT_CHARPOS (*it), dy));
9465 move_it_to (it, ZV, -1, it->current_y + dy, -1,
9466 MOVE_TO_POS | MOVE_TO_Y);
9467 TRACE_MOVE ((stderr, "move_it_v: to %d\n", IT_CHARPOS (*it)));
9468
9469 /* If buffer ends in ZV without a newline, move to the start of
9470 the line to satisfy the post-condition. */
9471 if (IT_CHARPOS (*it) == ZV
9472 && ZV > BEGV
9473 && FETCH_BYTE (IT_BYTEPOS (*it) - 1) != '\n')
9474 move_it_by_lines (it, 0);
9475 }
9476 }
9477
9478
9479 /* Move iterator IT past the end of the text line it is in. */
9480
9481 void
9482 move_it_past_eol (struct it *it)
9483 {
9484 enum move_it_result rc;
9485
9486 rc = move_it_in_display_line_to (it, Z, 0, MOVE_TO_POS);
9487 if (rc == MOVE_NEWLINE_OR_CR)
9488 set_iterator_to_next (it, 0);
9489 }
9490
9491
9492 /* Move IT by a specified number DVPOS of screen lines down. DVPOS
9493 negative means move up. DVPOS == 0 means move to the start of the
9494 screen line.
9495
9496 Optimization idea: If we would know that IT->f doesn't use
9497 a face with proportional font, we could be faster for
9498 truncate-lines nil. */
9499
9500 void
9501 move_it_by_lines (struct it *it, ptrdiff_t dvpos)
9502 {
9503
9504 /* The commented-out optimization uses vmotion on terminals. This
9505 gives bad results, because elements like it->what, on which
9506 callers such as pos_visible_p rely, aren't updated. */
9507 /* struct position pos;
9508 if (!FRAME_WINDOW_P (it->f))
9509 {
9510 struct text_pos textpos;
9511
9512 pos = *vmotion (IT_CHARPOS (*it), dvpos, it->w);
9513 SET_TEXT_POS (textpos, pos.bufpos, pos.bytepos);
9514 reseat (it, textpos, 1);
9515 it->vpos += pos.vpos;
9516 it->current_y += pos.vpos;
9517 }
9518 else */
9519
9520 if (dvpos == 0)
9521 {
9522 /* DVPOS == 0 means move to the start of the screen line. */
9523 move_it_vertically_backward (it, 0);
9524 /* Let next call to line_bottom_y calculate real line height. */
9525 last_height = 0;
9526 }
9527 else if (dvpos > 0)
9528 {
9529 move_it_to (it, -1, -1, -1, it->vpos + dvpos, MOVE_TO_VPOS);
9530 if (!IT_POS_VALID_AFTER_MOVE_P (it))
9531 {
9532 /* Only move to the next buffer position if we ended up in a
9533 string from display property, not in an overlay string
9534 (before-string or after-string). That is because the
9535 latter don't conceal the underlying buffer position, so
9536 we can ask to move the iterator to the exact position we
9537 are interested in. Note that, even if we are already at
9538 IT_CHARPOS (*it), the call below is not a no-op, as it
9539 will detect that we are at the end of the string, pop the
9540 iterator, and compute it->current_x and it->hpos
9541 correctly. */
9542 move_it_to (it, IT_CHARPOS (*it) + it->string_from_display_prop_p,
9543 -1, -1, -1, MOVE_TO_POS);
9544 }
9545 }
9546 else
9547 {
9548 struct it it2;
9549 void *it2data = NULL;
9550 ptrdiff_t start_charpos, i;
9551 int nchars_per_row
9552 = (it->last_visible_x - it->first_visible_x) / FRAME_COLUMN_WIDTH (it->f);
9553 bool hit_pos_limit = false;
9554 ptrdiff_t pos_limit;
9555
9556 /* Start at the beginning of the screen line containing IT's
9557 position. This may actually move vertically backwards,
9558 in case of overlays, so adjust dvpos accordingly. */
9559 dvpos += it->vpos;
9560 move_it_vertically_backward (it, 0);
9561 dvpos -= it->vpos;
9562
9563 /* Go back -DVPOS buffer lines, but no farther than -DVPOS full
9564 screen lines, and reseat the iterator there. */
9565 start_charpos = IT_CHARPOS (*it);
9566 if (it->line_wrap == TRUNCATE || nchars_per_row == 0)
9567 pos_limit = BEGV;
9568 else
9569 pos_limit = max (start_charpos + dvpos * nchars_per_row, BEGV);
9570
9571 for (i = -dvpos; i > 0 && IT_CHARPOS (*it) > pos_limit; --i)
9572 back_to_previous_visible_line_start (it);
9573 if (i > 0 && IT_CHARPOS (*it) <= pos_limit)
9574 hit_pos_limit = true;
9575 reseat (it, it->current.pos, 1);
9576
9577 /* Move further back if we end up in a string or an image. */
9578 while (!IT_POS_VALID_AFTER_MOVE_P (it))
9579 {
9580 /* First try to move to start of display line. */
9581 dvpos += it->vpos;
9582 move_it_vertically_backward (it, 0);
9583 dvpos -= it->vpos;
9584 if (IT_POS_VALID_AFTER_MOVE_P (it))
9585 break;
9586 /* If start of line is still in string or image,
9587 move further back. */
9588 back_to_previous_visible_line_start (it);
9589 reseat (it, it->current.pos, 1);
9590 dvpos--;
9591 }
9592
9593 it->current_x = it->hpos = 0;
9594
9595 /* Above call may have moved too far if continuation lines
9596 are involved. Scan forward and see if it did. */
9597 SAVE_IT (it2, *it, it2data);
9598 it2.vpos = it2.current_y = 0;
9599 move_it_to (&it2, start_charpos, -1, -1, -1, MOVE_TO_POS);
9600 it->vpos -= it2.vpos;
9601 it->current_y -= it2.current_y;
9602 it->current_x = it->hpos = 0;
9603
9604 /* If we moved too far back, move IT some lines forward. */
9605 if (it2.vpos > -dvpos)
9606 {
9607 int delta = it2.vpos + dvpos;
9608
9609 RESTORE_IT (&it2, &it2, it2data);
9610 SAVE_IT (it2, *it, it2data);
9611 move_it_to (it, -1, -1, -1, it->vpos + delta, MOVE_TO_VPOS);
9612 /* Move back again if we got too far ahead. */
9613 if (IT_CHARPOS (*it) >= start_charpos)
9614 RESTORE_IT (it, &it2, it2data);
9615 else
9616 bidi_unshelve_cache (it2data, 1);
9617 }
9618 else if (hit_pos_limit && pos_limit > BEGV
9619 && dvpos < 0 && it2.vpos < -dvpos)
9620 {
9621 /* If we hit the limit, but still didn't make it far enough
9622 back, that means there's a display string with a newline
9623 covering a large chunk of text, and that caused
9624 back_to_previous_visible_line_start try to go too far.
9625 Punish those who commit such atrocities by going back
9626 until we've reached DVPOS, after lifting the limit, which
9627 could make it slow for very long lines. "If it hurts,
9628 don't do that!" */
9629 dvpos += it2.vpos;
9630 RESTORE_IT (it, it, it2data);
9631 for (i = -dvpos; i > 0; --i)
9632 {
9633 back_to_previous_visible_line_start (it);
9634 it->vpos--;
9635 }
9636 reseat_1 (it, it->current.pos, 1);
9637 }
9638 else
9639 RESTORE_IT (it, it, it2data);
9640 }
9641 }
9642
9643 /* Return true if IT points into the middle of a display vector. */
9644
9645 bool
9646 in_display_vector_p (struct it *it)
9647 {
9648 return (it->method == GET_FROM_DISPLAY_VECTOR
9649 && it->current.dpvec_index > 0
9650 && it->dpvec + it->current.dpvec_index != it->dpend);
9651 }
9652
9653 DEFUN ("window-text-pixel-size", Fwindow_text_pixel_size, Swindow_text_pixel_size, 0, 6, 0,
9654 doc: /* Return the size of the text of WINDOW's buffer in pixels.
9655 WINDOW must be a live window and defaults to the selected one. The
9656 return value is a cons of the maximum pixel-width of any text line and
9657 the maximum pixel-height of all text lines.
9658
9659 The optional argument FROM, if non-nil, specifies the first text
9660 position and defaults to the minimum accessible position of the buffer.
9661 If FROM is t, use the minimum accessible position that is not a newline
9662 character. TO, if non-nil, specifies the last text position and
9663 defaults to the maximum accessible position of the buffer. If TO is t,
9664 use the maximum accessible position that is not a newline character.
9665
9666 The optional argument X-LIMIT, if non-nil, specifies the maximum text
9667 width that can be returned. X-LIMIT nil or omitted, means to use the
9668 pixel-width of WINDOW's body; use this if you do not intend to change
9669 the width of WINDOW. Use the maximum width WINDOW may assume if you
9670 intend to change WINDOW's width. In any case, text whose x-coordinate
9671 is beyond X-LIMIT is ignored. Since calculating the width of long lines
9672 can take some time, it's always a good idea to make this argument as
9673 small as possible; in particular, if the buffer contains long lines that
9674 shall be truncated anyway.
9675
9676 The optional argument Y-LIMIT, if non-nil, specifies the maximum text
9677 height that can be returned. Text lines whose y-coordinate is beyond
9678 Y-LIMIT are ignored. Since calculating the text height of a large
9679 buffer can take some time, it makes sense to specify this argument if
9680 the size of the buffer is unknown.
9681
9682 Optional argument MODE-AND-HEADER-LINE nil or omitted means do not
9683 include the height of the mode- or header-line of WINDOW in the return
9684 value. If it is either the symbol `mode-line' or `header-line', include
9685 only the height of that line, if present, in the return value. If t,
9686 include the height of both, if present, in the return value. */)
9687 (Lisp_Object window, Lisp_Object from, Lisp_Object to, Lisp_Object x_limit, Lisp_Object y_limit,
9688 Lisp_Object mode_and_header_line)
9689 {
9690 struct window *w = decode_live_window (window);
9691 Lisp_Object buf;
9692 struct buffer *b;
9693 struct it it;
9694 struct buffer *old_buffer = NULL;
9695 ptrdiff_t start, end, pos;
9696 struct text_pos startp;
9697 void *itdata = NULL;
9698 int c, max_y = -1, x = 0, y = 0;
9699
9700 buf = w->contents;
9701 CHECK_BUFFER (buf);
9702 b = XBUFFER (buf);
9703
9704 if (b != current_buffer)
9705 {
9706 old_buffer = current_buffer;
9707 set_buffer_internal (b);
9708 }
9709
9710 if (NILP (from))
9711 start = BEGV;
9712 else if (EQ (from, Qt))
9713 {
9714 start = pos = BEGV;
9715 while ((pos++ < ZV) && (c = FETCH_CHAR (pos))
9716 && (c == ' ' || c == '\t' || c == '\n' || c == '\r'))
9717 start = pos;
9718 while ((pos-- > BEGV) && (c = FETCH_CHAR (pos)) && (c == ' ' || c == '\t'))
9719 start = pos;
9720 }
9721 else
9722 {
9723 CHECK_NUMBER_COERCE_MARKER (from);
9724 start = min (max (XINT (from), BEGV), ZV);
9725 }
9726
9727 if (NILP (to))
9728 end = ZV;
9729 else if (EQ (to, Qt))
9730 {
9731 end = pos = ZV;
9732 while ((pos-- > BEGV) && (c = FETCH_CHAR (pos))
9733 && (c == ' ' || c == '\t' || c == '\n' || c == '\r'))
9734 end = pos;
9735 while ((pos++ < ZV) && (c = FETCH_CHAR (pos)) && (c == ' ' || c == '\t'))
9736 end = pos;
9737 }
9738 else
9739 {
9740 CHECK_NUMBER_COERCE_MARKER (to);
9741 end = max (start, min (XINT (to), ZV));
9742 }
9743
9744 if (!NILP (y_limit))
9745 {
9746 CHECK_NUMBER (y_limit);
9747 max_y = min (XINT (y_limit), INT_MAX);
9748 }
9749
9750 itdata = bidi_shelve_cache ();
9751 SET_TEXT_POS (startp, start, CHAR_TO_BYTE (start));
9752 start_display (&it, w, startp);
9753
9754 if (NILP (x_limit))
9755 x = move_it_to (&it, end, -1, max_y, -1, MOVE_TO_POS | MOVE_TO_Y);
9756 else
9757 {
9758 CHECK_NUMBER (x_limit);
9759 it.last_visible_x = min (XINT (x_limit), INFINITY);
9760 /* Actually, we never want move_it_to stop at to_x. But to make
9761 sure that move_it_in_display_line_to always moves far enough,
9762 we set it to INT_MAX and specify MOVE_TO_X. */
9763 x = move_it_to (&it, end, INT_MAX, max_y, -1,
9764 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
9765 }
9766
9767 y = it.current_y + it.max_ascent + it.max_descent;
9768
9769 if (!EQ (mode_and_header_line, Qheader_line)
9770 && !EQ (mode_and_header_line, Qt))
9771 /* Do not count the header-line which was counted automatically by
9772 start_display. */
9773 y = y - WINDOW_HEADER_LINE_HEIGHT (w);
9774
9775 if (EQ (mode_and_header_line, Qmode_line)
9776 || EQ (mode_and_header_line, Qt))
9777 /* Do count the mode-line which is not included automatically by
9778 start_display. */
9779 y = y + WINDOW_MODE_LINE_HEIGHT (w);
9780
9781 bidi_unshelve_cache (itdata, 0);
9782
9783 if (old_buffer)
9784 set_buffer_internal (old_buffer);
9785
9786 return Fcons (make_number (x), make_number (y));
9787 }
9788 \f
9789 /***********************************************************************
9790 Messages
9791 ***********************************************************************/
9792
9793
9794 /* Add a message with format string FORMAT and arguments ARG1 and ARG2
9795 to *Messages*. */
9796
9797 void
9798 add_to_log (const char *format, Lisp_Object arg1, Lisp_Object arg2)
9799 {
9800 Lisp_Object msg, fmt;
9801 char *buffer;
9802 ptrdiff_t len;
9803 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
9804 USE_SAFE_ALLOCA;
9805
9806 fmt = msg = Qnil;
9807 GCPRO4 (fmt, msg, arg1, arg2);
9808
9809 fmt = build_string (format);
9810 msg = CALLN (Fformat, fmt, arg1, arg2);
9811
9812 len = SBYTES (msg) + 1;
9813 buffer = SAFE_ALLOCA (len);
9814 memcpy (buffer, SDATA (msg), len);
9815
9816 message_dolog (buffer, len - 1, 1, 0);
9817 SAFE_FREE ();
9818
9819 UNGCPRO;
9820 }
9821
9822
9823 /* Output a newline in the *Messages* buffer if "needs" one. */
9824
9825 void
9826 message_log_maybe_newline (void)
9827 {
9828 if (message_log_need_newline)
9829 message_dolog ("", 0, 1, 0);
9830 }
9831
9832
9833 /* Add a string M of length NBYTES to the message log, optionally
9834 terminated with a newline when NLFLAG is true. MULTIBYTE, if
9835 true, means interpret the contents of M as multibyte. This
9836 function calls low-level routines in order to bypass text property
9837 hooks, etc. which might not be safe to run.
9838
9839 This may GC (insert may run before/after change hooks),
9840 so the buffer M must NOT point to a Lisp string. */
9841
9842 void
9843 message_dolog (const char *m, ptrdiff_t nbytes, bool nlflag, bool multibyte)
9844 {
9845 const unsigned char *msg = (const unsigned char *) m;
9846
9847 if (!NILP (Vmemory_full))
9848 return;
9849
9850 if (!NILP (Vmessage_log_max))
9851 {
9852 struct buffer *oldbuf;
9853 Lisp_Object oldpoint, oldbegv, oldzv;
9854 int old_windows_or_buffers_changed = windows_or_buffers_changed;
9855 ptrdiff_t point_at_end = 0;
9856 ptrdiff_t zv_at_end = 0;
9857 Lisp_Object old_deactivate_mark;
9858 struct gcpro gcpro1;
9859
9860 old_deactivate_mark = Vdeactivate_mark;
9861 oldbuf = current_buffer;
9862
9863 /* Ensure the Messages buffer exists, and switch to it.
9864 If we created it, set the major-mode. */
9865 {
9866 int newbuffer = 0;
9867 if (NILP (Fget_buffer (Vmessages_buffer_name))) newbuffer = 1;
9868
9869 Fset_buffer (Fget_buffer_create (Vmessages_buffer_name));
9870
9871 if (newbuffer
9872 && !NILP (Ffboundp (intern ("messages-buffer-mode"))))
9873 call0 (intern ("messages-buffer-mode"));
9874 }
9875
9876 bset_undo_list (current_buffer, Qt);
9877 bset_cache_long_scans (current_buffer, Qnil);
9878
9879 oldpoint = message_dolog_marker1;
9880 set_marker_restricted_both (oldpoint, Qnil, PT, PT_BYTE);
9881 oldbegv = message_dolog_marker2;
9882 set_marker_restricted_both (oldbegv, Qnil, BEGV, BEGV_BYTE);
9883 oldzv = message_dolog_marker3;
9884 set_marker_restricted_both (oldzv, Qnil, ZV, ZV_BYTE);
9885 GCPRO1 (old_deactivate_mark);
9886
9887 if (PT == Z)
9888 point_at_end = 1;
9889 if (ZV == Z)
9890 zv_at_end = 1;
9891
9892 BEGV = BEG;
9893 BEGV_BYTE = BEG_BYTE;
9894 ZV = Z;
9895 ZV_BYTE = Z_BYTE;
9896 TEMP_SET_PT_BOTH (Z, Z_BYTE);
9897
9898 /* Insert the string--maybe converting multibyte to single byte
9899 or vice versa, so that all the text fits the buffer. */
9900 if (multibyte
9901 && NILP (BVAR (current_buffer, enable_multibyte_characters)))
9902 {
9903 ptrdiff_t i;
9904 int c, char_bytes;
9905 char work[1];
9906
9907 /* Convert a multibyte string to single-byte
9908 for the *Message* buffer. */
9909 for (i = 0; i < nbytes; i += char_bytes)
9910 {
9911 c = string_char_and_length (msg + i, &char_bytes);
9912 work[0] = CHAR_TO_BYTE8 (c);
9913 insert_1_both (work, 1, 1, 1, 0, 0);
9914 }
9915 }
9916 else if (! multibyte
9917 && ! NILP (BVAR (current_buffer, enable_multibyte_characters)))
9918 {
9919 ptrdiff_t i;
9920 int c, char_bytes;
9921 unsigned char str[MAX_MULTIBYTE_LENGTH];
9922 /* Convert a single-byte string to multibyte
9923 for the *Message* buffer. */
9924 for (i = 0; i < nbytes; i++)
9925 {
9926 c = msg[i];
9927 MAKE_CHAR_MULTIBYTE (c);
9928 char_bytes = CHAR_STRING (c, str);
9929 insert_1_both ((char *) str, 1, char_bytes, 1, 0, 0);
9930 }
9931 }
9932 else if (nbytes)
9933 insert_1_both (m, chars_in_text (msg, nbytes), nbytes, 1, 0, 0);
9934
9935 if (nlflag)
9936 {
9937 ptrdiff_t this_bol, this_bol_byte, prev_bol, prev_bol_byte;
9938 printmax_t dups;
9939
9940 insert_1_both ("\n", 1, 1, 1, 0, 0);
9941
9942 scan_newline (Z, Z_BYTE, BEG, BEG_BYTE, -2, 0);
9943 this_bol = PT;
9944 this_bol_byte = PT_BYTE;
9945
9946 /* See if this line duplicates the previous one.
9947 If so, combine duplicates. */
9948 if (this_bol > BEG)
9949 {
9950 scan_newline (PT, PT_BYTE, BEG, BEG_BYTE, -2, 0);
9951 prev_bol = PT;
9952 prev_bol_byte = PT_BYTE;
9953
9954 dups = message_log_check_duplicate (prev_bol_byte,
9955 this_bol_byte);
9956 if (dups)
9957 {
9958 del_range_both (prev_bol, prev_bol_byte,
9959 this_bol, this_bol_byte, 0);
9960 if (dups > 1)
9961 {
9962 char dupstr[sizeof " [ times]"
9963 + INT_STRLEN_BOUND (printmax_t)];
9964
9965 /* If you change this format, don't forget to also
9966 change message_log_check_duplicate. */
9967 int duplen = sprintf (dupstr, " [%"pMd" times]", dups);
9968 TEMP_SET_PT_BOTH (Z - 1, Z_BYTE - 1);
9969 insert_1_both (dupstr, duplen, duplen, 1, 0, 1);
9970 }
9971 }
9972 }
9973
9974 /* If we have more than the desired maximum number of lines
9975 in the *Messages* buffer now, delete the oldest ones.
9976 This is safe because we don't have undo in this buffer. */
9977
9978 if (NATNUMP (Vmessage_log_max))
9979 {
9980 scan_newline (Z, Z_BYTE, BEG, BEG_BYTE,
9981 -XFASTINT (Vmessage_log_max) - 1, 0);
9982 del_range_both (BEG, BEG_BYTE, PT, PT_BYTE, 0);
9983 }
9984 }
9985 BEGV = marker_position (oldbegv);
9986 BEGV_BYTE = marker_byte_position (oldbegv);
9987
9988 if (zv_at_end)
9989 {
9990 ZV = Z;
9991 ZV_BYTE = Z_BYTE;
9992 }
9993 else
9994 {
9995 ZV = marker_position (oldzv);
9996 ZV_BYTE = marker_byte_position (oldzv);
9997 }
9998
9999 if (point_at_end)
10000 TEMP_SET_PT_BOTH (Z, Z_BYTE);
10001 else
10002 /* We can't do Fgoto_char (oldpoint) because it will run some
10003 Lisp code. */
10004 TEMP_SET_PT_BOTH (marker_position (oldpoint),
10005 marker_byte_position (oldpoint));
10006
10007 UNGCPRO;
10008 unchain_marker (XMARKER (oldpoint));
10009 unchain_marker (XMARKER (oldbegv));
10010 unchain_marker (XMARKER (oldzv));
10011
10012 /* We called insert_1_both above with its 5th argument (PREPARE)
10013 zero, which prevents insert_1_both from calling
10014 prepare_to_modify_buffer, which in turns prevents us from
10015 incrementing windows_or_buffers_changed even if *Messages* is
10016 shown in some window. So we must manually set
10017 windows_or_buffers_changed here to make up for that. */
10018 windows_or_buffers_changed = old_windows_or_buffers_changed;
10019 bset_redisplay (current_buffer);
10020
10021 set_buffer_internal (oldbuf);
10022
10023 message_log_need_newline = !nlflag;
10024 Vdeactivate_mark = old_deactivate_mark;
10025 }
10026 }
10027
10028
10029 /* We are at the end of the buffer after just having inserted a newline.
10030 (Note: We depend on the fact we won't be crossing the gap.)
10031 Check to see if the most recent message looks a lot like the previous one.
10032 Return 0 if different, 1 if the new one should just replace it, or a
10033 value N > 1 if we should also append " [N times]". */
10034
10035 static intmax_t
10036 message_log_check_duplicate (ptrdiff_t prev_bol_byte, ptrdiff_t this_bol_byte)
10037 {
10038 ptrdiff_t i;
10039 ptrdiff_t len = Z_BYTE - 1 - this_bol_byte;
10040 int seen_dots = 0;
10041 unsigned char *p1 = BUF_BYTE_ADDRESS (current_buffer, prev_bol_byte);
10042 unsigned char *p2 = BUF_BYTE_ADDRESS (current_buffer, this_bol_byte);
10043
10044 for (i = 0; i < len; i++)
10045 {
10046 if (i >= 3 && p1[i - 3] == '.' && p1[i - 2] == '.' && p1[i - 1] == '.')
10047 seen_dots = 1;
10048 if (p1[i] != p2[i])
10049 return seen_dots;
10050 }
10051 p1 += len;
10052 if (*p1 == '\n')
10053 return 2;
10054 if (*p1++ == ' ' && *p1++ == '[')
10055 {
10056 char *pend;
10057 intmax_t n = strtoimax ((char *) p1, &pend, 10);
10058 if (0 < n && n < INTMAX_MAX && strncmp (pend, " times]\n", 8) == 0)
10059 return n + 1;
10060 }
10061 return 0;
10062 }
10063 \f
10064
10065 /* Display an echo area message M with a specified length of NBYTES
10066 bytes. The string may include null characters. If M is not a
10067 string, clear out any existing message, and let the mini-buffer
10068 text show through.
10069
10070 This function cancels echoing. */
10071
10072 void
10073 message3 (Lisp_Object m)
10074 {
10075 struct gcpro gcpro1;
10076
10077 GCPRO1 (m);
10078 clear_message (true, true);
10079 cancel_echoing ();
10080
10081 /* First flush out any partial line written with print. */
10082 message_log_maybe_newline ();
10083 if (STRINGP (m))
10084 {
10085 ptrdiff_t nbytes = SBYTES (m);
10086 bool multibyte = STRING_MULTIBYTE (m);
10087 char *buffer;
10088 USE_SAFE_ALLOCA;
10089 SAFE_ALLOCA_STRING (buffer, m);
10090 message_dolog (buffer, nbytes, 1, multibyte);
10091 SAFE_FREE ();
10092 }
10093 message3_nolog (m);
10094
10095 UNGCPRO;
10096 }
10097
10098
10099 /* The non-logging version of message3.
10100 This does not cancel echoing, because it is used for echoing.
10101 Perhaps we need to make a separate function for echoing
10102 and make this cancel echoing. */
10103
10104 void
10105 message3_nolog (Lisp_Object m)
10106 {
10107 struct frame *sf = SELECTED_FRAME ();
10108
10109 if (FRAME_INITIAL_P (sf))
10110 {
10111 if (noninteractive_need_newline)
10112 putc ('\n', stderr);
10113 noninteractive_need_newline = 0;
10114 if (STRINGP (m))
10115 {
10116 Lisp_Object s = ENCODE_SYSTEM (m);
10117
10118 fwrite (SDATA (s), SBYTES (s), 1, stderr);
10119 }
10120 if (cursor_in_echo_area == 0)
10121 fprintf (stderr, "\n");
10122 fflush (stderr);
10123 }
10124 /* Error messages get reported properly by cmd_error, so this must be just an
10125 informative message; if the frame hasn't really been initialized yet, just
10126 toss it. */
10127 else if (INTERACTIVE && sf->glyphs_initialized_p)
10128 {
10129 /* Get the frame containing the mini-buffer
10130 that the selected frame is using. */
10131 Lisp_Object mini_window = FRAME_MINIBUF_WINDOW (sf);
10132 Lisp_Object frame = XWINDOW (mini_window)->frame;
10133 struct frame *f = XFRAME (frame);
10134
10135 if (FRAME_VISIBLE_P (sf) && !FRAME_VISIBLE_P (f))
10136 Fmake_frame_visible (frame);
10137
10138 if (STRINGP (m) && SCHARS (m) > 0)
10139 {
10140 set_message (m);
10141 if (minibuffer_auto_raise)
10142 Fraise_frame (frame);
10143 /* Assume we are not echoing.
10144 (If we are, echo_now will override this.) */
10145 echo_message_buffer = Qnil;
10146 }
10147 else
10148 clear_message (true, true);
10149
10150 do_pending_window_change (false);
10151 echo_area_display (true);
10152 do_pending_window_change (false);
10153 if (FRAME_TERMINAL (f)->frame_up_to_date_hook)
10154 (*FRAME_TERMINAL (f)->frame_up_to_date_hook) (f);
10155 }
10156 }
10157
10158
10159 /* Display a null-terminated echo area message M. If M is 0, clear
10160 out any existing message, and let the mini-buffer text show through.
10161
10162 The buffer M must continue to exist until after the echo area gets
10163 cleared or some other message gets displayed there. Do not pass
10164 text that is stored in a Lisp string. Do not pass text in a buffer
10165 that was alloca'd. */
10166
10167 void
10168 message1 (const char *m)
10169 {
10170 message3 (m ? build_unibyte_string (m) : Qnil);
10171 }
10172
10173
10174 /* The non-logging counterpart of message1. */
10175
10176 void
10177 message1_nolog (const char *m)
10178 {
10179 message3_nolog (m ? build_unibyte_string (m) : Qnil);
10180 }
10181
10182 /* Display a message M which contains a single %s
10183 which gets replaced with STRING. */
10184
10185 void
10186 message_with_string (const char *m, Lisp_Object string, int log)
10187 {
10188 CHECK_STRING (string);
10189
10190 if (noninteractive)
10191 {
10192 if (m)
10193 {
10194 /* ENCODE_SYSTEM below can GC and/or relocate the
10195 Lisp data, so make sure we don't use it here. */
10196 eassert (relocatable_string_data_p (m) != 1);
10197
10198 if (noninteractive_need_newline)
10199 putc ('\n', stderr);
10200 noninteractive_need_newline = 0;
10201 fprintf (stderr, m, SDATA (ENCODE_SYSTEM (string)));
10202 if (!cursor_in_echo_area)
10203 fprintf (stderr, "\n");
10204 fflush (stderr);
10205 }
10206 }
10207 else if (INTERACTIVE)
10208 {
10209 /* The frame whose minibuffer we're going to display the message on.
10210 It may be larger than the selected frame, so we need
10211 to use its buffer, not the selected frame's buffer. */
10212 Lisp_Object mini_window;
10213 struct frame *f, *sf = SELECTED_FRAME ();
10214
10215 /* Get the frame containing the minibuffer
10216 that the selected frame is using. */
10217 mini_window = FRAME_MINIBUF_WINDOW (sf);
10218 f = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
10219
10220 /* Error messages get reported properly by cmd_error, so this must be
10221 just an informative message; if the frame hasn't really been
10222 initialized yet, just toss it. */
10223 if (f->glyphs_initialized_p)
10224 {
10225 struct gcpro gcpro1, gcpro2;
10226
10227 Lisp_Object fmt = build_string (m);
10228 Lisp_Object msg = string;
10229 GCPRO2 (fmt, msg);
10230
10231 msg = CALLN (Fformat, fmt, msg);
10232
10233 if (log)
10234 message3 (msg);
10235 else
10236 message3_nolog (msg);
10237
10238 UNGCPRO;
10239
10240 /* Print should start at the beginning of the message
10241 buffer next time. */
10242 message_buf_print = 0;
10243 }
10244 }
10245 }
10246
10247
10248 /* Dump an informative message to the minibuf. If M is 0, clear out
10249 any existing message, and let the mini-buffer text show through. */
10250
10251 static void
10252 vmessage (const char *m, va_list ap)
10253 {
10254 if (noninteractive)
10255 {
10256 if (m)
10257 {
10258 if (noninteractive_need_newline)
10259 putc ('\n', stderr);
10260 noninteractive_need_newline = 0;
10261 vfprintf (stderr, m, ap);
10262 if (cursor_in_echo_area == 0)
10263 fprintf (stderr, "\n");
10264 fflush (stderr);
10265 }
10266 }
10267 else if (INTERACTIVE)
10268 {
10269 /* The frame whose mini-buffer we're going to display the message
10270 on. It may be larger than the selected frame, so we need to
10271 use its buffer, not the selected frame's buffer. */
10272 Lisp_Object mini_window;
10273 struct frame *f, *sf = SELECTED_FRAME ();
10274
10275 /* Get the frame containing the mini-buffer
10276 that the selected frame is using. */
10277 mini_window = FRAME_MINIBUF_WINDOW (sf);
10278 f = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
10279
10280 /* Error messages get reported properly by cmd_error, so this must be
10281 just an informative message; if the frame hasn't really been
10282 initialized yet, just toss it. */
10283 if (f->glyphs_initialized_p)
10284 {
10285 if (m)
10286 {
10287 ptrdiff_t len;
10288 ptrdiff_t maxsize = FRAME_MESSAGE_BUF_SIZE (f);
10289 USE_SAFE_ALLOCA;
10290 char *message_buf = SAFE_ALLOCA (maxsize + 1);
10291
10292 len = doprnt (message_buf, maxsize, m, 0, ap);
10293
10294 message3 (make_string (message_buf, len));
10295 SAFE_FREE ();
10296 }
10297 else
10298 message1 (0);
10299
10300 /* Print should start at the beginning of the message
10301 buffer next time. */
10302 message_buf_print = 0;
10303 }
10304 }
10305 }
10306
10307 void
10308 message (const char *m, ...)
10309 {
10310 va_list ap;
10311 va_start (ap, m);
10312 vmessage (m, ap);
10313 va_end (ap);
10314 }
10315
10316
10317 #if 0
10318 /* The non-logging version of message. */
10319
10320 void
10321 message_nolog (const char *m, ...)
10322 {
10323 Lisp_Object old_log_max;
10324 va_list ap;
10325 va_start (ap, m);
10326 old_log_max = Vmessage_log_max;
10327 Vmessage_log_max = Qnil;
10328 vmessage (m, ap);
10329 Vmessage_log_max = old_log_max;
10330 va_end (ap);
10331 }
10332 #endif
10333
10334
10335 /* Display the current message in the current mini-buffer. This is
10336 only called from error handlers in process.c, and is not time
10337 critical. */
10338
10339 void
10340 update_echo_area (void)
10341 {
10342 if (!NILP (echo_area_buffer[0]))
10343 {
10344 Lisp_Object string;
10345 string = Fcurrent_message ();
10346 message3 (string);
10347 }
10348 }
10349
10350
10351 /* Make sure echo area buffers in `echo_buffers' are live.
10352 If they aren't, make new ones. */
10353
10354 static void
10355 ensure_echo_area_buffers (void)
10356 {
10357 int i;
10358
10359 for (i = 0; i < 2; ++i)
10360 if (!BUFFERP (echo_buffer[i])
10361 || !BUFFER_LIVE_P (XBUFFER (echo_buffer[i])))
10362 {
10363 char name[30];
10364 Lisp_Object old_buffer;
10365 int j;
10366
10367 old_buffer = echo_buffer[i];
10368 echo_buffer[i] = Fget_buffer_create
10369 (make_formatted_string (name, " *Echo Area %d*", i));
10370 bset_truncate_lines (XBUFFER (echo_buffer[i]), Qnil);
10371 /* to force word wrap in echo area -
10372 it was decided to postpone this*/
10373 /* XBUFFER (echo_buffer[i])->word_wrap = Qt; */
10374
10375 for (j = 0; j < 2; ++j)
10376 if (EQ (old_buffer, echo_area_buffer[j]))
10377 echo_area_buffer[j] = echo_buffer[i];
10378 }
10379 }
10380
10381
10382 /* Call FN with args A1..A2 with either the current or last displayed
10383 echo_area_buffer as current buffer.
10384
10385 WHICH zero means use the current message buffer
10386 echo_area_buffer[0]. If that is nil, choose a suitable buffer
10387 from echo_buffer[] and clear it.
10388
10389 WHICH > 0 means use echo_area_buffer[1]. If that is nil, choose a
10390 suitable buffer from echo_buffer[] and clear it.
10391
10392 If WHICH < 0, set echo_area_buffer[1] to echo_area_buffer[0], so
10393 that the current message becomes the last displayed one, make
10394 choose a suitable buffer for echo_area_buffer[0], and clear it.
10395
10396 Value is what FN returns. */
10397
10398 static int
10399 with_echo_area_buffer (struct window *w, int which,
10400 int (*fn) (ptrdiff_t, Lisp_Object),
10401 ptrdiff_t a1, Lisp_Object a2)
10402 {
10403 Lisp_Object buffer;
10404 int this_one, the_other, clear_buffer_p, rc;
10405 ptrdiff_t count = SPECPDL_INDEX ();
10406
10407 /* If buffers aren't live, make new ones. */
10408 ensure_echo_area_buffers ();
10409
10410 clear_buffer_p = 0;
10411
10412 if (which == 0)
10413 this_one = 0, the_other = 1;
10414 else if (which > 0)
10415 this_one = 1, the_other = 0;
10416 else
10417 {
10418 this_one = 0, the_other = 1;
10419 clear_buffer_p = true;
10420
10421 /* We need a fresh one in case the current echo buffer equals
10422 the one containing the last displayed echo area message. */
10423 if (!NILP (echo_area_buffer[this_one])
10424 && EQ (echo_area_buffer[this_one], echo_area_buffer[the_other]))
10425 echo_area_buffer[this_one] = Qnil;
10426 }
10427
10428 /* Choose a suitable buffer from echo_buffer[] is we don't
10429 have one. */
10430 if (NILP (echo_area_buffer[this_one]))
10431 {
10432 echo_area_buffer[this_one]
10433 = (EQ (echo_area_buffer[the_other], echo_buffer[this_one])
10434 ? echo_buffer[the_other]
10435 : echo_buffer[this_one]);
10436 clear_buffer_p = true;
10437 }
10438
10439 buffer = echo_area_buffer[this_one];
10440
10441 /* Don't get confused by reusing the buffer used for echoing
10442 for a different purpose. */
10443 if (echo_kboard == NULL && EQ (buffer, echo_message_buffer))
10444 cancel_echoing ();
10445
10446 record_unwind_protect (unwind_with_echo_area_buffer,
10447 with_echo_area_buffer_unwind_data (w));
10448
10449 /* Make the echo area buffer current. Note that for display
10450 purposes, it is not necessary that the displayed window's buffer
10451 == current_buffer, except for text property lookup. So, let's
10452 only set that buffer temporarily here without doing a full
10453 Fset_window_buffer. We must also change w->pointm, though,
10454 because otherwise an assertions in unshow_buffer fails, and Emacs
10455 aborts. */
10456 set_buffer_internal_1 (XBUFFER (buffer));
10457 if (w)
10458 {
10459 wset_buffer (w, buffer);
10460 set_marker_both (w->pointm, buffer, BEG, BEG_BYTE);
10461 set_marker_both (w->old_pointm, buffer, BEG, BEG_BYTE);
10462 }
10463
10464 bset_undo_list (current_buffer, Qt);
10465 bset_read_only (current_buffer, Qnil);
10466 specbind (Qinhibit_read_only, Qt);
10467 specbind (Qinhibit_modification_hooks, Qt);
10468
10469 if (clear_buffer_p && Z > BEG)
10470 del_range (BEG, Z);
10471
10472 eassert (BEGV >= BEG);
10473 eassert (ZV <= Z && ZV >= BEGV);
10474
10475 rc = fn (a1, a2);
10476
10477 eassert (BEGV >= BEG);
10478 eassert (ZV <= Z && ZV >= BEGV);
10479
10480 unbind_to (count, Qnil);
10481 return rc;
10482 }
10483
10484
10485 /* Save state that should be preserved around the call to the function
10486 FN called in with_echo_area_buffer. */
10487
10488 static Lisp_Object
10489 with_echo_area_buffer_unwind_data (struct window *w)
10490 {
10491 int i = 0;
10492 Lisp_Object vector, tmp;
10493
10494 /* Reduce consing by keeping one vector in
10495 Vwith_echo_area_save_vector. */
10496 vector = Vwith_echo_area_save_vector;
10497 Vwith_echo_area_save_vector = Qnil;
10498
10499 if (NILP (vector))
10500 vector = Fmake_vector (make_number (11), Qnil);
10501
10502 XSETBUFFER (tmp, current_buffer); ASET (vector, i, tmp); ++i;
10503 ASET (vector, i, Vdeactivate_mark); ++i;
10504 ASET (vector, i, make_number (windows_or_buffers_changed)); ++i;
10505
10506 if (w)
10507 {
10508 XSETWINDOW (tmp, w); ASET (vector, i, tmp); ++i;
10509 ASET (vector, i, w->contents); ++i;
10510 ASET (vector, i, make_number (marker_position (w->pointm))); ++i;
10511 ASET (vector, i, make_number (marker_byte_position (w->pointm))); ++i;
10512 ASET (vector, i, make_number (marker_position (w->old_pointm))); ++i;
10513 ASET (vector, i, make_number (marker_byte_position (w->old_pointm))); ++i;
10514 ASET (vector, i, make_number (marker_position (w->start))); ++i;
10515 ASET (vector, i, make_number (marker_byte_position (w->start))); ++i;
10516 }
10517 else
10518 {
10519 int end = i + 8;
10520 for (; i < end; ++i)
10521 ASET (vector, i, Qnil);
10522 }
10523
10524 eassert (i == ASIZE (vector));
10525 return vector;
10526 }
10527
10528
10529 /* Restore global state from VECTOR which was created by
10530 with_echo_area_buffer_unwind_data. */
10531
10532 static void
10533 unwind_with_echo_area_buffer (Lisp_Object vector)
10534 {
10535 set_buffer_internal_1 (XBUFFER (AREF (vector, 0)));
10536 Vdeactivate_mark = AREF (vector, 1);
10537 windows_or_buffers_changed = XFASTINT (AREF (vector, 2));
10538
10539 if (WINDOWP (AREF (vector, 3)))
10540 {
10541 struct window *w;
10542 Lisp_Object buffer;
10543
10544 w = XWINDOW (AREF (vector, 3));
10545 buffer = AREF (vector, 4);
10546
10547 wset_buffer (w, buffer);
10548 set_marker_both (w->pointm, buffer,
10549 XFASTINT (AREF (vector, 5)),
10550 XFASTINT (AREF (vector, 6)));
10551 set_marker_both (w->old_pointm, buffer,
10552 XFASTINT (AREF (vector, 7)),
10553 XFASTINT (AREF (vector, 8)));
10554 set_marker_both (w->start, buffer,
10555 XFASTINT (AREF (vector, 9)),
10556 XFASTINT (AREF (vector, 10)));
10557 }
10558
10559 Vwith_echo_area_save_vector = vector;
10560 }
10561
10562
10563 /* Set up the echo area for use by print functions. MULTIBYTE_P
10564 non-zero means we will print multibyte. */
10565
10566 void
10567 setup_echo_area_for_printing (int multibyte_p)
10568 {
10569 /* If we can't find an echo area any more, exit. */
10570 if (! FRAME_LIVE_P (XFRAME (selected_frame)))
10571 Fkill_emacs (Qnil);
10572
10573 ensure_echo_area_buffers ();
10574
10575 if (!message_buf_print)
10576 {
10577 /* A message has been output since the last time we printed.
10578 Choose a fresh echo area buffer. */
10579 if (EQ (echo_area_buffer[1], echo_buffer[0]))
10580 echo_area_buffer[0] = echo_buffer[1];
10581 else
10582 echo_area_buffer[0] = echo_buffer[0];
10583
10584 /* Switch to that buffer and clear it. */
10585 set_buffer_internal (XBUFFER (echo_area_buffer[0]));
10586 bset_truncate_lines (current_buffer, Qnil);
10587
10588 if (Z > BEG)
10589 {
10590 ptrdiff_t count = SPECPDL_INDEX ();
10591 specbind (Qinhibit_read_only, Qt);
10592 /* Note that undo recording is always disabled. */
10593 del_range (BEG, Z);
10594 unbind_to (count, Qnil);
10595 }
10596 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
10597
10598 /* Set up the buffer for the multibyteness we need. */
10599 if (multibyte_p
10600 != !NILP (BVAR (current_buffer, enable_multibyte_characters)))
10601 Fset_buffer_multibyte (multibyte_p ? Qt : Qnil);
10602
10603 /* Raise the frame containing the echo area. */
10604 if (minibuffer_auto_raise)
10605 {
10606 struct frame *sf = SELECTED_FRAME ();
10607 Lisp_Object mini_window;
10608 mini_window = FRAME_MINIBUF_WINDOW (sf);
10609 Fraise_frame (WINDOW_FRAME (XWINDOW (mini_window)));
10610 }
10611
10612 message_log_maybe_newline ();
10613 message_buf_print = 1;
10614 }
10615 else
10616 {
10617 if (NILP (echo_area_buffer[0]))
10618 {
10619 if (EQ (echo_area_buffer[1], echo_buffer[0]))
10620 echo_area_buffer[0] = echo_buffer[1];
10621 else
10622 echo_area_buffer[0] = echo_buffer[0];
10623 }
10624
10625 if (current_buffer != XBUFFER (echo_area_buffer[0]))
10626 {
10627 /* Someone switched buffers between print requests. */
10628 set_buffer_internal (XBUFFER (echo_area_buffer[0]));
10629 bset_truncate_lines (current_buffer, Qnil);
10630 }
10631 }
10632 }
10633
10634
10635 /* Display an echo area message in window W. Value is non-zero if W's
10636 height is changed. If display_last_displayed_message_p is
10637 non-zero, display the message that was last displayed, otherwise
10638 display the current message. */
10639
10640 static int
10641 display_echo_area (struct window *w)
10642 {
10643 int i, no_message_p, window_height_changed_p;
10644
10645 /* Temporarily disable garbage collections while displaying the echo
10646 area. This is done because a GC can print a message itself.
10647 That message would modify the echo area buffer's contents while a
10648 redisplay of the buffer is going on, and seriously confuse
10649 redisplay. */
10650 ptrdiff_t count = inhibit_garbage_collection ();
10651
10652 /* If there is no message, we must call display_echo_area_1
10653 nevertheless because it resizes the window. But we will have to
10654 reset the echo_area_buffer in question to nil at the end because
10655 with_echo_area_buffer will sets it to an empty buffer. */
10656 i = display_last_displayed_message_p ? 1 : 0;
10657 no_message_p = NILP (echo_area_buffer[i]);
10658
10659 window_height_changed_p
10660 = with_echo_area_buffer (w, display_last_displayed_message_p,
10661 display_echo_area_1,
10662 (intptr_t) w, Qnil);
10663
10664 if (no_message_p)
10665 echo_area_buffer[i] = Qnil;
10666
10667 unbind_to (count, Qnil);
10668 return window_height_changed_p;
10669 }
10670
10671
10672 /* Helper for display_echo_area. Display the current buffer which
10673 contains the current echo area message in window W, a mini-window,
10674 a pointer to which is passed in A1. A2..A4 are currently not used.
10675 Change the height of W so that all of the message is displayed.
10676 Value is non-zero if height of W was changed. */
10677
10678 static int
10679 display_echo_area_1 (ptrdiff_t a1, Lisp_Object a2)
10680 {
10681 intptr_t i1 = a1;
10682 struct window *w = (struct window *) i1;
10683 Lisp_Object window;
10684 struct text_pos start;
10685 int window_height_changed_p = 0;
10686
10687 /* Do this before displaying, so that we have a large enough glyph
10688 matrix for the display. If we can't get enough space for the
10689 whole text, display the last N lines. That works by setting w->start. */
10690 window_height_changed_p = resize_mini_window (w, 0);
10691
10692 /* Use the starting position chosen by resize_mini_window. */
10693 SET_TEXT_POS_FROM_MARKER (start, w->start);
10694
10695 /* Display. */
10696 clear_glyph_matrix (w->desired_matrix);
10697 XSETWINDOW (window, w);
10698 try_window (window, start, 0);
10699
10700 return window_height_changed_p;
10701 }
10702
10703
10704 /* Resize the echo area window to exactly the size needed for the
10705 currently displayed message, if there is one. If a mini-buffer
10706 is active, don't shrink it. */
10707
10708 void
10709 resize_echo_area_exactly (void)
10710 {
10711 if (BUFFERP (echo_area_buffer[0])
10712 && WINDOWP (echo_area_window))
10713 {
10714 struct window *w = XWINDOW (echo_area_window);
10715 Lisp_Object resize_exactly = (minibuf_level == 0 ? Qt : Qnil);
10716 int resized_p = with_echo_area_buffer (w, 0, resize_mini_window_1,
10717 (intptr_t) w, resize_exactly);
10718 if (resized_p)
10719 {
10720 windows_or_buffers_changed = 42;
10721 update_mode_lines = 30;
10722 redisplay_internal ();
10723 }
10724 }
10725 }
10726
10727
10728 /* Callback function for with_echo_area_buffer, when used from
10729 resize_echo_area_exactly. A1 contains a pointer to the window to
10730 resize, EXACTLY non-nil means resize the mini-window exactly to the
10731 size of the text displayed. A3 and A4 are not used. Value is what
10732 resize_mini_window returns. */
10733
10734 static int
10735 resize_mini_window_1 (ptrdiff_t a1, Lisp_Object exactly)
10736 {
10737 intptr_t i1 = a1;
10738 return resize_mini_window ((struct window *) i1, !NILP (exactly));
10739 }
10740
10741
10742 /* Resize mini-window W to fit the size of its contents. EXACT_P
10743 means size the window exactly to the size needed. Otherwise, it's
10744 only enlarged until W's buffer is empty.
10745
10746 Set W->start to the right place to begin display. If the whole
10747 contents fit, start at the beginning. Otherwise, start so as
10748 to make the end of the contents appear. This is particularly
10749 important for y-or-n-p, but seems desirable generally.
10750
10751 Value is non-zero if the window height has been changed. */
10752
10753 int
10754 resize_mini_window (struct window *w, int exact_p)
10755 {
10756 struct frame *f = XFRAME (w->frame);
10757 int window_height_changed_p = 0;
10758
10759 eassert (MINI_WINDOW_P (w));
10760
10761 /* By default, start display at the beginning. */
10762 set_marker_both (w->start, w->contents,
10763 BUF_BEGV (XBUFFER (w->contents)),
10764 BUF_BEGV_BYTE (XBUFFER (w->contents)));
10765
10766 /* Don't resize windows while redisplaying a window; it would
10767 confuse redisplay functions when the size of the window they are
10768 displaying changes from under them. Such a resizing can happen,
10769 for instance, when which-func prints a long message while
10770 we are running fontification-functions. We're running these
10771 functions with safe_call which binds inhibit-redisplay to t. */
10772 if (!NILP (Vinhibit_redisplay))
10773 return 0;
10774
10775 /* Nil means don't try to resize. */
10776 if (NILP (Vresize_mini_windows)
10777 || (FRAME_X_P (f) && FRAME_X_OUTPUT (f) == NULL))
10778 return 0;
10779
10780 if (!FRAME_MINIBUF_ONLY_P (f))
10781 {
10782 struct it it;
10783 int total_height = (WINDOW_PIXEL_HEIGHT (XWINDOW (FRAME_ROOT_WINDOW (f)))
10784 + WINDOW_PIXEL_HEIGHT (w));
10785 int unit = FRAME_LINE_HEIGHT (f);
10786 int height, max_height;
10787 struct text_pos start;
10788 struct buffer *old_current_buffer = NULL;
10789
10790 if (current_buffer != XBUFFER (w->contents))
10791 {
10792 old_current_buffer = current_buffer;
10793 set_buffer_internal (XBUFFER (w->contents));
10794 }
10795
10796 init_iterator (&it, w, BEGV, BEGV_BYTE, NULL, DEFAULT_FACE_ID);
10797
10798 /* Compute the max. number of lines specified by the user. */
10799 if (FLOATP (Vmax_mini_window_height))
10800 max_height = XFLOATINT (Vmax_mini_window_height) * total_height;
10801 else if (INTEGERP (Vmax_mini_window_height))
10802 max_height = XINT (Vmax_mini_window_height) * unit;
10803 else
10804 max_height = total_height / 4;
10805
10806 /* Correct that max. height if it's bogus. */
10807 max_height = clip_to_bounds (unit, max_height, total_height);
10808
10809 /* Find out the height of the text in the window. */
10810 if (it.line_wrap == TRUNCATE)
10811 height = unit;
10812 else
10813 {
10814 last_height = 0;
10815 move_it_to (&it, ZV, -1, -1, -1, MOVE_TO_POS);
10816 if (it.max_ascent == 0 && it.max_descent == 0)
10817 height = it.current_y + last_height;
10818 else
10819 height = it.current_y + it.max_ascent + it.max_descent;
10820 height -= min (it.extra_line_spacing, it.max_extra_line_spacing);
10821 }
10822
10823 /* Compute a suitable window start. */
10824 if (height > max_height)
10825 {
10826 height = (max_height / unit) * unit;
10827 init_iterator (&it, w, ZV, ZV_BYTE, NULL, DEFAULT_FACE_ID);
10828 move_it_vertically_backward (&it, height - unit);
10829 start = it.current.pos;
10830 }
10831 else
10832 SET_TEXT_POS (start, BEGV, BEGV_BYTE);
10833 SET_MARKER_FROM_TEXT_POS (w->start, start);
10834
10835 if (EQ (Vresize_mini_windows, Qgrow_only))
10836 {
10837 /* Let it grow only, until we display an empty message, in which
10838 case the window shrinks again. */
10839 if (height > WINDOW_PIXEL_HEIGHT (w))
10840 {
10841 int old_height = WINDOW_PIXEL_HEIGHT (w);
10842
10843 FRAME_WINDOWS_FROZEN (f) = 1;
10844 grow_mini_window (w, height - WINDOW_PIXEL_HEIGHT (w), 1);
10845 window_height_changed_p = WINDOW_PIXEL_HEIGHT (w) != old_height;
10846 }
10847 else if (height < WINDOW_PIXEL_HEIGHT (w)
10848 && (exact_p || BEGV == ZV))
10849 {
10850 int old_height = WINDOW_PIXEL_HEIGHT (w);
10851
10852 FRAME_WINDOWS_FROZEN (f) = 0;
10853 shrink_mini_window (w, 1);
10854 window_height_changed_p = WINDOW_PIXEL_HEIGHT (w) != old_height;
10855 }
10856 }
10857 else
10858 {
10859 /* Always resize to exact size needed. */
10860 if (height > WINDOW_PIXEL_HEIGHT (w))
10861 {
10862 int old_height = WINDOW_PIXEL_HEIGHT (w);
10863
10864 FRAME_WINDOWS_FROZEN (f) = 1;
10865 grow_mini_window (w, height - WINDOW_PIXEL_HEIGHT (w), 1);
10866 window_height_changed_p = WINDOW_PIXEL_HEIGHT (w) != old_height;
10867 }
10868 else if (height < WINDOW_PIXEL_HEIGHT (w))
10869 {
10870 int old_height = WINDOW_PIXEL_HEIGHT (w);
10871
10872 FRAME_WINDOWS_FROZEN (f) = 0;
10873 shrink_mini_window (w, 1);
10874
10875 if (height)
10876 {
10877 FRAME_WINDOWS_FROZEN (f) = 1;
10878 grow_mini_window (w, height - WINDOW_PIXEL_HEIGHT (w), 1);
10879 }
10880
10881 window_height_changed_p = WINDOW_PIXEL_HEIGHT (w) != old_height;
10882 }
10883 }
10884
10885 if (old_current_buffer)
10886 set_buffer_internal (old_current_buffer);
10887 }
10888
10889 return window_height_changed_p;
10890 }
10891
10892
10893 /* Value is the current message, a string, or nil if there is no
10894 current message. */
10895
10896 Lisp_Object
10897 current_message (void)
10898 {
10899 Lisp_Object msg;
10900
10901 if (!BUFFERP (echo_area_buffer[0]))
10902 msg = Qnil;
10903 else
10904 {
10905 with_echo_area_buffer (0, 0, current_message_1,
10906 (intptr_t) &msg, Qnil);
10907 if (NILP (msg))
10908 echo_area_buffer[0] = Qnil;
10909 }
10910
10911 return msg;
10912 }
10913
10914
10915 static int
10916 current_message_1 (ptrdiff_t a1, Lisp_Object a2)
10917 {
10918 intptr_t i1 = a1;
10919 Lisp_Object *msg = (Lisp_Object *) i1;
10920
10921 if (Z > BEG)
10922 *msg = make_buffer_string (BEG, Z, 1);
10923 else
10924 *msg = Qnil;
10925 return 0;
10926 }
10927
10928
10929 /* Push the current message on Vmessage_stack for later restoration
10930 by restore_message. Value is non-zero if the current message isn't
10931 empty. This is a relatively infrequent operation, so it's not
10932 worth optimizing. */
10933
10934 bool
10935 push_message (void)
10936 {
10937 Lisp_Object msg = current_message ();
10938 Vmessage_stack = Fcons (msg, Vmessage_stack);
10939 return STRINGP (msg);
10940 }
10941
10942
10943 /* Restore message display from the top of Vmessage_stack. */
10944
10945 void
10946 restore_message (void)
10947 {
10948 eassert (CONSP (Vmessage_stack));
10949 message3_nolog (XCAR (Vmessage_stack));
10950 }
10951
10952
10953 /* Handler for unwind-protect calling pop_message. */
10954
10955 void
10956 pop_message_unwind (void)
10957 {
10958 /* Pop the top-most entry off Vmessage_stack. */
10959 eassert (CONSP (Vmessage_stack));
10960 Vmessage_stack = XCDR (Vmessage_stack);
10961 }
10962
10963
10964 /* Check that Vmessage_stack is nil. Called from emacs.c when Emacs
10965 exits. If the stack is not empty, we have a missing pop_message
10966 somewhere. */
10967
10968 void
10969 check_message_stack (void)
10970 {
10971 if (!NILP (Vmessage_stack))
10972 emacs_abort ();
10973 }
10974
10975
10976 /* Truncate to NCHARS what will be displayed in the echo area the next
10977 time we display it---but don't redisplay it now. */
10978
10979 void
10980 truncate_echo_area (ptrdiff_t nchars)
10981 {
10982 if (nchars == 0)
10983 echo_area_buffer[0] = Qnil;
10984 else if (!noninteractive
10985 && INTERACTIVE
10986 && !NILP (echo_area_buffer[0]))
10987 {
10988 struct frame *sf = SELECTED_FRAME ();
10989 /* Error messages get reported properly by cmd_error, so this must be
10990 just an informative message; if the frame hasn't really been
10991 initialized yet, just toss it. */
10992 if (sf->glyphs_initialized_p)
10993 with_echo_area_buffer (0, 0, truncate_message_1, nchars, Qnil);
10994 }
10995 }
10996
10997
10998 /* Helper function for truncate_echo_area. Truncate the current
10999 message to at most NCHARS characters. */
11000
11001 static int
11002 truncate_message_1 (ptrdiff_t nchars, Lisp_Object a2)
11003 {
11004 if (BEG + nchars < Z)
11005 del_range (BEG + nchars, Z);
11006 if (Z == BEG)
11007 echo_area_buffer[0] = Qnil;
11008 return 0;
11009 }
11010
11011 /* Set the current message to STRING. */
11012
11013 static void
11014 set_message (Lisp_Object string)
11015 {
11016 eassert (STRINGP (string));
11017
11018 message_enable_multibyte = STRING_MULTIBYTE (string);
11019
11020 with_echo_area_buffer (0, -1, set_message_1, 0, string);
11021 message_buf_print = 0;
11022 help_echo_showing_p = 0;
11023
11024 if (STRINGP (Vdebug_on_message)
11025 && STRINGP (string)
11026 && fast_string_match (Vdebug_on_message, string) >= 0)
11027 call_debugger (list2 (Qerror, string));
11028 }
11029
11030
11031 /* Helper function for set_message. First argument is ignored and second
11032 argument has the same meaning as for set_message.
11033 This function is called with the echo area buffer being current. */
11034
11035 static int
11036 set_message_1 (ptrdiff_t a1, Lisp_Object string)
11037 {
11038 eassert (STRINGP (string));
11039
11040 /* Change multibyteness of the echo buffer appropriately. */
11041 if (message_enable_multibyte
11042 != !NILP (BVAR (current_buffer, enable_multibyte_characters)))
11043 Fset_buffer_multibyte (message_enable_multibyte ? Qt : Qnil);
11044
11045 bset_truncate_lines (current_buffer, message_truncate_lines ? Qt : Qnil);
11046 if (!NILP (BVAR (current_buffer, bidi_display_reordering)))
11047 bset_bidi_paragraph_direction (current_buffer, Qleft_to_right);
11048
11049 /* Insert new message at BEG. */
11050 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
11051
11052 /* This function takes care of single/multibyte conversion.
11053 We just have to ensure that the echo area buffer has the right
11054 setting of enable_multibyte_characters. */
11055 insert_from_string (string, 0, 0, SCHARS (string), SBYTES (string), 1);
11056
11057 return 0;
11058 }
11059
11060
11061 /* Clear messages. CURRENT_P non-zero means clear the current
11062 message. LAST_DISPLAYED_P non-zero means clear the message
11063 last displayed. */
11064
11065 void
11066 clear_message (bool current_p, bool last_displayed_p)
11067 {
11068 if (current_p)
11069 {
11070 echo_area_buffer[0] = Qnil;
11071 message_cleared_p = true;
11072 }
11073
11074 if (last_displayed_p)
11075 echo_area_buffer[1] = Qnil;
11076
11077 message_buf_print = 0;
11078 }
11079
11080 /* Clear garbaged frames.
11081
11082 This function is used where the old redisplay called
11083 redraw_garbaged_frames which in turn called redraw_frame which in
11084 turn called clear_frame. The call to clear_frame was a source of
11085 flickering. I believe a clear_frame is not necessary. It should
11086 suffice in the new redisplay to invalidate all current matrices,
11087 and ensure a complete redisplay of all windows. */
11088
11089 static void
11090 clear_garbaged_frames (void)
11091 {
11092 if (frame_garbaged)
11093 {
11094 Lisp_Object tail, frame;
11095
11096 FOR_EACH_FRAME (tail, frame)
11097 {
11098 struct frame *f = XFRAME (frame);
11099
11100 if (FRAME_VISIBLE_P (f) && FRAME_GARBAGED_P (f))
11101 {
11102 if (f->resized_p)
11103 redraw_frame (f);
11104 else
11105 clear_current_matrices (f);
11106 fset_redisplay (f);
11107 f->garbaged = false;
11108 f->resized_p = false;
11109 }
11110 }
11111
11112 frame_garbaged = false;
11113 }
11114 }
11115
11116
11117 /* Redisplay the echo area of the selected frame. If UPDATE_FRAME_P
11118 is non-zero update selected_frame. Value is non-zero if the
11119 mini-windows height has been changed. */
11120
11121 static bool
11122 echo_area_display (bool update_frame_p)
11123 {
11124 Lisp_Object mini_window;
11125 struct window *w;
11126 struct frame *f;
11127 bool window_height_changed_p = false;
11128 struct frame *sf = SELECTED_FRAME ();
11129
11130 mini_window = FRAME_MINIBUF_WINDOW (sf);
11131 w = XWINDOW (mini_window);
11132 f = XFRAME (WINDOW_FRAME (w));
11133
11134 /* Don't display if frame is invisible or not yet initialized. */
11135 if (!FRAME_VISIBLE_P (f) || !f->glyphs_initialized_p)
11136 return 0;
11137
11138 #ifdef HAVE_WINDOW_SYSTEM
11139 /* When Emacs starts, selected_frame may be the initial terminal
11140 frame. If we let this through, a message would be displayed on
11141 the terminal. */
11142 if (FRAME_INITIAL_P (XFRAME (selected_frame)))
11143 return 0;
11144 #endif /* HAVE_WINDOW_SYSTEM */
11145
11146 /* Redraw garbaged frames. */
11147 clear_garbaged_frames ();
11148
11149 if (!NILP (echo_area_buffer[0]) || minibuf_level == 0)
11150 {
11151 echo_area_window = mini_window;
11152 window_height_changed_p = display_echo_area (w);
11153 w->must_be_updated_p = true;
11154
11155 /* Update the display, unless called from redisplay_internal.
11156 Also don't update the screen during redisplay itself. The
11157 update will happen at the end of redisplay, and an update
11158 here could cause confusion. */
11159 if (update_frame_p && !redisplaying_p)
11160 {
11161 int n = 0;
11162
11163 /* If the display update has been interrupted by pending
11164 input, update mode lines in the frame. Due to the
11165 pending input, it might have been that redisplay hasn't
11166 been called, so that mode lines above the echo area are
11167 garbaged. This looks odd, so we prevent it here. */
11168 if (!display_completed)
11169 n = redisplay_mode_lines (FRAME_ROOT_WINDOW (f), false);
11170
11171 if (window_height_changed_p
11172 /* Don't do this if Emacs is shutting down. Redisplay
11173 needs to run hooks. */
11174 && !NILP (Vrun_hooks))
11175 {
11176 /* Must update other windows. Likewise as in other
11177 cases, don't let this update be interrupted by
11178 pending input. */
11179 ptrdiff_t count = SPECPDL_INDEX ();
11180 specbind (Qredisplay_dont_pause, Qt);
11181 windows_or_buffers_changed = 44;
11182 redisplay_internal ();
11183 unbind_to (count, Qnil);
11184 }
11185 else if (FRAME_WINDOW_P (f) && n == 0)
11186 {
11187 /* Window configuration is the same as before.
11188 Can do with a display update of the echo area,
11189 unless we displayed some mode lines. */
11190 update_single_window (w);
11191 flush_frame (f);
11192 }
11193 else
11194 update_frame (f, true, true);
11195
11196 /* If cursor is in the echo area, make sure that the next
11197 redisplay displays the minibuffer, so that the cursor will
11198 be replaced with what the minibuffer wants. */
11199 if (cursor_in_echo_area)
11200 wset_redisplay (XWINDOW (mini_window));
11201 }
11202 }
11203 else if (!EQ (mini_window, selected_window))
11204 wset_redisplay (XWINDOW (mini_window));
11205
11206 /* Last displayed message is now the current message. */
11207 echo_area_buffer[1] = echo_area_buffer[0];
11208 /* Inform read_char that we're not echoing. */
11209 echo_message_buffer = Qnil;
11210
11211 /* Prevent redisplay optimization in redisplay_internal by resetting
11212 this_line_start_pos. This is done because the mini-buffer now
11213 displays the message instead of its buffer text. */
11214 if (EQ (mini_window, selected_window))
11215 CHARPOS (this_line_start_pos) = 0;
11216
11217 return window_height_changed_p;
11218 }
11219
11220 /* Nonzero if W's buffer was changed but not saved. */
11221
11222 static int
11223 window_buffer_changed (struct window *w)
11224 {
11225 struct buffer *b = XBUFFER (w->contents);
11226
11227 eassert (BUFFER_LIVE_P (b));
11228
11229 return (((BUF_SAVE_MODIFF (b) < BUF_MODIFF (b)) != w->last_had_star));
11230 }
11231
11232 /* Nonzero if W has %c in its mode line and mode line should be updated. */
11233
11234 static int
11235 mode_line_update_needed (struct window *w)
11236 {
11237 return (w->column_number_displayed != -1
11238 && !(PT == w->last_point && !window_outdated (w))
11239 && (w->column_number_displayed != current_column ()));
11240 }
11241
11242 /* Nonzero if window start of W is frozen and may not be changed during
11243 redisplay. */
11244
11245 static bool
11246 window_frozen_p (struct window *w)
11247 {
11248 if (FRAME_WINDOWS_FROZEN (XFRAME (WINDOW_FRAME (w))))
11249 {
11250 Lisp_Object window;
11251
11252 XSETWINDOW (window, w);
11253 if (MINI_WINDOW_P (w))
11254 return 0;
11255 else if (EQ (window, selected_window))
11256 return 0;
11257 else if (MINI_WINDOW_P (XWINDOW (selected_window))
11258 && EQ (window, Vminibuf_scroll_window))
11259 /* This special window can't be frozen too. */
11260 return 0;
11261 else
11262 return 1;
11263 }
11264 return 0;
11265 }
11266
11267 /***********************************************************************
11268 Mode Lines and Frame Titles
11269 ***********************************************************************/
11270
11271 /* A buffer for constructing non-propertized mode-line strings and
11272 frame titles in it; allocated from the heap in init_xdisp and
11273 resized as needed in store_mode_line_noprop_char. */
11274
11275 static char *mode_line_noprop_buf;
11276
11277 /* The buffer's end, and a current output position in it. */
11278
11279 static char *mode_line_noprop_buf_end;
11280 static char *mode_line_noprop_ptr;
11281
11282 #define MODE_LINE_NOPROP_LEN(start) \
11283 ((mode_line_noprop_ptr - mode_line_noprop_buf) - start)
11284
11285 static enum {
11286 MODE_LINE_DISPLAY = 0,
11287 MODE_LINE_TITLE,
11288 MODE_LINE_NOPROP,
11289 MODE_LINE_STRING
11290 } mode_line_target;
11291
11292 /* Alist that caches the results of :propertize.
11293 Each element is (PROPERTIZED-STRING . PROPERTY-LIST). */
11294 static Lisp_Object mode_line_proptrans_alist;
11295
11296 /* List of strings making up the mode-line. */
11297 static Lisp_Object mode_line_string_list;
11298
11299 /* Base face property when building propertized mode line string. */
11300 static Lisp_Object mode_line_string_face;
11301 static Lisp_Object mode_line_string_face_prop;
11302
11303
11304 /* Unwind data for mode line strings */
11305
11306 static Lisp_Object Vmode_line_unwind_vector;
11307
11308 static Lisp_Object
11309 format_mode_line_unwind_data (struct frame *target_frame,
11310 struct buffer *obuf,
11311 Lisp_Object owin,
11312 int save_proptrans)
11313 {
11314 Lisp_Object vector, tmp;
11315
11316 /* Reduce consing by keeping one vector in
11317 Vwith_echo_area_save_vector. */
11318 vector = Vmode_line_unwind_vector;
11319 Vmode_line_unwind_vector = Qnil;
11320
11321 if (NILP (vector))
11322 vector = Fmake_vector (make_number (10), Qnil);
11323
11324 ASET (vector, 0, make_number (mode_line_target));
11325 ASET (vector, 1, make_number (MODE_LINE_NOPROP_LEN (0)));
11326 ASET (vector, 2, mode_line_string_list);
11327 ASET (vector, 3, save_proptrans ? mode_line_proptrans_alist : Qt);
11328 ASET (vector, 4, mode_line_string_face);
11329 ASET (vector, 5, mode_line_string_face_prop);
11330
11331 if (obuf)
11332 XSETBUFFER (tmp, obuf);
11333 else
11334 tmp = Qnil;
11335 ASET (vector, 6, tmp);
11336 ASET (vector, 7, owin);
11337 if (target_frame)
11338 {
11339 /* Similarly to `with-selected-window', if the operation selects
11340 a window on another frame, we must restore that frame's
11341 selected window, and (for a tty) the top-frame. */
11342 ASET (vector, 8, target_frame->selected_window);
11343 if (FRAME_TERMCAP_P (target_frame))
11344 ASET (vector, 9, FRAME_TTY (target_frame)->top_frame);
11345 }
11346
11347 return vector;
11348 }
11349
11350 static void
11351 unwind_format_mode_line (Lisp_Object vector)
11352 {
11353 Lisp_Object old_window = AREF (vector, 7);
11354 Lisp_Object target_frame_window = AREF (vector, 8);
11355 Lisp_Object old_top_frame = AREF (vector, 9);
11356
11357 mode_line_target = XINT (AREF (vector, 0));
11358 mode_line_noprop_ptr = mode_line_noprop_buf + XINT (AREF (vector, 1));
11359 mode_line_string_list = AREF (vector, 2);
11360 if (! EQ (AREF (vector, 3), Qt))
11361 mode_line_proptrans_alist = AREF (vector, 3);
11362 mode_line_string_face = AREF (vector, 4);
11363 mode_line_string_face_prop = AREF (vector, 5);
11364
11365 /* Select window before buffer, since it may change the buffer. */
11366 if (!NILP (old_window))
11367 {
11368 /* If the operation that we are unwinding had selected a window
11369 on a different frame, reset its frame-selected-window. For a
11370 text terminal, reset its top-frame if necessary. */
11371 if (!NILP (target_frame_window))
11372 {
11373 Lisp_Object frame
11374 = WINDOW_FRAME (XWINDOW (target_frame_window));
11375
11376 if (!EQ (frame, WINDOW_FRAME (XWINDOW (old_window))))
11377 Fselect_window (target_frame_window, Qt);
11378
11379 if (!NILP (old_top_frame) && !EQ (old_top_frame, frame))
11380 Fselect_frame (old_top_frame, Qt);
11381 }
11382
11383 Fselect_window (old_window, Qt);
11384 }
11385
11386 if (!NILP (AREF (vector, 6)))
11387 {
11388 set_buffer_internal_1 (XBUFFER (AREF (vector, 6)));
11389 ASET (vector, 6, Qnil);
11390 }
11391
11392 Vmode_line_unwind_vector = vector;
11393 }
11394
11395
11396 /* Store a single character C for the frame title in mode_line_noprop_buf.
11397 Re-allocate mode_line_noprop_buf if necessary. */
11398
11399 static void
11400 store_mode_line_noprop_char (char c)
11401 {
11402 /* If output position has reached the end of the allocated buffer,
11403 increase the buffer's size. */
11404 if (mode_line_noprop_ptr == mode_line_noprop_buf_end)
11405 {
11406 ptrdiff_t len = MODE_LINE_NOPROP_LEN (0);
11407 ptrdiff_t size = len;
11408 mode_line_noprop_buf =
11409 xpalloc (mode_line_noprop_buf, &size, 1, STRING_BYTES_BOUND, 1);
11410 mode_line_noprop_buf_end = mode_line_noprop_buf + size;
11411 mode_line_noprop_ptr = mode_line_noprop_buf + len;
11412 }
11413
11414 *mode_line_noprop_ptr++ = c;
11415 }
11416
11417
11418 /* Store part of a frame title in mode_line_noprop_buf, beginning at
11419 mode_line_noprop_ptr. STRING is the string to store. Do not copy
11420 characters that yield more columns than PRECISION; PRECISION <= 0
11421 means copy the whole string. Pad with spaces until FIELD_WIDTH
11422 number of characters have been copied; FIELD_WIDTH <= 0 means don't
11423 pad. Called from display_mode_element when it is used to build a
11424 frame title. */
11425
11426 static int
11427 store_mode_line_noprop (const char *string, int field_width, int precision)
11428 {
11429 const unsigned char *str = (const unsigned char *) string;
11430 int n = 0;
11431 ptrdiff_t dummy, nbytes;
11432
11433 /* Copy at most PRECISION chars from STR. */
11434 nbytes = strlen (string);
11435 n += c_string_width (str, nbytes, precision, &dummy, &nbytes);
11436 while (nbytes--)
11437 store_mode_line_noprop_char (*str++);
11438
11439 /* Fill up with spaces until FIELD_WIDTH reached. */
11440 while (field_width > 0
11441 && n < field_width)
11442 {
11443 store_mode_line_noprop_char (' ');
11444 ++n;
11445 }
11446
11447 return n;
11448 }
11449
11450 /***********************************************************************
11451 Frame Titles
11452 ***********************************************************************/
11453
11454 #ifdef HAVE_WINDOW_SYSTEM
11455
11456 /* Set the title of FRAME, if it has changed. The title format is
11457 Vicon_title_format if FRAME is iconified, otherwise it is
11458 frame_title_format. */
11459
11460 static void
11461 x_consider_frame_title (Lisp_Object frame)
11462 {
11463 struct frame *f = XFRAME (frame);
11464
11465 if (FRAME_WINDOW_P (f)
11466 || FRAME_MINIBUF_ONLY_P (f)
11467 || f->explicit_name)
11468 {
11469 /* Do we have more than one visible frame on this X display? */
11470 Lisp_Object tail, other_frame, fmt;
11471 ptrdiff_t title_start;
11472 char *title;
11473 ptrdiff_t len;
11474 struct it it;
11475 ptrdiff_t count = SPECPDL_INDEX ();
11476
11477 FOR_EACH_FRAME (tail, other_frame)
11478 {
11479 struct frame *tf = XFRAME (other_frame);
11480
11481 if (tf != f
11482 && FRAME_KBOARD (tf) == FRAME_KBOARD (f)
11483 && !FRAME_MINIBUF_ONLY_P (tf)
11484 && !EQ (other_frame, tip_frame)
11485 && (FRAME_VISIBLE_P (tf) || FRAME_ICONIFIED_P (tf)))
11486 break;
11487 }
11488
11489 /* Set global variable indicating that multiple frames exist. */
11490 multiple_frames = CONSP (tail);
11491
11492 /* Switch to the buffer of selected window of the frame. Set up
11493 mode_line_target so that display_mode_element will output into
11494 mode_line_noprop_buf; then display the title. */
11495 record_unwind_protect (unwind_format_mode_line,
11496 format_mode_line_unwind_data
11497 (f, current_buffer, selected_window, 0));
11498
11499 Fselect_window (f->selected_window, Qt);
11500 set_buffer_internal_1
11501 (XBUFFER (XWINDOW (f->selected_window)->contents));
11502 fmt = FRAME_ICONIFIED_P (f) ? Vicon_title_format : Vframe_title_format;
11503
11504 mode_line_target = MODE_LINE_TITLE;
11505 title_start = MODE_LINE_NOPROP_LEN (0);
11506 init_iterator (&it, XWINDOW (f->selected_window), -1, -1,
11507 NULL, DEFAULT_FACE_ID);
11508 display_mode_element (&it, 0, -1, -1, fmt, Qnil, 0);
11509 len = MODE_LINE_NOPROP_LEN (title_start);
11510 title = mode_line_noprop_buf + title_start;
11511 unbind_to (count, Qnil);
11512
11513 /* Set the title only if it's changed. This avoids consing in
11514 the common case where it hasn't. (If it turns out that we've
11515 already wasted too much time by walking through the list with
11516 display_mode_element, then we might need to optimize at a
11517 higher level than this.) */
11518 if (! STRINGP (f->name)
11519 || SBYTES (f->name) != len
11520 || memcmp (title, SDATA (f->name), len) != 0)
11521 x_implicitly_set_name (f, make_string (title, len), Qnil);
11522 }
11523 }
11524
11525 #endif /* not HAVE_WINDOW_SYSTEM */
11526
11527 \f
11528 /***********************************************************************
11529 Menu Bars
11530 ***********************************************************************/
11531
11532 /* Non-zero if we will not redisplay all visible windows. */
11533 #define REDISPLAY_SOME_P() \
11534 ((windows_or_buffers_changed == 0 \
11535 || windows_or_buffers_changed == REDISPLAY_SOME) \
11536 && (update_mode_lines == 0 \
11537 || update_mode_lines == REDISPLAY_SOME))
11538
11539 /* Prepare for redisplay by updating menu-bar item lists when
11540 appropriate. This can call eval. */
11541
11542 static void
11543 prepare_menu_bars (void)
11544 {
11545 bool all_windows = windows_or_buffers_changed || update_mode_lines;
11546 bool some_windows = REDISPLAY_SOME_P ();
11547 struct gcpro gcpro1, gcpro2;
11548 Lisp_Object tooltip_frame;
11549
11550 #ifdef HAVE_WINDOW_SYSTEM
11551 tooltip_frame = tip_frame;
11552 #else
11553 tooltip_frame = Qnil;
11554 #endif
11555
11556 if (FUNCTIONP (Vpre_redisplay_function))
11557 {
11558 Lisp_Object windows = all_windows ? Qt : Qnil;
11559 if (all_windows && some_windows)
11560 {
11561 Lisp_Object ws = window_list ();
11562 for (windows = Qnil; CONSP (ws); ws = XCDR (ws))
11563 {
11564 Lisp_Object this = XCAR (ws);
11565 struct window *w = XWINDOW (this);
11566 if (w->redisplay
11567 || XFRAME (w->frame)->redisplay
11568 || XBUFFER (w->contents)->text->redisplay)
11569 {
11570 windows = Fcons (this, windows);
11571 }
11572 }
11573 }
11574 safe__call1 (true, Vpre_redisplay_function, windows);
11575 }
11576
11577 /* Update all frame titles based on their buffer names, etc. We do
11578 this before the menu bars so that the buffer-menu will show the
11579 up-to-date frame titles. */
11580 #ifdef HAVE_WINDOW_SYSTEM
11581 if (all_windows)
11582 {
11583 Lisp_Object tail, frame;
11584
11585 FOR_EACH_FRAME (tail, frame)
11586 {
11587 struct frame *f = XFRAME (frame);
11588 struct window *w = XWINDOW (FRAME_SELECTED_WINDOW (f));
11589 if (some_windows
11590 && !f->redisplay
11591 && !w->redisplay
11592 && !XBUFFER (w->contents)->text->redisplay)
11593 continue;
11594
11595 if (!EQ (frame, tooltip_frame)
11596 && (FRAME_ICONIFIED_P (f)
11597 || FRAME_VISIBLE_P (f) == 1
11598 /* Exclude TTY frames that are obscured because they
11599 are not the top frame on their console. This is
11600 because x_consider_frame_title actually switches
11601 to the frame, which for TTY frames means it is
11602 marked as garbaged, and will be completely
11603 redrawn on the next redisplay cycle. This causes
11604 TTY frames to be completely redrawn, when there
11605 are more than one of them, even though nothing
11606 should be changed on display. */
11607 || (FRAME_VISIBLE_P (f) == 2 && FRAME_WINDOW_P (f))))
11608 x_consider_frame_title (frame);
11609 }
11610 }
11611 #endif /* HAVE_WINDOW_SYSTEM */
11612
11613 /* Update the menu bar item lists, if appropriate. This has to be
11614 done before any actual redisplay or generation of display lines. */
11615
11616 if (all_windows)
11617 {
11618 Lisp_Object tail, frame;
11619 ptrdiff_t count = SPECPDL_INDEX ();
11620 /* 1 means that update_menu_bar has run its hooks
11621 so any further calls to update_menu_bar shouldn't do so again. */
11622 int menu_bar_hooks_run = 0;
11623
11624 record_unwind_save_match_data ();
11625
11626 FOR_EACH_FRAME (tail, frame)
11627 {
11628 struct frame *f = XFRAME (frame);
11629 struct window *w = XWINDOW (FRAME_SELECTED_WINDOW (f));
11630
11631 /* Ignore tooltip frame. */
11632 if (EQ (frame, tooltip_frame))
11633 continue;
11634
11635 if (some_windows
11636 && !f->redisplay
11637 && !w->redisplay
11638 && !XBUFFER (w->contents)->text->redisplay)
11639 continue;
11640
11641 /* If a window on this frame changed size, report that to
11642 the user and clear the size-change flag. */
11643 if (FRAME_WINDOW_SIZES_CHANGED (f))
11644 {
11645 Lisp_Object functions;
11646
11647 /* Clear flag first in case we get an error below. */
11648 FRAME_WINDOW_SIZES_CHANGED (f) = 0;
11649 functions = Vwindow_size_change_functions;
11650 GCPRO2 (tail, functions);
11651
11652 while (CONSP (functions))
11653 {
11654 if (!EQ (XCAR (functions), Qt))
11655 call1 (XCAR (functions), frame);
11656 functions = XCDR (functions);
11657 }
11658 UNGCPRO;
11659 }
11660
11661 GCPRO1 (tail);
11662 menu_bar_hooks_run = update_menu_bar (f, 0, menu_bar_hooks_run);
11663 #ifdef HAVE_WINDOW_SYSTEM
11664 update_tool_bar (f, 0);
11665 #endif
11666 UNGCPRO;
11667 }
11668
11669 unbind_to (count, Qnil);
11670 }
11671 else
11672 {
11673 struct frame *sf = SELECTED_FRAME ();
11674 update_menu_bar (sf, 1, 0);
11675 #ifdef HAVE_WINDOW_SYSTEM
11676 update_tool_bar (sf, 1);
11677 #endif
11678 }
11679 }
11680
11681
11682 /* Update the menu bar item list for frame F. This has to be done
11683 before we start to fill in any display lines, because it can call
11684 eval.
11685
11686 If SAVE_MATCH_DATA is non-zero, we must save and restore it here.
11687
11688 If HOOKS_RUN is 1, that means a previous call to update_menu_bar
11689 already ran the menu bar hooks for this redisplay, so there
11690 is no need to run them again. The return value is the
11691 updated value of this flag, to pass to the next call. */
11692
11693 static int
11694 update_menu_bar (struct frame *f, int save_match_data, int hooks_run)
11695 {
11696 Lisp_Object window;
11697 register struct window *w;
11698
11699 /* If called recursively during a menu update, do nothing. This can
11700 happen when, for instance, an activate-menubar-hook causes a
11701 redisplay. */
11702 if (inhibit_menubar_update)
11703 return hooks_run;
11704
11705 window = FRAME_SELECTED_WINDOW (f);
11706 w = XWINDOW (window);
11707
11708 if (FRAME_WINDOW_P (f)
11709 ?
11710 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) \
11711 || defined (HAVE_NS) || defined (USE_GTK)
11712 FRAME_EXTERNAL_MENU_BAR (f)
11713 #else
11714 FRAME_MENU_BAR_LINES (f) > 0
11715 #endif
11716 : FRAME_MENU_BAR_LINES (f) > 0)
11717 {
11718 /* If the user has switched buffers or windows, we need to
11719 recompute to reflect the new bindings. But we'll
11720 recompute when update_mode_lines is set too; that means
11721 that people can use force-mode-line-update to request
11722 that the menu bar be recomputed. The adverse effect on
11723 the rest of the redisplay algorithm is about the same as
11724 windows_or_buffers_changed anyway. */
11725 if (windows_or_buffers_changed
11726 /* This used to test w->update_mode_line, but we believe
11727 there is no need to recompute the menu in that case. */
11728 || update_mode_lines
11729 || window_buffer_changed (w))
11730 {
11731 struct buffer *prev = current_buffer;
11732 ptrdiff_t count = SPECPDL_INDEX ();
11733
11734 specbind (Qinhibit_menubar_update, Qt);
11735
11736 set_buffer_internal_1 (XBUFFER (w->contents));
11737 if (save_match_data)
11738 record_unwind_save_match_data ();
11739 if (NILP (Voverriding_local_map_menu_flag))
11740 {
11741 specbind (Qoverriding_terminal_local_map, Qnil);
11742 specbind (Qoverriding_local_map, Qnil);
11743 }
11744
11745 if (!hooks_run)
11746 {
11747 /* Run the Lucid hook. */
11748 safe_run_hooks (Qactivate_menubar_hook);
11749
11750 /* If it has changed current-menubar from previous value,
11751 really recompute the menu-bar from the value. */
11752 if (! NILP (Vlucid_menu_bar_dirty_flag))
11753 call0 (Qrecompute_lucid_menubar);
11754
11755 safe_run_hooks (Qmenu_bar_update_hook);
11756
11757 hooks_run = 1;
11758 }
11759
11760 XSETFRAME (Vmenu_updating_frame, f);
11761 fset_menu_bar_items (f, menu_bar_items (FRAME_MENU_BAR_ITEMS (f)));
11762
11763 /* Redisplay the menu bar in case we changed it. */
11764 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) \
11765 || defined (HAVE_NS) || defined (USE_GTK)
11766 if (FRAME_WINDOW_P (f))
11767 {
11768 #if defined (HAVE_NS)
11769 /* All frames on Mac OS share the same menubar. So only
11770 the selected frame should be allowed to set it. */
11771 if (f == SELECTED_FRAME ())
11772 #endif
11773 set_frame_menubar (f, 0, 0);
11774 }
11775 else
11776 /* On a terminal screen, the menu bar is an ordinary screen
11777 line, and this makes it get updated. */
11778 w->update_mode_line = 1;
11779 #else /* ! (USE_X_TOOLKIT || HAVE_NTGUI || HAVE_NS || USE_GTK) */
11780 /* In the non-toolkit version, the menu bar is an ordinary screen
11781 line, and this makes it get updated. */
11782 w->update_mode_line = 1;
11783 #endif /* ! (USE_X_TOOLKIT || HAVE_NTGUI || HAVE_NS || USE_GTK) */
11784
11785 unbind_to (count, Qnil);
11786 set_buffer_internal_1 (prev);
11787 }
11788 }
11789
11790 return hooks_run;
11791 }
11792
11793 /***********************************************************************
11794 Tool-bars
11795 ***********************************************************************/
11796
11797 #ifdef HAVE_WINDOW_SYSTEM
11798
11799 /* Select `frame' temporarily without running all the code in
11800 do_switch_frame.
11801 FIXME: Maybe do_switch_frame should be trimmed down similarly
11802 when `norecord' is set. */
11803 static void
11804 fast_set_selected_frame (Lisp_Object frame)
11805 {
11806 if (!EQ (selected_frame, frame))
11807 {
11808 selected_frame = frame;
11809 selected_window = XFRAME (frame)->selected_window;
11810 }
11811 }
11812
11813 /* Update the tool-bar item list for frame F. This has to be done
11814 before we start to fill in any display lines. Called from
11815 prepare_menu_bars. If SAVE_MATCH_DATA is non-zero, we must save
11816 and restore it here. */
11817
11818 static void
11819 update_tool_bar (struct frame *f, int save_match_data)
11820 {
11821 #if defined (USE_GTK) || defined (HAVE_NS)
11822 int do_update = FRAME_EXTERNAL_TOOL_BAR (f);
11823 #else
11824 int do_update = (WINDOWP (f->tool_bar_window)
11825 && WINDOW_TOTAL_LINES (XWINDOW (f->tool_bar_window)) > 0);
11826 #endif
11827
11828 if (do_update)
11829 {
11830 Lisp_Object window;
11831 struct window *w;
11832
11833 window = FRAME_SELECTED_WINDOW (f);
11834 w = XWINDOW (window);
11835
11836 /* If the user has switched buffers or windows, we need to
11837 recompute to reflect the new bindings. But we'll
11838 recompute when update_mode_lines is set too; that means
11839 that people can use force-mode-line-update to request
11840 that the menu bar be recomputed. The adverse effect on
11841 the rest of the redisplay algorithm is about the same as
11842 windows_or_buffers_changed anyway. */
11843 if (windows_or_buffers_changed
11844 || w->update_mode_line
11845 || update_mode_lines
11846 || window_buffer_changed (w))
11847 {
11848 struct buffer *prev = current_buffer;
11849 ptrdiff_t count = SPECPDL_INDEX ();
11850 Lisp_Object frame, new_tool_bar;
11851 int new_n_tool_bar;
11852 struct gcpro gcpro1;
11853
11854 /* Set current_buffer to the buffer of the selected
11855 window of the frame, so that we get the right local
11856 keymaps. */
11857 set_buffer_internal_1 (XBUFFER (w->contents));
11858
11859 /* Save match data, if we must. */
11860 if (save_match_data)
11861 record_unwind_save_match_data ();
11862
11863 /* Make sure that we don't accidentally use bogus keymaps. */
11864 if (NILP (Voverriding_local_map_menu_flag))
11865 {
11866 specbind (Qoverriding_terminal_local_map, Qnil);
11867 specbind (Qoverriding_local_map, Qnil);
11868 }
11869
11870 GCPRO1 (new_tool_bar);
11871
11872 /* We must temporarily set the selected frame to this frame
11873 before calling tool_bar_items, because the calculation of
11874 the tool-bar keymap uses the selected frame (see
11875 `tool-bar-make-keymap' in tool-bar.el). */
11876 eassert (EQ (selected_window,
11877 /* Since we only explicitly preserve selected_frame,
11878 check that selected_window would be redundant. */
11879 XFRAME (selected_frame)->selected_window));
11880 record_unwind_protect (fast_set_selected_frame, selected_frame);
11881 XSETFRAME (frame, f);
11882 fast_set_selected_frame (frame);
11883
11884 /* Build desired tool-bar items from keymaps. */
11885 new_tool_bar
11886 = tool_bar_items (Fcopy_sequence (f->tool_bar_items),
11887 &new_n_tool_bar);
11888
11889 /* Redisplay the tool-bar if we changed it. */
11890 if (new_n_tool_bar != f->n_tool_bar_items
11891 || NILP (Fequal (new_tool_bar, f->tool_bar_items)))
11892 {
11893 /* Redisplay that happens asynchronously due to an expose event
11894 may access f->tool_bar_items. Make sure we update both
11895 variables within BLOCK_INPUT so no such event interrupts. */
11896 block_input ();
11897 fset_tool_bar_items (f, new_tool_bar);
11898 f->n_tool_bar_items = new_n_tool_bar;
11899 w->update_mode_line = 1;
11900 unblock_input ();
11901 }
11902
11903 UNGCPRO;
11904
11905 unbind_to (count, Qnil);
11906 set_buffer_internal_1 (prev);
11907 }
11908 }
11909 }
11910
11911 #if ! defined (USE_GTK) && ! defined (HAVE_NS)
11912
11913 /* Set F->desired_tool_bar_string to a Lisp string representing frame
11914 F's desired tool-bar contents. F->tool_bar_items must have
11915 been set up previously by calling prepare_menu_bars. */
11916
11917 static void
11918 build_desired_tool_bar_string (struct frame *f)
11919 {
11920 int i, size, size_needed;
11921 struct gcpro gcpro1, gcpro2;
11922 Lisp_Object image, plist;
11923
11924 image = plist = Qnil;
11925 GCPRO2 (image, plist);
11926
11927 /* Prepare F->desired_tool_bar_string. If we can reuse it, do so.
11928 Otherwise, make a new string. */
11929
11930 /* The size of the string we might be able to reuse. */
11931 size = (STRINGP (f->desired_tool_bar_string)
11932 ? SCHARS (f->desired_tool_bar_string)
11933 : 0);
11934
11935 /* We need one space in the string for each image. */
11936 size_needed = f->n_tool_bar_items;
11937
11938 /* Reuse f->desired_tool_bar_string, if possible. */
11939 if (size < size_needed || NILP (f->desired_tool_bar_string))
11940 fset_desired_tool_bar_string
11941 (f, Fmake_string (make_number (size_needed), make_number (' ')));
11942 else
11943 {
11944 AUTO_LIST4 (props, Qdisplay, Qnil, Qmenu_item, Qnil);
11945 struct gcpro gcpro1;
11946 GCPRO1 (props);
11947 Fremove_text_properties (make_number (0), make_number (size),
11948 props, f->desired_tool_bar_string);
11949 UNGCPRO;
11950 }
11951
11952 /* Put a `display' property on the string for the images to display,
11953 put a `menu_item' property on tool-bar items with a value that
11954 is the index of the item in F's tool-bar item vector. */
11955 for (i = 0; i < f->n_tool_bar_items; ++i)
11956 {
11957 #define PROP(IDX) \
11958 AREF (f->tool_bar_items, i * TOOL_BAR_ITEM_NSLOTS + (IDX))
11959
11960 int enabled_p = !NILP (PROP (TOOL_BAR_ITEM_ENABLED_P));
11961 int selected_p = !NILP (PROP (TOOL_BAR_ITEM_SELECTED_P));
11962 int hmargin, vmargin, relief, idx, end;
11963
11964 /* If image is a vector, choose the image according to the
11965 button state. */
11966 image = PROP (TOOL_BAR_ITEM_IMAGES);
11967 if (VECTORP (image))
11968 {
11969 if (enabled_p)
11970 idx = (selected_p
11971 ? TOOL_BAR_IMAGE_ENABLED_SELECTED
11972 : TOOL_BAR_IMAGE_ENABLED_DESELECTED);
11973 else
11974 idx = (selected_p
11975 ? TOOL_BAR_IMAGE_DISABLED_SELECTED
11976 : TOOL_BAR_IMAGE_DISABLED_DESELECTED);
11977
11978 eassert (ASIZE (image) >= idx);
11979 image = AREF (image, idx);
11980 }
11981 else
11982 idx = -1;
11983
11984 /* Ignore invalid image specifications. */
11985 if (!valid_image_p (image))
11986 continue;
11987
11988 /* Display the tool-bar button pressed, or depressed. */
11989 plist = Fcopy_sequence (XCDR (image));
11990
11991 /* Compute margin and relief to draw. */
11992 relief = (tool_bar_button_relief >= 0
11993 ? tool_bar_button_relief
11994 : DEFAULT_TOOL_BAR_BUTTON_RELIEF);
11995 hmargin = vmargin = relief;
11996
11997 if (RANGED_INTEGERP (1, Vtool_bar_button_margin,
11998 INT_MAX - max (hmargin, vmargin)))
11999 {
12000 hmargin += XFASTINT (Vtool_bar_button_margin);
12001 vmargin += XFASTINT (Vtool_bar_button_margin);
12002 }
12003 else if (CONSP (Vtool_bar_button_margin))
12004 {
12005 if (RANGED_INTEGERP (1, XCAR (Vtool_bar_button_margin),
12006 INT_MAX - hmargin))
12007 hmargin += XFASTINT (XCAR (Vtool_bar_button_margin));
12008
12009 if (RANGED_INTEGERP (1, XCDR (Vtool_bar_button_margin),
12010 INT_MAX - vmargin))
12011 vmargin += XFASTINT (XCDR (Vtool_bar_button_margin));
12012 }
12013
12014 if (auto_raise_tool_bar_buttons_p)
12015 {
12016 /* Add a `:relief' property to the image spec if the item is
12017 selected. */
12018 if (selected_p)
12019 {
12020 plist = Fplist_put (plist, QCrelief, make_number (-relief));
12021 hmargin -= relief;
12022 vmargin -= relief;
12023 }
12024 }
12025 else
12026 {
12027 /* If image is selected, display it pressed, i.e. with a
12028 negative relief. If it's not selected, display it with a
12029 raised relief. */
12030 plist = Fplist_put (plist, QCrelief,
12031 (selected_p
12032 ? make_number (-relief)
12033 : make_number (relief)));
12034 hmargin -= relief;
12035 vmargin -= relief;
12036 }
12037
12038 /* Put a margin around the image. */
12039 if (hmargin || vmargin)
12040 {
12041 if (hmargin == vmargin)
12042 plist = Fplist_put (plist, QCmargin, make_number (hmargin));
12043 else
12044 plist = Fplist_put (plist, QCmargin,
12045 Fcons (make_number (hmargin),
12046 make_number (vmargin)));
12047 }
12048
12049 /* If button is not enabled, and we don't have special images
12050 for the disabled state, make the image appear disabled by
12051 applying an appropriate algorithm to it. */
12052 if (!enabled_p && idx < 0)
12053 plist = Fplist_put (plist, QCconversion, Qdisabled);
12054
12055 /* Put a `display' text property on the string for the image to
12056 display. Put a `menu-item' property on the string that gives
12057 the start of this item's properties in the tool-bar items
12058 vector. */
12059 image = Fcons (Qimage, plist);
12060 AUTO_LIST4 (props, Qdisplay, image, Qmenu_item,
12061 make_number (i * TOOL_BAR_ITEM_NSLOTS));
12062 struct gcpro gcpro1;
12063 GCPRO1 (props);
12064
12065 /* Let the last image hide all remaining spaces in the tool bar
12066 string. The string can be longer than needed when we reuse a
12067 previous string. */
12068 if (i + 1 == f->n_tool_bar_items)
12069 end = SCHARS (f->desired_tool_bar_string);
12070 else
12071 end = i + 1;
12072 Fadd_text_properties (make_number (i), make_number (end),
12073 props, f->desired_tool_bar_string);
12074 UNGCPRO;
12075 #undef PROP
12076 }
12077
12078 UNGCPRO;
12079 }
12080
12081
12082 /* Display one line of the tool-bar of frame IT->f.
12083
12084 HEIGHT specifies the desired height of the tool-bar line.
12085 If the actual height of the glyph row is less than HEIGHT, the
12086 row's height is increased to HEIGHT, and the icons are centered
12087 vertically in the new height.
12088
12089 If HEIGHT is -1, we are counting needed tool-bar lines, so don't
12090 count a final empty row in case the tool-bar width exactly matches
12091 the window width.
12092 */
12093
12094 static void
12095 display_tool_bar_line (struct it *it, int height)
12096 {
12097 struct glyph_row *row = it->glyph_row;
12098 int max_x = it->last_visible_x;
12099 struct glyph *last;
12100
12101 /* Don't extend on a previously drawn tool bar items (Bug#16058). */
12102 clear_glyph_row (row);
12103 row->enabled_p = true;
12104 row->y = it->current_y;
12105
12106 /* Note that this isn't made use of if the face hasn't a box,
12107 so there's no need to check the face here. */
12108 it->start_of_box_run_p = 1;
12109
12110 while (it->current_x < max_x)
12111 {
12112 int x, n_glyphs_before, i, nglyphs;
12113 struct it it_before;
12114
12115 /* Get the next display element. */
12116 if (!get_next_display_element (it))
12117 {
12118 /* Don't count empty row if we are counting needed tool-bar lines. */
12119 if (height < 0 && !it->hpos)
12120 return;
12121 break;
12122 }
12123
12124 /* Produce glyphs. */
12125 n_glyphs_before = row->used[TEXT_AREA];
12126 it_before = *it;
12127
12128 PRODUCE_GLYPHS (it);
12129
12130 nglyphs = row->used[TEXT_AREA] - n_glyphs_before;
12131 i = 0;
12132 x = it_before.current_x;
12133 while (i < nglyphs)
12134 {
12135 struct glyph *glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
12136
12137 if (x + glyph->pixel_width > max_x)
12138 {
12139 /* Glyph doesn't fit on line. Backtrack. */
12140 row->used[TEXT_AREA] = n_glyphs_before;
12141 *it = it_before;
12142 /* If this is the only glyph on this line, it will never fit on the
12143 tool-bar, so skip it. But ensure there is at least one glyph,
12144 so we don't accidentally disable the tool-bar. */
12145 if (n_glyphs_before == 0
12146 && (it->vpos > 0 || IT_STRING_CHARPOS (*it) < it->end_charpos-1))
12147 break;
12148 goto out;
12149 }
12150
12151 ++it->hpos;
12152 x += glyph->pixel_width;
12153 ++i;
12154 }
12155
12156 /* Stop at line end. */
12157 if (ITERATOR_AT_END_OF_LINE_P (it))
12158 break;
12159
12160 set_iterator_to_next (it, 1);
12161 }
12162
12163 out:;
12164
12165 row->displays_text_p = row->used[TEXT_AREA] != 0;
12166
12167 /* Use default face for the border below the tool bar.
12168
12169 FIXME: When auto-resize-tool-bars is grow-only, there is
12170 no additional border below the possibly empty tool-bar lines.
12171 So to make the extra empty lines look "normal", we have to
12172 use the tool-bar face for the border too. */
12173 if (!MATRIX_ROW_DISPLAYS_TEXT_P (row)
12174 && !EQ (Vauto_resize_tool_bars, Qgrow_only))
12175 it->face_id = DEFAULT_FACE_ID;
12176
12177 extend_face_to_end_of_line (it);
12178 last = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1;
12179 last->right_box_line_p = 1;
12180 if (last == row->glyphs[TEXT_AREA])
12181 last->left_box_line_p = 1;
12182
12183 /* Make line the desired height and center it vertically. */
12184 if ((height -= it->max_ascent + it->max_descent) > 0)
12185 {
12186 /* Don't add more than one line height. */
12187 height %= FRAME_LINE_HEIGHT (it->f);
12188 it->max_ascent += height / 2;
12189 it->max_descent += (height + 1) / 2;
12190 }
12191
12192 compute_line_metrics (it);
12193
12194 /* If line is empty, make it occupy the rest of the tool-bar. */
12195 if (!MATRIX_ROW_DISPLAYS_TEXT_P (row))
12196 {
12197 row->height = row->phys_height = it->last_visible_y - row->y;
12198 row->visible_height = row->height;
12199 row->ascent = row->phys_ascent = 0;
12200 row->extra_line_spacing = 0;
12201 }
12202
12203 row->full_width_p = 1;
12204 row->continued_p = 0;
12205 row->truncated_on_left_p = 0;
12206 row->truncated_on_right_p = 0;
12207
12208 it->current_x = it->hpos = 0;
12209 it->current_y += row->height;
12210 ++it->vpos;
12211 ++it->glyph_row;
12212 }
12213
12214
12215 /* Value is the number of pixels needed to make all tool-bar items of
12216 frame F visible. The actual number of glyph rows needed is
12217 returned in *N_ROWS if non-NULL. */
12218 static int
12219 tool_bar_height (struct frame *f, int *n_rows, bool pixelwise)
12220 {
12221 struct window *w = XWINDOW (f->tool_bar_window);
12222 struct it it;
12223 /* tool_bar_height is called from redisplay_tool_bar after building
12224 the desired matrix, so use (unused) mode-line row as temporary row to
12225 avoid destroying the first tool-bar row. */
12226 struct glyph_row *temp_row = MATRIX_MODE_LINE_ROW (w->desired_matrix);
12227
12228 /* Initialize an iterator for iteration over
12229 F->desired_tool_bar_string in the tool-bar window of frame F. */
12230 init_iterator (&it, w, -1, -1, temp_row, TOOL_BAR_FACE_ID);
12231 temp_row->reversed_p = false;
12232 it.first_visible_x = 0;
12233 it.last_visible_x = WINDOW_PIXEL_WIDTH (w);
12234 reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
12235 it.paragraph_embedding = L2R;
12236
12237 while (!ITERATOR_AT_END_P (&it))
12238 {
12239 clear_glyph_row (temp_row);
12240 it.glyph_row = temp_row;
12241 display_tool_bar_line (&it, -1);
12242 }
12243 clear_glyph_row (temp_row);
12244
12245 /* f->n_tool_bar_rows == 0 means "unknown"; -1 means no tool-bar. */
12246 if (n_rows)
12247 *n_rows = it.vpos > 0 ? it.vpos : -1;
12248
12249 if (pixelwise)
12250 return it.current_y;
12251 else
12252 return (it.current_y + FRAME_LINE_HEIGHT (f) - 1) / FRAME_LINE_HEIGHT (f);
12253 }
12254
12255 #endif /* !USE_GTK && !HAVE_NS */
12256
12257 DEFUN ("tool-bar-height", Ftool_bar_height, Stool_bar_height,
12258 0, 2, 0,
12259 doc: /* Return the number of lines occupied by the tool bar of FRAME.
12260 If FRAME is nil or omitted, use the selected frame. Optional argument
12261 PIXELWISE non-nil means return the height of the tool bar in pixels. */)
12262 (Lisp_Object frame, Lisp_Object pixelwise)
12263 {
12264 int height = 0;
12265
12266 #if ! defined (USE_GTK) && ! defined (HAVE_NS)
12267 struct frame *f = decode_any_frame (frame);
12268
12269 if (WINDOWP (f->tool_bar_window)
12270 && WINDOW_PIXEL_HEIGHT (XWINDOW (f->tool_bar_window)) > 0)
12271 {
12272 update_tool_bar (f, 1);
12273 if (f->n_tool_bar_items)
12274 {
12275 build_desired_tool_bar_string (f);
12276 height = tool_bar_height (f, NULL, NILP (pixelwise) ? 0 : 1);
12277 }
12278 }
12279 #endif
12280
12281 return make_number (height);
12282 }
12283
12284
12285 /* Display the tool-bar of frame F. Value is non-zero if tool-bar's
12286 height should be changed. */
12287 static int
12288 redisplay_tool_bar (struct frame *f)
12289 {
12290 #if defined (USE_GTK) || defined (HAVE_NS)
12291
12292 if (FRAME_EXTERNAL_TOOL_BAR (f))
12293 update_frame_tool_bar (f);
12294 return 0;
12295
12296 #else /* !USE_GTK && !HAVE_NS */
12297
12298 struct window *w;
12299 struct it it;
12300 struct glyph_row *row;
12301
12302 /* If frame hasn't a tool-bar window or if it is zero-height, don't
12303 do anything. This means you must start with tool-bar-lines
12304 non-zero to get the auto-sizing effect. Or in other words, you
12305 can turn off tool-bars by specifying tool-bar-lines zero. */
12306 if (!WINDOWP (f->tool_bar_window)
12307 || (w = XWINDOW (f->tool_bar_window),
12308 WINDOW_TOTAL_LINES (w) == 0))
12309 return 0;
12310
12311 /* Set up an iterator for the tool-bar window. */
12312 init_iterator (&it, w, -1, -1, w->desired_matrix->rows, TOOL_BAR_FACE_ID);
12313 it.first_visible_x = 0;
12314 it.last_visible_x = WINDOW_PIXEL_WIDTH (w);
12315 row = it.glyph_row;
12316 row->reversed_p = false;
12317
12318 /* Build a string that represents the contents of the tool-bar. */
12319 build_desired_tool_bar_string (f);
12320 reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
12321 /* FIXME: This should be controlled by a user option. But it
12322 doesn't make sense to have an R2L tool bar if the menu bar cannot
12323 be drawn also R2L, and making the menu bar R2L is tricky due
12324 toolkit-specific code that implements it. If an R2L tool bar is
12325 ever supported, display_tool_bar_line should also be augmented to
12326 call unproduce_glyphs like display_line and display_string
12327 do. */
12328 it.paragraph_embedding = L2R;
12329
12330 if (f->n_tool_bar_rows == 0)
12331 {
12332 int new_height = tool_bar_height (f, &f->n_tool_bar_rows, 1);
12333
12334 if (new_height != WINDOW_PIXEL_HEIGHT (w))
12335 {
12336 x_change_tool_bar_height (f, new_height);
12337 frame_default_tool_bar_height = new_height;
12338 /* Always do that now. */
12339 clear_glyph_matrix (w->desired_matrix);
12340 f->fonts_changed = 1;
12341 return 1;
12342 }
12343 }
12344
12345 /* Display as many lines as needed to display all tool-bar items. */
12346
12347 if (f->n_tool_bar_rows > 0)
12348 {
12349 int border, rows, height, extra;
12350
12351 if (TYPE_RANGED_INTEGERP (int, Vtool_bar_border))
12352 border = XINT (Vtool_bar_border);
12353 else if (EQ (Vtool_bar_border, Qinternal_border_width))
12354 border = FRAME_INTERNAL_BORDER_WIDTH (f);
12355 else if (EQ (Vtool_bar_border, Qborder_width))
12356 border = f->border_width;
12357 else
12358 border = 0;
12359 if (border < 0)
12360 border = 0;
12361
12362 rows = f->n_tool_bar_rows;
12363 height = max (1, (it.last_visible_y - border) / rows);
12364 extra = it.last_visible_y - border - height * rows;
12365
12366 while (it.current_y < it.last_visible_y)
12367 {
12368 int h = 0;
12369 if (extra > 0 && rows-- > 0)
12370 {
12371 h = (extra + rows - 1) / rows;
12372 extra -= h;
12373 }
12374 display_tool_bar_line (&it, height + h);
12375 }
12376 }
12377 else
12378 {
12379 while (it.current_y < it.last_visible_y)
12380 display_tool_bar_line (&it, 0);
12381 }
12382
12383 /* It doesn't make much sense to try scrolling in the tool-bar
12384 window, so don't do it. */
12385 w->desired_matrix->no_scrolling_p = 1;
12386 w->must_be_updated_p = 1;
12387
12388 if (!NILP (Vauto_resize_tool_bars))
12389 {
12390 int change_height_p = 0;
12391
12392 /* If we couldn't display everything, change the tool-bar's
12393 height if there is room for more. */
12394 if (IT_STRING_CHARPOS (it) < it.end_charpos)
12395 change_height_p = 1;
12396
12397 /* We subtract 1 because display_tool_bar_line advances the
12398 glyph_row pointer before returning to its caller. We want to
12399 examine the last glyph row produced by
12400 display_tool_bar_line. */
12401 row = it.glyph_row - 1;
12402
12403 /* If there are blank lines at the end, except for a partially
12404 visible blank line at the end that is smaller than
12405 FRAME_LINE_HEIGHT, change the tool-bar's height. */
12406 if (!MATRIX_ROW_DISPLAYS_TEXT_P (row)
12407 && row->height >= FRAME_LINE_HEIGHT (f))
12408 change_height_p = 1;
12409
12410 /* If row displays tool-bar items, but is partially visible,
12411 change the tool-bar's height. */
12412 if (MATRIX_ROW_DISPLAYS_TEXT_P (row)
12413 && MATRIX_ROW_BOTTOM_Y (row) > it.last_visible_y)
12414 change_height_p = 1;
12415
12416 /* Resize windows as needed by changing the `tool-bar-lines'
12417 frame parameter. */
12418 if (change_height_p)
12419 {
12420 int nrows;
12421 int new_height = tool_bar_height (f, &nrows, 1);
12422
12423 change_height_p = ((EQ (Vauto_resize_tool_bars, Qgrow_only)
12424 && !f->minimize_tool_bar_window_p)
12425 ? (new_height > WINDOW_PIXEL_HEIGHT (w))
12426 : (new_height != WINDOW_PIXEL_HEIGHT (w)));
12427 f->minimize_tool_bar_window_p = 0;
12428
12429 if (change_height_p)
12430 {
12431 x_change_tool_bar_height (f, new_height);
12432 frame_default_tool_bar_height = new_height;
12433 clear_glyph_matrix (w->desired_matrix);
12434 f->n_tool_bar_rows = nrows;
12435 f->fonts_changed = 1;
12436
12437 return 1;
12438 }
12439 }
12440 }
12441
12442 f->minimize_tool_bar_window_p = 0;
12443 return 0;
12444
12445 #endif /* USE_GTK || HAVE_NS */
12446 }
12447
12448 #if ! defined (USE_GTK) && ! defined (HAVE_NS)
12449
12450 /* Get information about the tool-bar item which is displayed in GLYPH
12451 on frame F. Return in *PROP_IDX the index where tool-bar item
12452 properties start in F->tool_bar_items. Value is zero if
12453 GLYPH doesn't display a tool-bar item. */
12454
12455 static int
12456 tool_bar_item_info (struct frame *f, struct glyph *glyph, int *prop_idx)
12457 {
12458 Lisp_Object prop;
12459 int success_p;
12460 int charpos;
12461
12462 /* This function can be called asynchronously, which means we must
12463 exclude any possibility that Fget_text_property signals an
12464 error. */
12465 charpos = min (SCHARS (f->current_tool_bar_string), glyph->charpos);
12466 charpos = max (0, charpos);
12467
12468 /* Get the text property `menu-item' at pos. The value of that
12469 property is the start index of this item's properties in
12470 F->tool_bar_items. */
12471 prop = Fget_text_property (make_number (charpos),
12472 Qmenu_item, f->current_tool_bar_string);
12473 if (INTEGERP (prop))
12474 {
12475 *prop_idx = XINT (prop);
12476 success_p = 1;
12477 }
12478 else
12479 success_p = 0;
12480
12481 return success_p;
12482 }
12483
12484 \f
12485 /* Get information about the tool-bar item at position X/Y on frame F.
12486 Return in *GLYPH a pointer to the glyph of the tool-bar item in
12487 the current matrix of the tool-bar window of F, or NULL if not
12488 on a tool-bar item. Return in *PROP_IDX the index of the tool-bar
12489 item in F->tool_bar_items. Value is
12490
12491 -1 if X/Y is not on a tool-bar item
12492 0 if X/Y is on the same item that was highlighted before.
12493 1 otherwise. */
12494
12495 static int
12496 get_tool_bar_item (struct frame *f, int x, int y, struct glyph **glyph,
12497 int *hpos, int *vpos, int *prop_idx)
12498 {
12499 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
12500 struct window *w = XWINDOW (f->tool_bar_window);
12501 int area;
12502
12503 /* Find the glyph under X/Y. */
12504 *glyph = x_y_to_hpos_vpos (w, x, y, hpos, vpos, 0, 0, &area);
12505 if (*glyph == NULL)
12506 return -1;
12507
12508 /* Get the start of this tool-bar item's properties in
12509 f->tool_bar_items. */
12510 if (!tool_bar_item_info (f, *glyph, prop_idx))
12511 return -1;
12512
12513 /* Is mouse on the highlighted item? */
12514 if (EQ (f->tool_bar_window, hlinfo->mouse_face_window)
12515 && *vpos >= hlinfo->mouse_face_beg_row
12516 && *vpos <= hlinfo->mouse_face_end_row
12517 && (*vpos > hlinfo->mouse_face_beg_row
12518 || *hpos >= hlinfo->mouse_face_beg_col)
12519 && (*vpos < hlinfo->mouse_face_end_row
12520 || *hpos < hlinfo->mouse_face_end_col
12521 || hlinfo->mouse_face_past_end))
12522 return 0;
12523
12524 return 1;
12525 }
12526
12527
12528 /* EXPORT:
12529 Handle mouse button event on the tool-bar of frame F, at
12530 frame-relative coordinates X/Y. DOWN_P is 1 for a button press,
12531 0 for button release. MODIFIERS is event modifiers for button
12532 release. */
12533
12534 void
12535 handle_tool_bar_click (struct frame *f, int x, int y, int down_p,
12536 int modifiers)
12537 {
12538 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
12539 struct window *w = XWINDOW (f->tool_bar_window);
12540 int hpos, vpos, prop_idx;
12541 struct glyph *glyph;
12542 Lisp_Object enabled_p;
12543 int ts;
12544
12545 /* If not on the highlighted tool-bar item, and mouse-highlight is
12546 non-nil, return. This is so we generate the tool-bar button
12547 click only when the mouse button is released on the same item as
12548 where it was pressed. However, when mouse-highlight is disabled,
12549 generate the click when the button is released regardless of the
12550 highlight, since tool-bar items are not highlighted in that
12551 case. */
12552 frame_to_window_pixel_xy (w, &x, &y);
12553 ts = get_tool_bar_item (f, x, y, &glyph, &hpos, &vpos, &prop_idx);
12554 if (ts == -1
12555 || (ts != 0 && !NILP (Vmouse_highlight)))
12556 return;
12557
12558 /* When mouse-highlight is off, generate the click for the item
12559 where the button was pressed, disregarding where it was
12560 released. */
12561 if (NILP (Vmouse_highlight) && !down_p)
12562 prop_idx = f->last_tool_bar_item;
12563
12564 /* If item is disabled, do nothing. */
12565 enabled_p = AREF (f->tool_bar_items, prop_idx + TOOL_BAR_ITEM_ENABLED_P);
12566 if (NILP (enabled_p))
12567 return;
12568
12569 if (down_p)
12570 {
12571 /* Show item in pressed state. */
12572 if (!NILP (Vmouse_highlight))
12573 show_mouse_face (hlinfo, DRAW_IMAGE_SUNKEN);
12574 f->last_tool_bar_item = prop_idx;
12575 }
12576 else
12577 {
12578 Lisp_Object key, frame;
12579 struct input_event event;
12580 EVENT_INIT (event);
12581
12582 /* Show item in released state. */
12583 if (!NILP (Vmouse_highlight))
12584 show_mouse_face (hlinfo, DRAW_IMAGE_RAISED);
12585
12586 key = AREF (f->tool_bar_items, prop_idx + TOOL_BAR_ITEM_KEY);
12587
12588 XSETFRAME (frame, f);
12589 event.kind = TOOL_BAR_EVENT;
12590 event.frame_or_window = frame;
12591 event.arg = frame;
12592 kbd_buffer_store_event (&event);
12593
12594 event.kind = TOOL_BAR_EVENT;
12595 event.frame_or_window = frame;
12596 event.arg = key;
12597 event.modifiers = modifiers;
12598 kbd_buffer_store_event (&event);
12599 f->last_tool_bar_item = -1;
12600 }
12601 }
12602
12603
12604 /* Possibly highlight a tool-bar item on frame F when mouse moves to
12605 tool-bar window-relative coordinates X/Y. Called from
12606 note_mouse_highlight. */
12607
12608 static void
12609 note_tool_bar_highlight (struct frame *f, int x, int y)
12610 {
12611 Lisp_Object window = f->tool_bar_window;
12612 struct window *w = XWINDOW (window);
12613 Display_Info *dpyinfo = FRAME_DISPLAY_INFO (f);
12614 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
12615 int hpos, vpos;
12616 struct glyph *glyph;
12617 struct glyph_row *row;
12618 int i;
12619 Lisp_Object enabled_p;
12620 int prop_idx;
12621 enum draw_glyphs_face draw = DRAW_IMAGE_RAISED;
12622 int mouse_down_p, rc;
12623
12624 /* Function note_mouse_highlight is called with negative X/Y
12625 values when mouse moves outside of the frame. */
12626 if (x <= 0 || y <= 0)
12627 {
12628 clear_mouse_face (hlinfo);
12629 return;
12630 }
12631
12632 rc = get_tool_bar_item (f, x, y, &glyph, &hpos, &vpos, &prop_idx);
12633 if (rc < 0)
12634 {
12635 /* Not on tool-bar item. */
12636 clear_mouse_face (hlinfo);
12637 return;
12638 }
12639 else if (rc == 0)
12640 /* On same tool-bar item as before. */
12641 goto set_help_echo;
12642
12643 clear_mouse_face (hlinfo);
12644
12645 /* Mouse is down, but on different tool-bar item? */
12646 mouse_down_p = (x_mouse_grabbed (dpyinfo)
12647 && f == dpyinfo->last_mouse_frame);
12648
12649 if (mouse_down_p && f->last_tool_bar_item != prop_idx)
12650 return;
12651
12652 draw = mouse_down_p ? DRAW_IMAGE_SUNKEN : DRAW_IMAGE_RAISED;
12653
12654 /* If tool-bar item is not enabled, don't highlight it. */
12655 enabled_p = AREF (f->tool_bar_items, prop_idx + TOOL_BAR_ITEM_ENABLED_P);
12656 if (!NILP (enabled_p) && !NILP (Vmouse_highlight))
12657 {
12658 /* Compute the x-position of the glyph. In front and past the
12659 image is a space. We include this in the highlighted area. */
12660 row = MATRIX_ROW (w->current_matrix, vpos);
12661 for (i = x = 0; i < hpos; ++i)
12662 x += row->glyphs[TEXT_AREA][i].pixel_width;
12663
12664 /* Record this as the current active region. */
12665 hlinfo->mouse_face_beg_col = hpos;
12666 hlinfo->mouse_face_beg_row = vpos;
12667 hlinfo->mouse_face_beg_x = x;
12668 hlinfo->mouse_face_past_end = 0;
12669
12670 hlinfo->mouse_face_end_col = hpos + 1;
12671 hlinfo->mouse_face_end_row = vpos;
12672 hlinfo->mouse_face_end_x = x + glyph->pixel_width;
12673 hlinfo->mouse_face_window = window;
12674 hlinfo->mouse_face_face_id = TOOL_BAR_FACE_ID;
12675
12676 /* Display it as active. */
12677 show_mouse_face (hlinfo, draw);
12678 }
12679
12680 set_help_echo:
12681
12682 /* Set help_echo_string to a help string to display for this tool-bar item.
12683 XTread_socket does the rest. */
12684 help_echo_object = help_echo_window = Qnil;
12685 help_echo_pos = -1;
12686 help_echo_string = AREF (f->tool_bar_items, prop_idx + TOOL_BAR_ITEM_HELP);
12687 if (NILP (help_echo_string))
12688 help_echo_string = AREF (f->tool_bar_items, prop_idx + TOOL_BAR_ITEM_CAPTION);
12689 }
12690
12691 #endif /* !USE_GTK && !HAVE_NS */
12692
12693 #endif /* HAVE_WINDOW_SYSTEM */
12694
12695
12696 \f
12697 /************************************************************************
12698 Horizontal scrolling
12699 ************************************************************************/
12700
12701 static int hscroll_window_tree (Lisp_Object);
12702 static int hscroll_windows (Lisp_Object);
12703
12704 /* For all leaf windows in the window tree rooted at WINDOW, set their
12705 hscroll value so that PT is (i) visible in the window, and (ii) so
12706 that it is not within a certain margin at the window's left and
12707 right border. Value is non-zero if any window's hscroll has been
12708 changed. */
12709
12710 static int
12711 hscroll_window_tree (Lisp_Object window)
12712 {
12713 int hscrolled_p = 0;
12714 int hscroll_relative_p = FLOATP (Vhscroll_step);
12715 int hscroll_step_abs = 0;
12716 double hscroll_step_rel = 0;
12717
12718 if (hscroll_relative_p)
12719 {
12720 hscroll_step_rel = XFLOAT_DATA (Vhscroll_step);
12721 if (hscroll_step_rel < 0)
12722 {
12723 hscroll_relative_p = 0;
12724 hscroll_step_abs = 0;
12725 }
12726 }
12727 else if (TYPE_RANGED_INTEGERP (int, Vhscroll_step))
12728 {
12729 hscroll_step_abs = XINT (Vhscroll_step);
12730 if (hscroll_step_abs < 0)
12731 hscroll_step_abs = 0;
12732 }
12733 else
12734 hscroll_step_abs = 0;
12735
12736 while (WINDOWP (window))
12737 {
12738 struct window *w = XWINDOW (window);
12739
12740 if (WINDOWP (w->contents))
12741 hscrolled_p |= hscroll_window_tree (w->contents);
12742 else if (w->cursor.vpos >= 0)
12743 {
12744 int h_margin;
12745 int text_area_width;
12746 struct glyph_row *cursor_row;
12747 struct glyph_row *bottom_row;
12748 int row_r2l_p;
12749
12750 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->desired_matrix, w);
12751 if (w->cursor.vpos < bottom_row - w->desired_matrix->rows)
12752 cursor_row = MATRIX_ROW (w->desired_matrix, w->cursor.vpos);
12753 else
12754 cursor_row = bottom_row - 1;
12755
12756 if (!cursor_row->enabled_p)
12757 {
12758 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
12759 if (w->cursor.vpos < bottom_row - w->current_matrix->rows)
12760 cursor_row = MATRIX_ROW (w->current_matrix, w->cursor.vpos);
12761 else
12762 cursor_row = bottom_row - 1;
12763 }
12764 row_r2l_p = cursor_row->reversed_p;
12765
12766 text_area_width = window_box_width (w, TEXT_AREA);
12767
12768 /* Scroll when cursor is inside this scroll margin. */
12769 h_margin = hscroll_margin * WINDOW_FRAME_COLUMN_WIDTH (w);
12770
12771 /* If the position of this window's point has explicitly
12772 changed, no more suspend auto hscrolling. */
12773 if (NILP (Fequal (Fwindow_point (window), Fwindow_old_point (window))))
12774 w->suspend_auto_hscroll = 0;
12775
12776 /* Remember window point. */
12777 Fset_marker (w->old_pointm,
12778 ((w == XWINDOW (selected_window))
12779 ? make_number (BUF_PT (XBUFFER (w->contents)))
12780 : Fmarker_position (w->pointm)),
12781 w->contents);
12782
12783 if (!NILP (Fbuffer_local_value (Qauto_hscroll_mode, w->contents))
12784 && w->suspend_auto_hscroll == 0
12785 /* In some pathological cases, like restoring a window
12786 configuration into a frame that is much smaller than
12787 the one from which the configuration was saved, we
12788 get glyph rows whose start and end have zero buffer
12789 positions, which we cannot handle below. Just skip
12790 such windows. */
12791 && CHARPOS (cursor_row->start.pos) >= BUF_BEG (w->contents)
12792 /* For left-to-right rows, hscroll when cursor is either
12793 (i) inside the right hscroll margin, or (ii) if it is
12794 inside the left margin and the window is already
12795 hscrolled. */
12796 && ((!row_r2l_p
12797 && ((w->hscroll && w->cursor.x <= h_margin)
12798 || (cursor_row->enabled_p
12799 && cursor_row->truncated_on_right_p
12800 && (w->cursor.x >= text_area_width - h_margin))))
12801 /* For right-to-left rows, the logic is similar,
12802 except that rules for scrolling to left and right
12803 are reversed. E.g., if cursor.x <= h_margin, we
12804 need to hscroll "to the right" unconditionally,
12805 and that will scroll the screen to the left so as
12806 to reveal the next portion of the row. */
12807 || (row_r2l_p
12808 && ((cursor_row->enabled_p
12809 /* FIXME: It is confusing to set the
12810 truncated_on_right_p flag when R2L rows
12811 are actually truncated on the left. */
12812 && cursor_row->truncated_on_right_p
12813 && w->cursor.x <= h_margin)
12814 || (w->hscroll
12815 && (w->cursor.x >= text_area_width - h_margin))))))
12816 {
12817 struct it it;
12818 ptrdiff_t hscroll;
12819 struct buffer *saved_current_buffer;
12820 ptrdiff_t pt;
12821 int wanted_x;
12822
12823 /* Find point in a display of infinite width. */
12824 saved_current_buffer = current_buffer;
12825 current_buffer = XBUFFER (w->contents);
12826
12827 if (w == XWINDOW (selected_window))
12828 pt = PT;
12829 else
12830 pt = clip_to_bounds (BEGV, marker_position (w->pointm), ZV);
12831
12832 /* Move iterator to pt starting at cursor_row->start in
12833 a line with infinite width. */
12834 init_to_row_start (&it, w, cursor_row);
12835 it.last_visible_x = INFINITY;
12836 move_it_in_display_line_to (&it, pt, -1, MOVE_TO_POS);
12837 current_buffer = saved_current_buffer;
12838
12839 /* Position cursor in window. */
12840 if (!hscroll_relative_p && hscroll_step_abs == 0)
12841 hscroll = max (0, (it.current_x
12842 - (ITERATOR_AT_END_OF_LINE_P (&it)
12843 ? (text_area_width - 4 * FRAME_COLUMN_WIDTH (it.f))
12844 : (text_area_width / 2))))
12845 / FRAME_COLUMN_WIDTH (it.f);
12846 else if ((!row_r2l_p
12847 && w->cursor.x >= text_area_width - h_margin)
12848 || (row_r2l_p && w->cursor.x <= h_margin))
12849 {
12850 if (hscroll_relative_p)
12851 wanted_x = text_area_width * (1 - hscroll_step_rel)
12852 - h_margin;
12853 else
12854 wanted_x = text_area_width
12855 - hscroll_step_abs * FRAME_COLUMN_WIDTH (it.f)
12856 - h_margin;
12857 hscroll
12858 = max (0, it.current_x - wanted_x) / FRAME_COLUMN_WIDTH (it.f);
12859 }
12860 else
12861 {
12862 if (hscroll_relative_p)
12863 wanted_x = text_area_width * hscroll_step_rel
12864 + h_margin;
12865 else
12866 wanted_x = hscroll_step_abs * FRAME_COLUMN_WIDTH (it.f)
12867 + h_margin;
12868 hscroll
12869 = max (0, it.current_x - wanted_x) / FRAME_COLUMN_WIDTH (it.f);
12870 }
12871 hscroll = max (hscroll, w->min_hscroll);
12872
12873 /* Don't prevent redisplay optimizations if hscroll
12874 hasn't changed, as it will unnecessarily slow down
12875 redisplay. */
12876 if (w->hscroll != hscroll)
12877 {
12878 XBUFFER (w->contents)->prevent_redisplay_optimizations_p = 1;
12879 w->hscroll = hscroll;
12880 hscrolled_p = 1;
12881 }
12882 }
12883 }
12884
12885 window = w->next;
12886 }
12887
12888 /* Value is non-zero if hscroll of any leaf window has been changed. */
12889 return hscrolled_p;
12890 }
12891
12892
12893 /* Set hscroll so that cursor is visible and not inside horizontal
12894 scroll margins for all windows in the tree rooted at WINDOW. See
12895 also hscroll_window_tree above. Value is non-zero if any window's
12896 hscroll has been changed. If it has, desired matrices on the frame
12897 of WINDOW are cleared. */
12898
12899 static int
12900 hscroll_windows (Lisp_Object window)
12901 {
12902 int hscrolled_p = hscroll_window_tree (window);
12903 if (hscrolled_p)
12904 clear_desired_matrices (XFRAME (WINDOW_FRAME (XWINDOW (window))));
12905 return hscrolled_p;
12906 }
12907
12908
12909 \f
12910 /************************************************************************
12911 Redisplay
12912 ************************************************************************/
12913
12914 /* Variables holding some state of redisplay if GLYPH_DEBUG is defined
12915 to a non-zero value. This is sometimes handy to have in a debugger
12916 session. */
12917
12918 #ifdef GLYPH_DEBUG
12919
12920 /* First and last unchanged row for try_window_id. */
12921
12922 static int debug_first_unchanged_at_end_vpos;
12923 static int debug_last_unchanged_at_beg_vpos;
12924
12925 /* Delta vpos and y. */
12926
12927 static int debug_dvpos, debug_dy;
12928
12929 /* Delta in characters and bytes for try_window_id. */
12930
12931 static ptrdiff_t debug_delta, debug_delta_bytes;
12932
12933 /* Values of window_end_pos and window_end_vpos at the end of
12934 try_window_id. */
12935
12936 static ptrdiff_t debug_end_vpos;
12937
12938 /* Append a string to W->desired_matrix->method. FMT is a printf
12939 format string. If trace_redisplay_p is true also printf the
12940 resulting string to stderr. */
12941
12942 static void debug_method_add (struct window *, char const *, ...)
12943 ATTRIBUTE_FORMAT_PRINTF (2, 3);
12944
12945 static void
12946 debug_method_add (struct window *w, char const *fmt, ...)
12947 {
12948 void *ptr = w;
12949 char *method = w->desired_matrix->method;
12950 int len = strlen (method);
12951 int size = sizeof w->desired_matrix->method;
12952 int remaining = size - len - 1;
12953 va_list ap;
12954
12955 if (len && remaining)
12956 {
12957 method[len] = '|';
12958 --remaining, ++len;
12959 }
12960
12961 va_start (ap, fmt);
12962 vsnprintf (method + len, remaining + 1, fmt, ap);
12963 va_end (ap);
12964
12965 if (trace_redisplay_p)
12966 fprintf (stderr, "%p (%s): %s\n",
12967 ptr,
12968 ((BUFFERP (w->contents)
12969 && STRINGP (BVAR (XBUFFER (w->contents), name)))
12970 ? SSDATA (BVAR (XBUFFER (w->contents), name))
12971 : "no buffer"),
12972 method + len);
12973 }
12974
12975 #endif /* GLYPH_DEBUG */
12976
12977
12978 /* Value is non-zero if all changes in window W, which displays
12979 current_buffer, are in the text between START and END. START is a
12980 buffer position, END is given as a distance from Z. Used in
12981 redisplay_internal for display optimization. */
12982
12983 static int
12984 text_outside_line_unchanged_p (struct window *w,
12985 ptrdiff_t start, ptrdiff_t end)
12986 {
12987 int unchanged_p = 1;
12988
12989 /* If text or overlays have changed, see where. */
12990 if (window_outdated (w))
12991 {
12992 /* Gap in the line? */
12993 if (GPT < start || Z - GPT < end)
12994 unchanged_p = 0;
12995
12996 /* Changes start in front of the line, or end after it? */
12997 if (unchanged_p
12998 && (BEG_UNCHANGED < start - 1
12999 || END_UNCHANGED < end))
13000 unchanged_p = 0;
13001
13002 /* If selective display, can't optimize if changes start at the
13003 beginning of the line. */
13004 if (unchanged_p
13005 && INTEGERP (BVAR (current_buffer, selective_display))
13006 && XINT (BVAR (current_buffer, selective_display)) > 0
13007 && (BEG_UNCHANGED < start || GPT <= start))
13008 unchanged_p = 0;
13009
13010 /* If there are overlays at the start or end of the line, these
13011 may have overlay strings with newlines in them. A change at
13012 START, for instance, may actually concern the display of such
13013 overlay strings as well, and they are displayed on different
13014 lines. So, quickly rule out this case. (For the future, it
13015 might be desirable to implement something more telling than
13016 just BEG/END_UNCHANGED.) */
13017 if (unchanged_p)
13018 {
13019 if (BEG + BEG_UNCHANGED == start
13020 && overlay_touches_p (start))
13021 unchanged_p = 0;
13022 if (END_UNCHANGED == end
13023 && overlay_touches_p (Z - end))
13024 unchanged_p = 0;
13025 }
13026
13027 /* Under bidi reordering, adding or deleting a character in the
13028 beginning of a paragraph, before the first strong directional
13029 character, can change the base direction of the paragraph (unless
13030 the buffer specifies a fixed paragraph direction), which will
13031 require to redisplay the whole paragraph. It might be worthwhile
13032 to find the paragraph limits and widen the range of redisplayed
13033 lines to that, but for now just give up this optimization. */
13034 if (!NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering))
13035 && NILP (BVAR (XBUFFER (w->contents), bidi_paragraph_direction)))
13036 unchanged_p = 0;
13037 }
13038
13039 return unchanged_p;
13040 }
13041
13042
13043 /* Do a frame update, taking possible shortcuts into account. This is
13044 the main external entry point for redisplay.
13045
13046 If the last redisplay displayed an echo area message and that message
13047 is no longer requested, we clear the echo area or bring back the
13048 mini-buffer if that is in use. */
13049
13050 void
13051 redisplay (void)
13052 {
13053 redisplay_internal ();
13054 }
13055
13056
13057 static Lisp_Object
13058 overlay_arrow_string_or_property (Lisp_Object var)
13059 {
13060 Lisp_Object val;
13061
13062 if (val = Fget (var, Qoverlay_arrow_string), STRINGP (val))
13063 return val;
13064
13065 return Voverlay_arrow_string;
13066 }
13067
13068 /* Return 1 if there are any overlay-arrows in current_buffer. */
13069 static int
13070 overlay_arrow_in_current_buffer_p (void)
13071 {
13072 Lisp_Object vlist;
13073
13074 for (vlist = Voverlay_arrow_variable_list;
13075 CONSP (vlist);
13076 vlist = XCDR (vlist))
13077 {
13078 Lisp_Object var = XCAR (vlist);
13079 Lisp_Object val;
13080
13081 if (!SYMBOLP (var))
13082 continue;
13083 val = find_symbol_value (var);
13084 if (MARKERP (val)
13085 && current_buffer == XMARKER (val)->buffer)
13086 return 1;
13087 }
13088 return 0;
13089 }
13090
13091
13092 /* Return 1 if any overlay_arrows have moved or overlay-arrow-string
13093 has changed. */
13094
13095 static int
13096 overlay_arrows_changed_p (void)
13097 {
13098 Lisp_Object vlist;
13099
13100 for (vlist = Voverlay_arrow_variable_list;
13101 CONSP (vlist);
13102 vlist = XCDR (vlist))
13103 {
13104 Lisp_Object var = XCAR (vlist);
13105 Lisp_Object val, pstr;
13106
13107 if (!SYMBOLP (var))
13108 continue;
13109 val = find_symbol_value (var);
13110 if (!MARKERP (val))
13111 continue;
13112 if (! EQ (COERCE_MARKER (val),
13113 Fget (var, Qlast_arrow_position))
13114 || ! (pstr = overlay_arrow_string_or_property (var),
13115 EQ (pstr, Fget (var, Qlast_arrow_string))))
13116 return 1;
13117 }
13118 return 0;
13119 }
13120
13121 /* Mark overlay arrows to be updated on next redisplay. */
13122
13123 static void
13124 update_overlay_arrows (int up_to_date)
13125 {
13126 Lisp_Object vlist;
13127
13128 for (vlist = Voverlay_arrow_variable_list;
13129 CONSP (vlist);
13130 vlist = XCDR (vlist))
13131 {
13132 Lisp_Object var = XCAR (vlist);
13133
13134 if (!SYMBOLP (var))
13135 continue;
13136
13137 if (up_to_date > 0)
13138 {
13139 Lisp_Object val = find_symbol_value (var);
13140 Fput (var, Qlast_arrow_position,
13141 COERCE_MARKER (val));
13142 Fput (var, Qlast_arrow_string,
13143 overlay_arrow_string_or_property (var));
13144 }
13145 else if (up_to_date < 0
13146 || !NILP (Fget (var, Qlast_arrow_position)))
13147 {
13148 Fput (var, Qlast_arrow_position, Qt);
13149 Fput (var, Qlast_arrow_string, Qt);
13150 }
13151 }
13152 }
13153
13154
13155 /* Return overlay arrow string to display at row.
13156 Return integer (bitmap number) for arrow bitmap in left fringe.
13157 Return nil if no overlay arrow. */
13158
13159 static Lisp_Object
13160 overlay_arrow_at_row (struct it *it, struct glyph_row *row)
13161 {
13162 Lisp_Object vlist;
13163
13164 for (vlist = Voverlay_arrow_variable_list;
13165 CONSP (vlist);
13166 vlist = XCDR (vlist))
13167 {
13168 Lisp_Object var = XCAR (vlist);
13169 Lisp_Object val;
13170
13171 if (!SYMBOLP (var))
13172 continue;
13173
13174 val = find_symbol_value (var);
13175
13176 if (MARKERP (val)
13177 && current_buffer == XMARKER (val)->buffer
13178 && (MATRIX_ROW_START_CHARPOS (row) == marker_position (val)))
13179 {
13180 if (FRAME_WINDOW_P (it->f)
13181 /* FIXME: if ROW->reversed_p is set, this should test
13182 the right fringe, not the left one. */
13183 && WINDOW_LEFT_FRINGE_WIDTH (it->w) > 0)
13184 {
13185 #ifdef HAVE_WINDOW_SYSTEM
13186 if (val = Fget (var, Qoverlay_arrow_bitmap), SYMBOLP (val))
13187 {
13188 int fringe_bitmap;
13189 if ((fringe_bitmap = lookup_fringe_bitmap (val)) != 0)
13190 return make_number (fringe_bitmap);
13191 }
13192 #endif
13193 return make_number (-1); /* Use default arrow bitmap. */
13194 }
13195 return overlay_arrow_string_or_property (var);
13196 }
13197 }
13198
13199 return Qnil;
13200 }
13201
13202 /* Return 1 if point moved out of or into a composition. Otherwise
13203 return 0. PREV_BUF and PREV_PT are the last point buffer and
13204 position. BUF and PT are the current point buffer and position. */
13205
13206 static int
13207 check_point_in_composition (struct buffer *prev_buf, ptrdiff_t prev_pt,
13208 struct buffer *buf, ptrdiff_t pt)
13209 {
13210 ptrdiff_t start, end;
13211 Lisp_Object prop;
13212 Lisp_Object buffer;
13213
13214 XSETBUFFER (buffer, buf);
13215 /* Check a composition at the last point if point moved within the
13216 same buffer. */
13217 if (prev_buf == buf)
13218 {
13219 if (prev_pt == pt)
13220 /* Point didn't move. */
13221 return 0;
13222
13223 if (prev_pt > BUF_BEGV (buf) && prev_pt < BUF_ZV (buf)
13224 && find_composition (prev_pt, -1, &start, &end, &prop, buffer)
13225 && composition_valid_p (start, end, prop)
13226 && start < prev_pt && end > prev_pt)
13227 /* The last point was within the composition. Return 1 iff
13228 point moved out of the composition. */
13229 return (pt <= start || pt >= end);
13230 }
13231
13232 /* Check a composition at the current point. */
13233 return (pt > BUF_BEGV (buf) && pt < BUF_ZV (buf)
13234 && find_composition (pt, -1, &start, &end, &prop, buffer)
13235 && composition_valid_p (start, end, prop)
13236 && start < pt && end > pt);
13237 }
13238
13239 /* Reconsider the clip changes of buffer which is displayed in W. */
13240
13241 static void
13242 reconsider_clip_changes (struct window *w)
13243 {
13244 struct buffer *b = XBUFFER (w->contents);
13245
13246 if (b->clip_changed
13247 && w->window_end_valid
13248 && w->current_matrix->buffer == b
13249 && w->current_matrix->zv == BUF_ZV (b)
13250 && w->current_matrix->begv == BUF_BEGV (b))
13251 b->clip_changed = 0;
13252
13253 /* If display wasn't paused, and W is not a tool bar window, see if
13254 point has been moved into or out of a composition. In that case,
13255 we set b->clip_changed to 1 to force updating the screen. If
13256 b->clip_changed has already been set to 1, we can skip this
13257 check. */
13258 if (!b->clip_changed && w->window_end_valid)
13259 {
13260 ptrdiff_t pt = (w == XWINDOW (selected_window)
13261 ? PT : marker_position (w->pointm));
13262
13263 if ((w->current_matrix->buffer != b || pt != w->last_point)
13264 && check_point_in_composition (w->current_matrix->buffer,
13265 w->last_point, b, pt))
13266 b->clip_changed = 1;
13267 }
13268 }
13269
13270 static void
13271 propagate_buffer_redisplay (void)
13272 { /* Resetting b->text->redisplay is problematic!
13273 We can't just reset it in the case that some window that displays
13274 it has not been redisplayed; and such a window can stay
13275 unredisplayed for a long time if it's currently invisible.
13276 But we do want to reset it at the end of redisplay otherwise
13277 its displayed windows will keep being redisplayed over and over
13278 again.
13279 So we copy all b->text->redisplay flags up to their windows here,
13280 such that mark_window_display_accurate can safely reset
13281 b->text->redisplay. */
13282 Lisp_Object ws = window_list ();
13283 for (; CONSP (ws); ws = XCDR (ws))
13284 {
13285 struct window *thisw = XWINDOW (XCAR (ws));
13286 struct buffer *thisb = XBUFFER (thisw->contents);
13287 if (thisb->text->redisplay)
13288 thisw->redisplay = true;
13289 }
13290 }
13291
13292 #define STOP_POLLING \
13293 do { if (! polling_stopped_here) stop_polling (); \
13294 polling_stopped_here = 1; } while (0)
13295
13296 #define RESUME_POLLING \
13297 do { if (polling_stopped_here) start_polling (); \
13298 polling_stopped_here = 0; } while (0)
13299
13300
13301 /* Perhaps in the future avoid recentering windows if it
13302 is not necessary; currently that causes some problems. */
13303
13304 static void
13305 redisplay_internal (void)
13306 {
13307 struct window *w = XWINDOW (selected_window);
13308 struct window *sw;
13309 struct frame *fr;
13310 bool pending;
13311 bool must_finish = 0, match_p;
13312 struct text_pos tlbufpos, tlendpos;
13313 int number_of_visible_frames;
13314 ptrdiff_t count;
13315 struct frame *sf;
13316 int polling_stopped_here = 0;
13317 Lisp_Object tail, frame;
13318
13319 /* True means redisplay has to consider all windows on all
13320 frames. False, only selected_window is considered. */
13321 bool consider_all_windows_p;
13322
13323 /* True means redisplay has to redisplay the miniwindow. */
13324 bool update_miniwindow_p = false;
13325
13326 TRACE ((stderr, "redisplay_internal %d\n", redisplaying_p));
13327
13328 /* No redisplay if running in batch mode or frame is not yet fully
13329 initialized, or redisplay is explicitly turned off by setting
13330 Vinhibit_redisplay. */
13331 if (FRAME_INITIAL_P (SELECTED_FRAME ())
13332 || !NILP (Vinhibit_redisplay))
13333 return;
13334
13335 /* Don't examine these until after testing Vinhibit_redisplay.
13336 When Emacs is shutting down, perhaps because its connection to
13337 X has dropped, we should not look at them at all. */
13338 fr = XFRAME (w->frame);
13339 sf = SELECTED_FRAME ();
13340
13341 if (!fr->glyphs_initialized_p)
13342 return;
13343
13344 #if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS)
13345 if (popup_activated ())
13346 return;
13347 #endif
13348
13349 /* I don't think this happens but let's be paranoid. */
13350 if (redisplaying_p)
13351 return;
13352
13353 /* Record a function that clears redisplaying_p
13354 when we leave this function. */
13355 count = SPECPDL_INDEX ();
13356 record_unwind_protect_void (unwind_redisplay);
13357 redisplaying_p = 1;
13358 specbind (Qinhibit_free_realized_faces, Qnil);
13359
13360 /* Record this function, so it appears on the profiler's backtraces. */
13361 record_in_backtrace (Qredisplay_internal, 0, 0);
13362
13363 FOR_EACH_FRAME (tail, frame)
13364 XFRAME (frame)->already_hscrolled_p = 0;
13365
13366 retry:
13367 /* Remember the currently selected window. */
13368 sw = w;
13369
13370 pending = false;
13371 last_escape_glyph_frame = NULL;
13372 last_escape_glyph_face_id = (1 << FACE_ID_BITS);
13373 last_glyphless_glyph_frame = NULL;
13374 last_glyphless_glyph_face_id = (1 << FACE_ID_BITS);
13375
13376 /* If face_change_count is non-zero, init_iterator will free all
13377 realized faces, which includes the faces referenced from current
13378 matrices. So, we can't reuse current matrices in this case. */
13379 if (face_change_count)
13380 windows_or_buffers_changed = 47;
13381
13382 if ((FRAME_TERMCAP_P (sf) || FRAME_MSDOS_P (sf))
13383 && FRAME_TTY (sf)->previous_frame != sf)
13384 {
13385 /* Since frames on a single ASCII terminal share the same
13386 display area, displaying a different frame means redisplay
13387 the whole thing. */
13388 SET_FRAME_GARBAGED (sf);
13389 #ifndef DOS_NT
13390 set_tty_color_mode (FRAME_TTY (sf), sf);
13391 #endif
13392 FRAME_TTY (sf)->previous_frame = sf;
13393 }
13394
13395 /* Set the visible flags for all frames. Do this before checking for
13396 resized or garbaged frames; they want to know if their frames are
13397 visible. See the comment in frame.h for FRAME_SAMPLE_VISIBILITY. */
13398 number_of_visible_frames = 0;
13399
13400 FOR_EACH_FRAME (tail, frame)
13401 {
13402 struct frame *f = XFRAME (frame);
13403
13404 if (FRAME_VISIBLE_P (f))
13405 {
13406 ++number_of_visible_frames;
13407 /* Adjust matrices for visible frames only. */
13408 if (f->fonts_changed)
13409 {
13410 adjust_frame_glyphs (f);
13411 f->fonts_changed = 0;
13412 }
13413 /* If cursor type has been changed on the frame
13414 other than selected, consider all frames. */
13415 if (f != sf && f->cursor_type_changed)
13416 update_mode_lines = 31;
13417 }
13418 clear_desired_matrices (f);
13419 }
13420
13421 /* Notice any pending interrupt request to change frame size. */
13422 do_pending_window_change (true);
13423
13424 /* do_pending_window_change could change the selected_window due to
13425 frame resizing which makes the selected window too small. */
13426 if (WINDOWP (selected_window) && (w = XWINDOW (selected_window)) != sw)
13427 sw = w;
13428
13429 /* Clear frames marked as garbaged. */
13430 clear_garbaged_frames ();
13431
13432 /* Build menubar and tool-bar items. */
13433 if (NILP (Vmemory_full))
13434 prepare_menu_bars ();
13435
13436 reconsider_clip_changes (w);
13437
13438 /* In most cases selected window displays current buffer. */
13439 match_p = XBUFFER (w->contents) == current_buffer;
13440 if (match_p)
13441 {
13442 /* Detect case that we need to write or remove a star in the mode line. */
13443 if ((SAVE_MODIFF < MODIFF) != w->last_had_star)
13444 w->update_mode_line = 1;
13445
13446 if (mode_line_update_needed (w))
13447 w->update_mode_line = 1;
13448
13449 /* If reconsider_clip_changes above decided that the narrowing
13450 in the current buffer changed, make sure all other windows
13451 showing that buffer will be redisplayed. */
13452 if (current_buffer->clip_changed)
13453 bset_update_mode_line (current_buffer);
13454 }
13455
13456 /* Normally the message* functions will have already displayed and
13457 updated the echo area, but the frame may have been trashed, or
13458 the update may have been preempted, so display the echo area
13459 again here. Checking message_cleared_p captures the case that
13460 the echo area should be cleared. */
13461 if ((!NILP (echo_area_buffer[0]) && !display_last_displayed_message_p)
13462 || (!NILP (echo_area_buffer[1]) && display_last_displayed_message_p)
13463 || (message_cleared_p
13464 && minibuf_level == 0
13465 /* If the mini-window is currently selected, this means the
13466 echo-area doesn't show through. */
13467 && !MINI_WINDOW_P (XWINDOW (selected_window))))
13468 {
13469 int window_height_changed_p = echo_area_display (false);
13470
13471 if (message_cleared_p)
13472 update_miniwindow_p = true;
13473
13474 must_finish = 1;
13475
13476 /* If we don't display the current message, don't clear the
13477 message_cleared_p flag, because, if we did, we wouldn't clear
13478 the echo area in the next redisplay which doesn't preserve
13479 the echo area. */
13480 if (!display_last_displayed_message_p)
13481 message_cleared_p = 0;
13482
13483 if (window_height_changed_p)
13484 {
13485 windows_or_buffers_changed = 50;
13486
13487 /* If window configuration was changed, frames may have been
13488 marked garbaged. Clear them or we will experience
13489 surprises wrt scrolling. */
13490 clear_garbaged_frames ();
13491 }
13492 }
13493 else if (EQ (selected_window, minibuf_window)
13494 && (current_buffer->clip_changed || window_outdated (w))
13495 && resize_mini_window (w, 0))
13496 {
13497 /* Resized active mini-window to fit the size of what it is
13498 showing if its contents might have changed. */
13499 must_finish = 1;
13500
13501 /* If window configuration was changed, frames may have been
13502 marked garbaged. Clear them or we will experience
13503 surprises wrt scrolling. */
13504 clear_garbaged_frames ();
13505 }
13506
13507 if (windows_or_buffers_changed && !update_mode_lines)
13508 /* Code that sets windows_or_buffers_changed doesn't distinguish whether
13509 only the windows's contents needs to be refreshed, or whether the
13510 mode-lines also need a refresh. */
13511 update_mode_lines = (windows_or_buffers_changed == REDISPLAY_SOME
13512 ? REDISPLAY_SOME : 32);
13513
13514 /* If specs for an arrow have changed, do thorough redisplay
13515 to ensure we remove any arrow that should no longer exist. */
13516 if (overlay_arrows_changed_p ())
13517 /* Apparently, this is the only case where we update other windows,
13518 without updating other mode-lines. */
13519 windows_or_buffers_changed = 49;
13520
13521 consider_all_windows_p = (update_mode_lines
13522 || windows_or_buffers_changed);
13523
13524 #define AINC(a,i) \
13525 if (VECTORP (a) && i >= 0 && i < ASIZE (a) && INTEGERP (AREF (a, i))) \
13526 ASET (a, i, make_number (1 + XINT (AREF (a, i))))
13527
13528 AINC (Vredisplay__all_windows_cause, windows_or_buffers_changed);
13529 AINC (Vredisplay__mode_lines_cause, update_mode_lines);
13530
13531 /* Optimize the case that only the line containing the cursor in the
13532 selected window has changed. Variables starting with this_ are
13533 set in display_line and record information about the line
13534 containing the cursor. */
13535 tlbufpos = this_line_start_pos;
13536 tlendpos = this_line_end_pos;
13537 if (!consider_all_windows_p
13538 && CHARPOS (tlbufpos) > 0
13539 && !w->update_mode_line
13540 && !current_buffer->clip_changed
13541 && !current_buffer->prevent_redisplay_optimizations_p
13542 && FRAME_VISIBLE_P (XFRAME (w->frame))
13543 && !FRAME_OBSCURED_P (XFRAME (w->frame))
13544 && !XFRAME (w->frame)->cursor_type_changed
13545 /* Make sure recorded data applies to current buffer, etc. */
13546 && this_line_buffer == current_buffer
13547 && match_p
13548 && !w->force_start
13549 && !w->optional_new_start
13550 /* Point must be on the line that we have info recorded about. */
13551 && PT >= CHARPOS (tlbufpos)
13552 && PT <= Z - CHARPOS (tlendpos)
13553 /* All text outside that line, including its final newline,
13554 must be unchanged. */
13555 && text_outside_line_unchanged_p (w, CHARPOS (tlbufpos),
13556 CHARPOS (tlendpos)))
13557 {
13558 if (CHARPOS (tlbufpos) > BEGV
13559 && FETCH_BYTE (BYTEPOS (tlbufpos) - 1) != '\n'
13560 && (CHARPOS (tlbufpos) == ZV
13561 || FETCH_BYTE (BYTEPOS (tlbufpos)) == '\n'))
13562 /* Former continuation line has disappeared by becoming empty. */
13563 goto cancel;
13564 else if (window_outdated (w) || MINI_WINDOW_P (w))
13565 {
13566 /* We have to handle the case of continuation around a
13567 wide-column character (see the comment in indent.c around
13568 line 1340).
13569
13570 For instance, in the following case:
13571
13572 -------- Insert --------
13573 K_A_N_\\ `a' K_A_N_a\ `X_' are wide-column chars.
13574 J_I_ ==> J_I_ `^^' are cursors.
13575 ^^ ^^
13576 -------- --------
13577
13578 As we have to redraw the line above, we cannot use this
13579 optimization. */
13580
13581 struct it it;
13582 int line_height_before = this_line_pixel_height;
13583
13584 /* Note that start_display will handle the case that the
13585 line starting at tlbufpos is a continuation line. */
13586 start_display (&it, w, tlbufpos);
13587
13588 /* Implementation note: It this still necessary? */
13589 if (it.current_x != this_line_start_x)
13590 goto cancel;
13591
13592 TRACE ((stderr, "trying display optimization 1\n"));
13593 w->cursor.vpos = -1;
13594 overlay_arrow_seen = 0;
13595 it.vpos = this_line_vpos;
13596 it.current_y = this_line_y;
13597 it.glyph_row = MATRIX_ROW (w->desired_matrix, this_line_vpos);
13598 display_line (&it);
13599
13600 /* If line contains point, is not continued,
13601 and ends at same distance from eob as before, we win. */
13602 if (w->cursor.vpos >= 0
13603 /* Line is not continued, otherwise this_line_start_pos
13604 would have been set to 0 in display_line. */
13605 && CHARPOS (this_line_start_pos)
13606 /* Line ends as before. */
13607 && CHARPOS (this_line_end_pos) == CHARPOS (tlendpos)
13608 /* Line has same height as before. Otherwise other lines
13609 would have to be shifted up or down. */
13610 && this_line_pixel_height == line_height_before)
13611 {
13612 /* If this is not the window's last line, we must adjust
13613 the charstarts of the lines below. */
13614 if (it.current_y < it.last_visible_y)
13615 {
13616 struct glyph_row *row
13617 = MATRIX_ROW (w->current_matrix, this_line_vpos + 1);
13618 ptrdiff_t delta, delta_bytes;
13619
13620 /* We used to distinguish between two cases here,
13621 conditioned by Z - CHARPOS (tlendpos) == ZV, for
13622 when the line ends in a newline or the end of the
13623 buffer's accessible portion. But both cases did
13624 the same, so they were collapsed. */
13625 delta = (Z
13626 - CHARPOS (tlendpos)
13627 - MATRIX_ROW_START_CHARPOS (row));
13628 delta_bytes = (Z_BYTE
13629 - BYTEPOS (tlendpos)
13630 - MATRIX_ROW_START_BYTEPOS (row));
13631
13632 increment_matrix_positions (w->current_matrix,
13633 this_line_vpos + 1,
13634 w->current_matrix->nrows,
13635 delta, delta_bytes);
13636 }
13637
13638 /* If this row displays text now but previously didn't,
13639 or vice versa, w->window_end_vpos may have to be
13640 adjusted. */
13641 if (MATRIX_ROW_DISPLAYS_TEXT_P (it.glyph_row - 1))
13642 {
13643 if (w->window_end_vpos < this_line_vpos)
13644 w->window_end_vpos = this_line_vpos;
13645 }
13646 else if (w->window_end_vpos == this_line_vpos
13647 && this_line_vpos > 0)
13648 w->window_end_vpos = this_line_vpos - 1;
13649 w->window_end_valid = 0;
13650
13651 /* Update hint: No need to try to scroll in update_window. */
13652 w->desired_matrix->no_scrolling_p = 1;
13653
13654 #ifdef GLYPH_DEBUG
13655 *w->desired_matrix->method = 0;
13656 debug_method_add (w, "optimization 1");
13657 #endif
13658 #ifdef HAVE_WINDOW_SYSTEM
13659 update_window_fringes (w, 0);
13660 #endif
13661 goto update;
13662 }
13663 else
13664 goto cancel;
13665 }
13666 else if (/* Cursor position hasn't changed. */
13667 PT == w->last_point
13668 /* Make sure the cursor was last displayed
13669 in this window. Otherwise we have to reposition it. */
13670
13671 /* PXW: Must be converted to pixels, probably. */
13672 && 0 <= w->cursor.vpos
13673 && w->cursor.vpos < WINDOW_TOTAL_LINES (w))
13674 {
13675 if (!must_finish)
13676 {
13677 do_pending_window_change (true);
13678 /* If selected_window changed, redisplay again. */
13679 if (WINDOWP (selected_window)
13680 && (w = XWINDOW (selected_window)) != sw)
13681 goto retry;
13682
13683 /* We used to always goto end_of_redisplay here, but this
13684 isn't enough if we have a blinking cursor. */
13685 if (w->cursor_off_p == w->last_cursor_off_p)
13686 goto end_of_redisplay;
13687 }
13688 goto update;
13689 }
13690 /* If highlighting the region, or if the cursor is in the echo area,
13691 then we can't just move the cursor. */
13692 else if (NILP (Vshow_trailing_whitespace)
13693 && !cursor_in_echo_area)
13694 {
13695 struct it it;
13696 struct glyph_row *row;
13697
13698 /* Skip from tlbufpos to PT and see where it is. Note that
13699 PT may be in invisible text. If so, we will end at the
13700 next visible position. */
13701 init_iterator (&it, w, CHARPOS (tlbufpos), BYTEPOS (tlbufpos),
13702 NULL, DEFAULT_FACE_ID);
13703 it.current_x = this_line_start_x;
13704 it.current_y = this_line_y;
13705 it.vpos = this_line_vpos;
13706
13707 /* The call to move_it_to stops in front of PT, but
13708 moves over before-strings. */
13709 move_it_to (&it, PT, -1, -1, -1, MOVE_TO_POS);
13710
13711 if (it.vpos == this_line_vpos
13712 && (row = MATRIX_ROW (w->current_matrix, this_line_vpos),
13713 row->enabled_p))
13714 {
13715 eassert (this_line_vpos == it.vpos);
13716 eassert (this_line_y == it.current_y);
13717 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
13718 #ifdef GLYPH_DEBUG
13719 *w->desired_matrix->method = 0;
13720 debug_method_add (w, "optimization 3");
13721 #endif
13722 goto update;
13723 }
13724 else
13725 goto cancel;
13726 }
13727
13728 cancel:
13729 /* Text changed drastically or point moved off of line. */
13730 SET_MATRIX_ROW_ENABLED_P (w->desired_matrix, this_line_vpos, false);
13731 }
13732
13733 CHARPOS (this_line_start_pos) = 0;
13734 ++clear_face_cache_count;
13735 #ifdef HAVE_WINDOW_SYSTEM
13736 ++clear_image_cache_count;
13737 #endif
13738
13739 /* Build desired matrices, and update the display. If
13740 consider_all_windows_p is non-zero, do it for all windows on all
13741 frames. Otherwise do it for selected_window, only. */
13742
13743 if (consider_all_windows_p)
13744 {
13745 FOR_EACH_FRAME (tail, frame)
13746 XFRAME (frame)->updated_p = 0;
13747
13748 propagate_buffer_redisplay ();
13749
13750 FOR_EACH_FRAME (tail, frame)
13751 {
13752 struct frame *f = XFRAME (frame);
13753
13754 /* We don't have to do anything for unselected terminal
13755 frames. */
13756 if ((FRAME_TERMCAP_P (f) || FRAME_MSDOS_P (f))
13757 && !EQ (FRAME_TTY (f)->top_frame, frame))
13758 continue;
13759
13760 retry_frame:
13761
13762 #if defined (HAVE_WINDOW_SYSTEM) && !defined (USE_GTK) && !defined (HAVE_NS)
13763 /* Redisplay internal tool bar if this is the first time so we
13764 can adjust the frame height right now, if necessary. */
13765 if (!f->tool_bar_redisplayed_once)
13766 {
13767 if (redisplay_tool_bar (f))
13768 adjust_frame_glyphs (f);
13769 f->tool_bar_redisplayed_once = true;
13770 }
13771 #endif
13772
13773 if (FRAME_WINDOW_P (f) || FRAME_TERMCAP_P (f) || f == sf)
13774 {
13775 bool gcscrollbars
13776 /* Only GC scrollbars when we redisplay the whole frame. */
13777 = f->redisplay || !REDISPLAY_SOME_P ();
13778 /* Mark all the scroll bars to be removed; we'll redeem
13779 the ones we want when we redisplay their windows. */
13780 if (gcscrollbars && FRAME_TERMINAL (f)->condemn_scroll_bars_hook)
13781 FRAME_TERMINAL (f)->condemn_scroll_bars_hook (f);
13782
13783 if (FRAME_VISIBLE_P (f) && !FRAME_OBSCURED_P (f))
13784 redisplay_windows (FRAME_ROOT_WINDOW (f));
13785 /* Remember that the invisible frames need to be redisplayed next
13786 time they're visible. */
13787 else if (!REDISPLAY_SOME_P ())
13788 f->redisplay = true;
13789
13790 /* The X error handler may have deleted that frame. */
13791 if (!FRAME_LIVE_P (f))
13792 continue;
13793
13794 /* Any scroll bars which redisplay_windows should have
13795 nuked should now go away. */
13796 if (gcscrollbars && FRAME_TERMINAL (f)->judge_scroll_bars_hook)
13797 FRAME_TERMINAL (f)->judge_scroll_bars_hook (f);
13798
13799 if (FRAME_VISIBLE_P (f) && !FRAME_OBSCURED_P (f))
13800 {
13801 /* If fonts changed on visible frame, display again. */
13802 if (f->fonts_changed)
13803 {
13804 adjust_frame_glyphs (f);
13805 f->fonts_changed = false;
13806 goto retry_frame;
13807 }
13808
13809 /* See if we have to hscroll. */
13810 if (!f->already_hscrolled_p)
13811 {
13812 f->already_hscrolled_p = true;
13813 if (hscroll_windows (f->root_window))
13814 goto retry_frame;
13815 }
13816
13817 /* Prevent various kinds of signals during display
13818 update. stdio is not robust about handling
13819 signals, which can cause an apparent I/O error. */
13820 if (interrupt_input)
13821 unrequest_sigio ();
13822 STOP_POLLING;
13823
13824 pending |= update_frame (f, false, false);
13825 f->cursor_type_changed = false;
13826 f->updated_p = true;
13827 }
13828 }
13829 }
13830
13831 eassert (EQ (XFRAME (selected_frame)->selected_window, selected_window));
13832
13833 if (!pending)
13834 {
13835 /* Do the mark_window_display_accurate after all windows have
13836 been redisplayed because this call resets flags in buffers
13837 which are needed for proper redisplay. */
13838 FOR_EACH_FRAME (tail, frame)
13839 {
13840 struct frame *f = XFRAME (frame);
13841 if (f->updated_p)
13842 {
13843 f->redisplay = false;
13844 mark_window_display_accurate (f->root_window, 1);
13845 if (FRAME_TERMINAL (f)->frame_up_to_date_hook)
13846 FRAME_TERMINAL (f)->frame_up_to_date_hook (f);
13847 }
13848 }
13849 }
13850 }
13851 else if (FRAME_VISIBLE_P (sf) && !FRAME_OBSCURED_P (sf))
13852 {
13853 Lisp_Object mini_window = FRAME_MINIBUF_WINDOW (sf);
13854 struct frame *mini_frame;
13855
13856 displayed_buffer = XBUFFER (XWINDOW (selected_window)->contents);
13857 /* Use list_of_error, not Qerror, so that
13858 we catch only errors and don't run the debugger. */
13859 internal_condition_case_1 (redisplay_window_1, selected_window,
13860 list_of_error,
13861 redisplay_window_error);
13862 if (update_miniwindow_p)
13863 internal_condition_case_1 (redisplay_window_1, mini_window,
13864 list_of_error,
13865 redisplay_window_error);
13866
13867 /* Compare desired and current matrices, perform output. */
13868
13869 update:
13870 /* If fonts changed, display again. */
13871 if (sf->fonts_changed)
13872 goto retry;
13873
13874 /* Prevent various kinds of signals during display update.
13875 stdio is not robust about handling signals,
13876 which can cause an apparent I/O error. */
13877 if (interrupt_input)
13878 unrequest_sigio ();
13879 STOP_POLLING;
13880
13881 if (FRAME_VISIBLE_P (sf) && !FRAME_OBSCURED_P (sf))
13882 {
13883 if (hscroll_windows (selected_window))
13884 goto retry;
13885
13886 XWINDOW (selected_window)->must_be_updated_p = true;
13887 pending = update_frame (sf, false, false);
13888 sf->cursor_type_changed = false;
13889 }
13890
13891 /* We may have called echo_area_display at the top of this
13892 function. If the echo area is on another frame, that may
13893 have put text on a frame other than the selected one, so the
13894 above call to update_frame would not have caught it. Catch
13895 it here. */
13896 mini_window = FRAME_MINIBUF_WINDOW (sf);
13897 mini_frame = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
13898
13899 if (mini_frame != sf && FRAME_WINDOW_P (mini_frame))
13900 {
13901 XWINDOW (mini_window)->must_be_updated_p = true;
13902 pending |= update_frame (mini_frame, false, false);
13903 mini_frame->cursor_type_changed = false;
13904 if (!pending && hscroll_windows (mini_window))
13905 goto retry;
13906 }
13907 }
13908
13909 /* If display was paused because of pending input, make sure we do a
13910 thorough update the next time. */
13911 if (pending)
13912 {
13913 /* Prevent the optimization at the beginning of
13914 redisplay_internal that tries a single-line update of the
13915 line containing the cursor in the selected window. */
13916 CHARPOS (this_line_start_pos) = 0;
13917
13918 /* Let the overlay arrow be updated the next time. */
13919 update_overlay_arrows (0);
13920
13921 /* If we pause after scrolling, some rows in the current
13922 matrices of some windows are not valid. */
13923 if (!WINDOW_FULL_WIDTH_P (w)
13924 && !FRAME_WINDOW_P (XFRAME (w->frame)))
13925 update_mode_lines = 36;
13926 }
13927 else
13928 {
13929 if (!consider_all_windows_p)
13930 {
13931 /* This has already been done above if
13932 consider_all_windows_p is set. */
13933 if (XBUFFER (w->contents)->text->redisplay
13934 && buffer_window_count (XBUFFER (w->contents)) > 1)
13935 /* This can happen if b->text->redisplay was set during
13936 jit-lock. */
13937 propagate_buffer_redisplay ();
13938 mark_window_display_accurate_1 (w, 1);
13939
13940 /* Say overlay arrows are up to date. */
13941 update_overlay_arrows (1);
13942
13943 if (FRAME_TERMINAL (sf)->frame_up_to_date_hook != 0)
13944 FRAME_TERMINAL (sf)->frame_up_to_date_hook (sf);
13945 }
13946
13947 update_mode_lines = 0;
13948 windows_or_buffers_changed = 0;
13949 }
13950
13951 /* Start SIGIO interrupts coming again. Having them off during the
13952 code above makes it less likely one will discard output, but not
13953 impossible, since there might be stuff in the system buffer here.
13954 But it is much hairier to try to do anything about that. */
13955 if (interrupt_input)
13956 request_sigio ();
13957 RESUME_POLLING;
13958
13959 /* If a frame has become visible which was not before, redisplay
13960 again, so that we display it. Expose events for such a frame
13961 (which it gets when becoming visible) don't call the parts of
13962 redisplay constructing glyphs, so simply exposing a frame won't
13963 display anything in this case. So, we have to display these
13964 frames here explicitly. */
13965 if (!pending)
13966 {
13967 int new_count = 0;
13968
13969 FOR_EACH_FRAME (tail, frame)
13970 {
13971 if (XFRAME (frame)->visible)
13972 new_count++;
13973 }
13974
13975 if (new_count != number_of_visible_frames)
13976 windows_or_buffers_changed = 52;
13977 }
13978
13979 /* Change frame size now if a change is pending. */
13980 do_pending_window_change (true);
13981
13982 /* If we just did a pending size change, or have additional
13983 visible frames, or selected_window changed, redisplay again. */
13984 if ((windows_or_buffers_changed && !pending)
13985 || (WINDOWP (selected_window) && (w = XWINDOW (selected_window)) != sw))
13986 goto retry;
13987
13988 /* Clear the face and image caches.
13989
13990 We used to do this only if consider_all_windows_p. But the cache
13991 needs to be cleared if a timer creates images in the current
13992 buffer (e.g. the test case in Bug#6230). */
13993
13994 if (clear_face_cache_count > CLEAR_FACE_CACHE_COUNT)
13995 {
13996 clear_face_cache (false);
13997 clear_face_cache_count = 0;
13998 }
13999
14000 #ifdef HAVE_WINDOW_SYSTEM
14001 if (clear_image_cache_count > CLEAR_IMAGE_CACHE_COUNT)
14002 {
14003 clear_image_caches (Qnil);
14004 clear_image_cache_count = 0;
14005 }
14006 #endif /* HAVE_WINDOW_SYSTEM */
14007
14008 end_of_redisplay:
14009 #ifdef HAVE_NS
14010 ns_set_doc_edited ();
14011 #endif
14012 if (interrupt_input && interrupts_deferred)
14013 request_sigio ();
14014
14015 unbind_to (count, Qnil);
14016 RESUME_POLLING;
14017 }
14018
14019
14020 /* Redisplay, but leave alone any recent echo area message unless
14021 another message has been requested in its place.
14022
14023 This is useful in situations where you need to redisplay but no
14024 user action has occurred, making it inappropriate for the message
14025 area to be cleared. See tracking_off and
14026 wait_reading_process_output for examples of these situations.
14027
14028 FROM_WHERE is an integer saying from where this function was
14029 called. This is useful for debugging. */
14030
14031 void
14032 redisplay_preserve_echo_area (int from_where)
14033 {
14034 TRACE ((stderr, "redisplay_preserve_echo_area (%d)\n", from_where));
14035
14036 if (!NILP (echo_area_buffer[1]))
14037 {
14038 /* We have a previously displayed message, but no current
14039 message. Redisplay the previous message. */
14040 display_last_displayed_message_p = true;
14041 redisplay_internal ();
14042 display_last_displayed_message_p = false;
14043 }
14044 else
14045 redisplay_internal ();
14046
14047 flush_frame (SELECTED_FRAME ());
14048 }
14049
14050
14051 /* Function registered with record_unwind_protect in redisplay_internal. */
14052
14053 static void
14054 unwind_redisplay (void)
14055 {
14056 redisplaying_p = 0;
14057 }
14058
14059
14060 /* Mark the display of leaf window W as accurate or inaccurate.
14061 If ACCURATE_P is non-zero mark display of W as accurate. If
14062 ACCURATE_P is zero, arrange for W to be redisplayed the next
14063 time redisplay_internal is called. */
14064
14065 static void
14066 mark_window_display_accurate_1 (struct window *w, int accurate_p)
14067 {
14068 struct buffer *b = XBUFFER (w->contents);
14069
14070 w->last_modified = accurate_p ? BUF_MODIFF (b) : 0;
14071 w->last_overlay_modified = accurate_p ? BUF_OVERLAY_MODIFF (b) : 0;
14072 w->last_had_star = BUF_MODIFF (b) > BUF_SAVE_MODIFF (b);
14073
14074 if (accurate_p)
14075 {
14076 b->clip_changed = false;
14077 b->prevent_redisplay_optimizations_p = false;
14078 eassert (buffer_window_count (b) > 0);
14079 /* Resetting b->text->redisplay is problematic!
14080 In order to make it safer to do it here, redisplay_internal must
14081 have copied all b->text->redisplay to their respective windows. */
14082 b->text->redisplay = false;
14083
14084 BUF_UNCHANGED_MODIFIED (b) = BUF_MODIFF (b);
14085 BUF_OVERLAY_UNCHANGED_MODIFIED (b) = BUF_OVERLAY_MODIFF (b);
14086 BUF_BEG_UNCHANGED (b) = BUF_GPT (b) - BUF_BEG (b);
14087 BUF_END_UNCHANGED (b) = BUF_Z (b) - BUF_GPT (b);
14088
14089 w->current_matrix->buffer = b;
14090 w->current_matrix->begv = BUF_BEGV (b);
14091 w->current_matrix->zv = BUF_ZV (b);
14092
14093 w->last_cursor_vpos = w->cursor.vpos;
14094 w->last_cursor_off_p = w->cursor_off_p;
14095
14096 if (w == XWINDOW (selected_window))
14097 w->last_point = BUF_PT (b);
14098 else
14099 w->last_point = marker_position (w->pointm);
14100
14101 w->window_end_valid = true;
14102 w->update_mode_line = false;
14103 }
14104
14105 w->redisplay = !accurate_p;
14106 }
14107
14108
14109 /* Mark the display of windows in the window tree rooted at WINDOW as
14110 accurate or inaccurate. If ACCURATE_P is non-zero mark display of
14111 windows as accurate. If ACCURATE_P is zero, arrange for windows to
14112 be redisplayed the next time redisplay_internal is called. */
14113
14114 void
14115 mark_window_display_accurate (Lisp_Object window, int accurate_p)
14116 {
14117 struct window *w;
14118
14119 for (; !NILP (window); window = w->next)
14120 {
14121 w = XWINDOW (window);
14122 if (WINDOWP (w->contents))
14123 mark_window_display_accurate (w->contents, accurate_p);
14124 else
14125 mark_window_display_accurate_1 (w, accurate_p);
14126 }
14127
14128 if (accurate_p)
14129 update_overlay_arrows (1);
14130 else
14131 /* Force a thorough redisplay the next time by setting
14132 last_arrow_position and last_arrow_string to t, which is
14133 unequal to any useful value of Voverlay_arrow_... */
14134 update_overlay_arrows (-1);
14135 }
14136
14137
14138 /* Return value in display table DP (Lisp_Char_Table *) for character
14139 C. Since a display table doesn't have any parent, we don't have to
14140 follow parent. Do not call this function directly but use the
14141 macro DISP_CHAR_VECTOR. */
14142
14143 Lisp_Object
14144 disp_char_vector (struct Lisp_Char_Table *dp, int c)
14145 {
14146 Lisp_Object val;
14147
14148 if (ASCII_CHAR_P (c))
14149 {
14150 val = dp->ascii;
14151 if (SUB_CHAR_TABLE_P (val))
14152 val = XSUB_CHAR_TABLE (val)->contents[c];
14153 }
14154 else
14155 {
14156 Lisp_Object table;
14157
14158 XSETCHAR_TABLE (table, dp);
14159 val = char_table_ref (table, c);
14160 }
14161 if (NILP (val))
14162 val = dp->defalt;
14163 return val;
14164 }
14165
14166
14167 \f
14168 /***********************************************************************
14169 Window Redisplay
14170 ***********************************************************************/
14171
14172 /* Redisplay all leaf windows in the window tree rooted at WINDOW. */
14173
14174 static void
14175 redisplay_windows (Lisp_Object window)
14176 {
14177 while (!NILP (window))
14178 {
14179 struct window *w = XWINDOW (window);
14180
14181 if (WINDOWP (w->contents))
14182 redisplay_windows (w->contents);
14183 else if (BUFFERP (w->contents))
14184 {
14185 displayed_buffer = XBUFFER (w->contents);
14186 /* Use list_of_error, not Qerror, so that
14187 we catch only errors and don't run the debugger. */
14188 internal_condition_case_1 (redisplay_window_0, window,
14189 list_of_error,
14190 redisplay_window_error);
14191 }
14192
14193 window = w->next;
14194 }
14195 }
14196
14197 static Lisp_Object
14198 redisplay_window_error (Lisp_Object ignore)
14199 {
14200 displayed_buffer->display_error_modiff = BUF_MODIFF (displayed_buffer);
14201 return Qnil;
14202 }
14203
14204 static Lisp_Object
14205 redisplay_window_0 (Lisp_Object window)
14206 {
14207 if (displayed_buffer->display_error_modiff < BUF_MODIFF (displayed_buffer))
14208 redisplay_window (window, false);
14209 return Qnil;
14210 }
14211
14212 static Lisp_Object
14213 redisplay_window_1 (Lisp_Object window)
14214 {
14215 if (displayed_buffer->display_error_modiff < BUF_MODIFF (displayed_buffer))
14216 redisplay_window (window, true);
14217 return Qnil;
14218 }
14219 \f
14220
14221 /* Set cursor position of W. PT is assumed to be displayed in ROW.
14222 DELTA and DELTA_BYTES are the numbers of characters and bytes by
14223 which positions recorded in ROW differ from current buffer
14224 positions.
14225
14226 Return 0 if cursor is not on this row, 1 otherwise. */
14227
14228 static int
14229 set_cursor_from_row (struct window *w, struct glyph_row *row,
14230 struct glyph_matrix *matrix,
14231 ptrdiff_t delta, ptrdiff_t delta_bytes,
14232 int dy, int dvpos)
14233 {
14234 struct glyph *glyph = row->glyphs[TEXT_AREA];
14235 struct glyph *end = glyph + row->used[TEXT_AREA];
14236 struct glyph *cursor = NULL;
14237 /* The last known character position in row. */
14238 ptrdiff_t last_pos = MATRIX_ROW_START_CHARPOS (row) + delta;
14239 int x = row->x;
14240 ptrdiff_t pt_old = PT - delta;
14241 ptrdiff_t pos_before = MATRIX_ROW_START_CHARPOS (row) + delta;
14242 ptrdiff_t pos_after = MATRIX_ROW_END_CHARPOS (row) + delta;
14243 struct glyph *glyph_before = glyph - 1, *glyph_after = end;
14244 /* A glyph beyond the edge of TEXT_AREA which we should never
14245 touch. */
14246 struct glyph *glyphs_end = end;
14247 /* Non-zero means we've found a match for cursor position, but that
14248 glyph has the avoid_cursor_p flag set. */
14249 int match_with_avoid_cursor = 0;
14250 /* Non-zero means we've seen at least one glyph that came from a
14251 display string. */
14252 int string_seen = 0;
14253 /* Largest and smallest buffer positions seen so far during scan of
14254 glyph row. */
14255 ptrdiff_t bpos_max = pos_before;
14256 ptrdiff_t bpos_min = pos_after;
14257 /* Last buffer position covered by an overlay string with an integer
14258 `cursor' property. */
14259 ptrdiff_t bpos_covered = 0;
14260 /* Non-zero means the display string on which to display the cursor
14261 comes from a text property, not from an overlay. */
14262 int string_from_text_prop = 0;
14263
14264 /* Don't even try doing anything if called for a mode-line or
14265 header-line row, since the rest of the code isn't prepared to
14266 deal with such calamities. */
14267 eassert (!row->mode_line_p);
14268 if (row->mode_line_p)
14269 return 0;
14270
14271 /* Skip over glyphs not having an object at the start and the end of
14272 the row. These are special glyphs like truncation marks on
14273 terminal frames. */
14274 if (MATRIX_ROW_DISPLAYS_TEXT_P (row))
14275 {
14276 if (!row->reversed_p)
14277 {
14278 while (glyph < end
14279 && NILP (glyph->object)
14280 && glyph->charpos < 0)
14281 {
14282 x += glyph->pixel_width;
14283 ++glyph;
14284 }
14285 while (end > glyph
14286 && NILP ((end - 1)->object)
14287 /* CHARPOS is zero for blanks and stretch glyphs
14288 inserted by extend_face_to_end_of_line. */
14289 && (end - 1)->charpos <= 0)
14290 --end;
14291 glyph_before = glyph - 1;
14292 glyph_after = end;
14293 }
14294 else
14295 {
14296 struct glyph *g;
14297
14298 /* If the glyph row is reversed, we need to process it from back
14299 to front, so swap the edge pointers. */
14300 glyphs_end = end = glyph - 1;
14301 glyph += row->used[TEXT_AREA] - 1;
14302
14303 while (glyph > end + 1
14304 && NILP (glyph->object)
14305 && glyph->charpos < 0)
14306 {
14307 --glyph;
14308 x -= glyph->pixel_width;
14309 }
14310 if (NILP (glyph->object) && glyph->charpos < 0)
14311 --glyph;
14312 /* By default, in reversed rows we put the cursor on the
14313 rightmost (first in the reading order) glyph. */
14314 for (g = end + 1; g < glyph; g++)
14315 x += g->pixel_width;
14316 while (end < glyph
14317 && NILP ((end + 1)->object)
14318 && (end + 1)->charpos <= 0)
14319 ++end;
14320 glyph_before = glyph + 1;
14321 glyph_after = end;
14322 }
14323 }
14324 else if (row->reversed_p)
14325 {
14326 /* In R2L rows that don't display text, put the cursor on the
14327 rightmost glyph. Case in point: an empty last line that is
14328 part of an R2L paragraph. */
14329 cursor = end - 1;
14330 /* Avoid placing the cursor on the last glyph of the row, where
14331 on terminal frames we hold the vertical border between
14332 adjacent windows. */
14333 if (!FRAME_WINDOW_P (WINDOW_XFRAME (w))
14334 && !WINDOW_RIGHTMOST_P (w)
14335 && cursor == row->glyphs[LAST_AREA] - 1)
14336 cursor--;
14337 x = -1; /* will be computed below, at label compute_x */
14338 }
14339
14340 /* Step 1: Try to find the glyph whose character position
14341 corresponds to point. If that's not possible, find 2 glyphs
14342 whose character positions are the closest to point, one before
14343 point, the other after it. */
14344 if (!row->reversed_p)
14345 while (/* not marched to end of glyph row */
14346 glyph < end
14347 /* glyph was not inserted by redisplay for internal purposes */
14348 && !NILP (glyph->object))
14349 {
14350 if (BUFFERP (glyph->object))
14351 {
14352 ptrdiff_t dpos = glyph->charpos - pt_old;
14353
14354 if (glyph->charpos > bpos_max)
14355 bpos_max = glyph->charpos;
14356 if (glyph->charpos < bpos_min)
14357 bpos_min = glyph->charpos;
14358 if (!glyph->avoid_cursor_p)
14359 {
14360 /* If we hit point, we've found the glyph on which to
14361 display the cursor. */
14362 if (dpos == 0)
14363 {
14364 match_with_avoid_cursor = 0;
14365 break;
14366 }
14367 /* See if we've found a better approximation to
14368 POS_BEFORE or to POS_AFTER. */
14369 if (0 > dpos && dpos > pos_before - pt_old)
14370 {
14371 pos_before = glyph->charpos;
14372 glyph_before = glyph;
14373 }
14374 else if (0 < dpos && dpos < pos_after - pt_old)
14375 {
14376 pos_after = glyph->charpos;
14377 glyph_after = glyph;
14378 }
14379 }
14380 else if (dpos == 0)
14381 match_with_avoid_cursor = 1;
14382 }
14383 else if (STRINGP (glyph->object))
14384 {
14385 Lisp_Object chprop;
14386 ptrdiff_t glyph_pos = glyph->charpos;
14387
14388 chprop = Fget_char_property (make_number (glyph_pos), Qcursor,
14389 glyph->object);
14390 if (!NILP (chprop))
14391 {
14392 /* If the string came from a `display' text property,
14393 look up the buffer position of that property and
14394 use that position to update bpos_max, as if we
14395 actually saw such a position in one of the row's
14396 glyphs. This helps with supporting integer values
14397 of `cursor' property on the display string in
14398 situations where most or all of the row's buffer
14399 text is completely covered by display properties,
14400 so that no glyph with valid buffer positions is
14401 ever seen in the row. */
14402 ptrdiff_t prop_pos =
14403 string_buffer_position_lim (glyph->object, pos_before,
14404 pos_after, 0);
14405
14406 if (prop_pos >= pos_before)
14407 bpos_max = prop_pos;
14408 }
14409 if (INTEGERP (chprop))
14410 {
14411 bpos_covered = bpos_max + XINT (chprop);
14412 /* If the `cursor' property covers buffer positions up
14413 to and including point, we should display cursor on
14414 this glyph. Note that, if a `cursor' property on one
14415 of the string's characters has an integer value, we
14416 will break out of the loop below _before_ we get to
14417 the position match above. IOW, integer values of
14418 the `cursor' property override the "exact match for
14419 point" strategy of positioning the cursor. */
14420 /* Implementation note: bpos_max == pt_old when, e.g.,
14421 we are in an empty line, where bpos_max is set to
14422 MATRIX_ROW_START_CHARPOS, see above. */
14423 if (bpos_max <= pt_old && bpos_covered >= pt_old)
14424 {
14425 cursor = glyph;
14426 break;
14427 }
14428 }
14429
14430 string_seen = 1;
14431 }
14432 x += glyph->pixel_width;
14433 ++glyph;
14434 }
14435 else if (glyph > end) /* row is reversed */
14436 while (!NILP (glyph->object))
14437 {
14438 if (BUFFERP (glyph->object))
14439 {
14440 ptrdiff_t dpos = glyph->charpos - pt_old;
14441
14442 if (glyph->charpos > bpos_max)
14443 bpos_max = glyph->charpos;
14444 if (glyph->charpos < bpos_min)
14445 bpos_min = glyph->charpos;
14446 if (!glyph->avoid_cursor_p)
14447 {
14448 if (dpos == 0)
14449 {
14450 match_with_avoid_cursor = 0;
14451 break;
14452 }
14453 if (0 > dpos && dpos > pos_before - pt_old)
14454 {
14455 pos_before = glyph->charpos;
14456 glyph_before = glyph;
14457 }
14458 else if (0 < dpos && dpos < pos_after - pt_old)
14459 {
14460 pos_after = glyph->charpos;
14461 glyph_after = glyph;
14462 }
14463 }
14464 else if (dpos == 0)
14465 match_with_avoid_cursor = 1;
14466 }
14467 else if (STRINGP (glyph->object))
14468 {
14469 Lisp_Object chprop;
14470 ptrdiff_t glyph_pos = glyph->charpos;
14471
14472 chprop = Fget_char_property (make_number (glyph_pos), Qcursor,
14473 glyph->object);
14474 if (!NILP (chprop))
14475 {
14476 ptrdiff_t prop_pos =
14477 string_buffer_position_lim (glyph->object, pos_before,
14478 pos_after, 0);
14479
14480 if (prop_pos >= pos_before)
14481 bpos_max = prop_pos;
14482 }
14483 if (INTEGERP (chprop))
14484 {
14485 bpos_covered = bpos_max + XINT (chprop);
14486 /* If the `cursor' property covers buffer positions up
14487 to and including point, we should display cursor on
14488 this glyph. */
14489 if (bpos_max <= pt_old && bpos_covered >= pt_old)
14490 {
14491 cursor = glyph;
14492 break;
14493 }
14494 }
14495 string_seen = 1;
14496 }
14497 --glyph;
14498 if (glyph == glyphs_end) /* don't dereference outside TEXT_AREA */
14499 {
14500 x--; /* can't use any pixel_width */
14501 break;
14502 }
14503 x -= glyph->pixel_width;
14504 }
14505
14506 /* Step 2: If we didn't find an exact match for point, we need to
14507 look for a proper place to put the cursor among glyphs between
14508 GLYPH_BEFORE and GLYPH_AFTER. */
14509 if (!((row->reversed_p ? glyph > glyphs_end : glyph < glyphs_end)
14510 && BUFFERP (glyph->object) && glyph->charpos == pt_old)
14511 && !(bpos_max <= pt_old && pt_old <= bpos_covered))
14512 {
14513 /* An empty line has a single glyph whose OBJECT is nil and
14514 whose CHARPOS is the position of a newline on that line.
14515 Note that on a TTY, there are more glyphs after that, which
14516 were produced by extend_face_to_end_of_line, but their
14517 CHARPOS is zero or negative. */
14518 int empty_line_p =
14519 (row->reversed_p ? glyph > glyphs_end : glyph < glyphs_end)
14520 && NILP (glyph->object) && glyph->charpos > 0
14521 /* On a TTY, continued and truncated rows also have a glyph at
14522 their end whose OBJECT is nil and whose CHARPOS is
14523 positive (the continuation and truncation glyphs), but such
14524 rows are obviously not "empty". */
14525 && !(row->continued_p || row->truncated_on_right_p);
14526
14527 if (row->ends_in_ellipsis_p && pos_after == last_pos)
14528 {
14529 ptrdiff_t ellipsis_pos;
14530
14531 /* Scan back over the ellipsis glyphs. */
14532 if (!row->reversed_p)
14533 {
14534 ellipsis_pos = (glyph - 1)->charpos;
14535 while (glyph > row->glyphs[TEXT_AREA]
14536 && (glyph - 1)->charpos == ellipsis_pos)
14537 glyph--, x -= glyph->pixel_width;
14538 /* That loop always goes one position too far, including
14539 the glyph before the ellipsis. So scan forward over
14540 that one. */
14541 x += glyph->pixel_width;
14542 glyph++;
14543 }
14544 else /* row is reversed */
14545 {
14546 ellipsis_pos = (glyph + 1)->charpos;
14547 while (glyph < row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1
14548 && (glyph + 1)->charpos == ellipsis_pos)
14549 glyph++, x += glyph->pixel_width;
14550 x -= glyph->pixel_width;
14551 glyph--;
14552 }
14553 }
14554 else if (match_with_avoid_cursor)
14555 {
14556 cursor = glyph_after;
14557 x = -1;
14558 }
14559 else if (string_seen)
14560 {
14561 int incr = row->reversed_p ? -1 : +1;
14562
14563 /* Need to find the glyph that came out of a string which is
14564 present at point. That glyph is somewhere between
14565 GLYPH_BEFORE and GLYPH_AFTER, and it came from a string
14566 positioned between POS_BEFORE and POS_AFTER in the
14567 buffer. */
14568 struct glyph *start, *stop;
14569 ptrdiff_t pos = pos_before;
14570
14571 x = -1;
14572
14573 /* If the row ends in a newline from a display string,
14574 reordering could have moved the glyphs belonging to the
14575 string out of the [GLYPH_BEFORE..GLYPH_AFTER] range. So
14576 in this case we extend the search to the last glyph in
14577 the row that was not inserted by redisplay. */
14578 if (row->ends_in_newline_from_string_p)
14579 {
14580 glyph_after = end;
14581 pos_after = MATRIX_ROW_END_CHARPOS (row) + delta;
14582 }
14583
14584 /* GLYPH_BEFORE and GLYPH_AFTER are the glyphs that
14585 correspond to POS_BEFORE and POS_AFTER, respectively. We
14586 need START and STOP in the order that corresponds to the
14587 row's direction as given by its reversed_p flag. If the
14588 directionality of characters between POS_BEFORE and
14589 POS_AFTER is the opposite of the row's base direction,
14590 these characters will have been reordered for display,
14591 and we need to reverse START and STOP. */
14592 if (!row->reversed_p)
14593 {
14594 start = min (glyph_before, glyph_after);
14595 stop = max (glyph_before, glyph_after);
14596 }
14597 else
14598 {
14599 start = max (glyph_before, glyph_after);
14600 stop = min (glyph_before, glyph_after);
14601 }
14602 for (glyph = start + incr;
14603 row->reversed_p ? glyph > stop : glyph < stop; )
14604 {
14605
14606 /* Any glyphs that come from the buffer are here because
14607 of bidi reordering. Skip them, and only pay
14608 attention to glyphs that came from some string. */
14609 if (STRINGP (glyph->object))
14610 {
14611 Lisp_Object str;
14612 ptrdiff_t tem;
14613 /* If the display property covers the newline, we
14614 need to search for it one position farther. */
14615 ptrdiff_t lim = pos_after
14616 + (pos_after == MATRIX_ROW_END_CHARPOS (row) + delta);
14617
14618 string_from_text_prop = 0;
14619 str = glyph->object;
14620 tem = string_buffer_position_lim (str, pos, lim, 0);
14621 if (tem == 0 /* from overlay */
14622 || pos <= tem)
14623 {
14624 /* If the string from which this glyph came is
14625 found in the buffer at point, or at position
14626 that is closer to point than pos_after, then
14627 we've found the glyph we've been looking for.
14628 If it comes from an overlay (tem == 0), and
14629 it has the `cursor' property on one of its
14630 glyphs, record that glyph as a candidate for
14631 displaying the cursor. (As in the
14632 unidirectional version, we will display the
14633 cursor on the last candidate we find.) */
14634 if (tem == 0
14635 || tem == pt_old
14636 || (tem - pt_old > 0 && tem < pos_after))
14637 {
14638 /* The glyphs from this string could have
14639 been reordered. Find the one with the
14640 smallest string position. Or there could
14641 be a character in the string with the
14642 `cursor' property, which means display
14643 cursor on that character's glyph. */
14644 ptrdiff_t strpos = glyph->charpos;
14645
14646 if (tem)
14647 {
14648 cursor = glyph;
14649 string_from_text_prop = 1;
14650 }
14651 for ( ;
14652 (row->reversed_p ? glyph > stop : glyph < stop)
14653 && EQ (glyph->object, str);
14654 glyph += incr)
14655 {
14656 Lisp_Object cprop;
14657 ptrdiff_t gpos = glyph->charpos;
14658
14659 cprop = Fget_char_property (make_number (gpos),
14660 Qcursor,
14661 glyph->object);
14662 if (!NILP (cprop))
14663 {
14664 cursor = glyph;
14665 break;
14666 }
14667 if (tem && glyph->charpos < strpos)
14668 {
14669 strpos = glyph->charpos;
14670 cursor = glyph;
14671 }
14672 }
14673
14674 if (tem == pt_old
14675 || (tem - pt_old > 0 && tem < pos_after))
14676 goto compute_x;
14677 }
14678 if (tem)
14679 pos = tem + 1; /* don't find previous instances */
14680 }
14681 /* This string is not what we want; skip all of the
14682 glyphs that came from it. */
14683 while ((row->reversed_p ? glyph > stop : glyph < stop)
14684 && EQ (glyph->object, str))
14685 glyph += incr;
14686 }
14687 else
14688 glyph += incr;
14689 }
14690
14691 /* If we reached the end of the line, and END was from a string,
14692 the cursor is not on this line. */
14693 if (cursor == NULL
14694 && (row->reversed_p ? glyph <= end : glyph >= end)
14695 && (row->reversed_p ? end > glyphs_end : end < glyphs_end)
14696 && STRINGP (end->object)
14697 && row->continued_p)
14698 return 0;
14699 }
14700 /* A truncated row may not include PT among its character positions.
14701 Setting the cursor inside the scroll margin will trigger
14702 recalculation of hscroll in hscroll_window_tree. But if a
14703 display string covers point, defer to the string-handling
14704 code below to figure this out. */
14705 else if (row->truncated_on_left_p && pt_old < bpos_min)
14706 {
14707 cursor = glyph_before;
14708 x = -1;
14709 }
14710 else if ((row->truncated_on_right_p && pt_old > bpos_max)
14711 /* Zero-width characters produce no glyphs. */
14712 || (!empty_line_p
14713 && (row->reversed_p
14714 ? glyph_after > glyphs_end
14715 : glyph_after < glyphs_end)))
14716 {
14717 cursor = glyph_after;
14718 x = -1;
14719 }
14720 }
14721
14722 compute_x:
14723 if (cursor != NULL)
14724 glyph = cursor;
14725 else if (glyph == glyphs_end
14726 && pos_before == pos_after
14727 && STRINGP ((row->reversed_p
14728 ? row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1
14729 : row->glyphs[TEXT_AREA])->object))
14730 {
14731 /* If all the glyphs of this row came from strings, put the
14732 cursor on the first glyph of the row. This avoids having the
14733 cursor outside of the text area in this very rare and hard
14734 use case. */
14735 glyph =
14736 row->reversed_p
14737 ? row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1
14738 : row->glyphs[TEXT_AREA];
14739 }
14740 if (x < 0)
14741 {
14742 struct glyph *g;
14743
14744 /* Need to compute x that corresponds to GLYPH. */
14745 for (g = row->glyphs[TEXT_AREA], x = row->x; g < glyph; g++)
14746 {
14747 if (g >= row->glyphs[TEXT_AREA] + row->used[TEXT_AREA])
14748 emacs_abort ();
14749 x += g->pixel_width;
14750 }
14751 }
14752
14753 /* ROW could be part of a continued line, which, under bidi
14754 reordering, might have other rows whose start and end charpos
14755 occlude point. Only set w->cursor if we found a better
14756 approximation to the cursor position than we have from previously
14757 examined candidate rows belonging to the same continued line. */
14758 if (/* We already have a candidate row. */
14759 w->cursor.vpos >= 0
14760 /* That candidate is not the row we are processing. */
14761 && MATRIX_ROW (matrix, w->cursor.vpos) != row
14762 /* Make sure cursor.vpos specifies a row whose start and end
14763 charpos occlude point, and it is valid candidate for being a
14764 cursor-row. This is because some callers of this function
14765 leave cursor.vpos at the row where the cursor was displayed
14766 during the last redisplay cycle. */
14767 && MATRIX_ROW_START_CHARPOS (MATRIX_ROW (matrix, w->cursor.vpos)) <= pt_old
14768 && pt_old <= MATRIX_ROW_END_CHARPOS (MATRIX_ROW (matrix, w->cursor.vpos))
14769 && cursor_row_p (MATRIX_ROW (matrix, w->cursor.vpos)))
14770 {
14771 struct glyph *g1
14772 = MATRIX_ROW_GLYPH_START (matrix, w->cursor.vpos) + w->cursor.hpos;
14773
14774 /* Don't consider glyphs that are outside TEXT_AREA. */
14775 if (!(row->reversed_p ? glyph > glyphs_end : glyph < glyphs_end))
14776 return 0;
14777 /* Keep the candidate whose buffer position is the closest to
14778 point or has the `cursor' property. */
14779 if (/* Previous candidate is a glyph in TEXT_AREA of that row. */
14780 w->cursor.hpos >= 0
14781 && w->cursor.hpos < MATRIX_ROW_USED (matrix, w->cursor.vpos)
14782 && ((BUFFERP (g1->object)
14783 && (g1->charpos == pt_old /* An exact match always wins. */
14784 || (BUFFERP (glyph->object)
14785 && eabs (g1->charpos - pt_old)
14786 < eabs (glyph->charpos - pt_old))))
14787 /* Previous candidate is a glyph from a string that has
14788 a non-nil `cursor' property. */
14789 || (STRINGP (g1->object)
14790 && (!NILP (Fget_char_property (make_number (g1->charpos),
14791 Qcursor, g1->object))
14792 /* Previous candidate is from the same display
14793 string as this one, and the display string
14794 came from a text property. */
14795 || (EQ (g1->object, glyph->object)
14796 && string_from_text_prop)
14797 /* this candidate is from newline and its
14798 position is not an exact match */
14799 || (NILP (glyph->object)
14800 && glyph->charpos != pt_old)))))
14801 return 0;
14802 /* If this candidate gives an exact match, use that. */
14803 if (!((BUFFERP (glyph->object) && glyph->charpos == pt_old)
14804 /* If this candidate is a glyph created for the
14805 terminating newline of a line, and point is on that
14806 newline, it wins because it's an exact match. */
14807 || (!row->continued_p
14808 && NILP (glyph->object)
14809 && glyph->charpos == 0
14810 && pt_old == MATRIX_ROW_END_CHARPOS (row) - 1))
14811 /* Otherwise, keep the candidate that comes from a row
14812 spanning less buffer positions. This may win when one or
14813 both candidate positions are on glyphs that came from
14814 display strings, for which we cannot compare buffer
14815 positions. */
14816 && MATRIX_ROW_END_CHARPOS (MATRIX_ROW (matrix, w->cursor.vpos))
14817 - MATRIX_ROW_START_CHARPOS (MATRIX_ROW (matrix, w->cursor.vpos))
14818 < MATRIX_ROW_END_CHARPOS (row) - MATRIX_ROW_START_CHARPOS (row))
14819 return 0;
14820 }
14821 w->cursor.hpos = glyph - row->glyphs[TEXT_AREA];
14822 w->cursor.x = x;
14823 w->cursor.vpos = MATRIX_ROW_VPOS (row, matrix) + dvpos;
14824 w->cursor.y = row->y + dy;
14825
14826 if (w == XWINDOW (selected_window))
14827 {
14828 if (!row->continued_p
14829 && !MATRIX_ROW_CONTINUATION_LINE_P (row)
14830 && row->x == 0)
14831 {
14832 this_line_buffer = XBUFFER (w->contents);
14833
14834 CHARPOS (this_line_start_pos)
14835 = MATRIX_ROW_START_CHARPOS (row) + delta;
14836 BYTEPOS (this_line_start_pos)
14837 = MATRIX_ROW_START_BYTEPOS (row) + delta_bytes;
14838
14839 CHARPOS (this_line_end_pos)
14840 = Z - (MATRIX_ROW_END_CHARPOS (row) + delta);
14841 BYTEPOS (this_line_end_pos)
14842 = Z_BYTE - (MATRIX_ROW_END_BYTEPOS (row) + delta_bytes);
14843
14844 this_line_y = w->cursor.y;
14845 this_line_pixel_height = row->height;
14846 this_line_vpos = w->cursor.vpos;
14847 this_line_start_x = row->x;
14848 }
14849 else
14850 CHARPOS (this_line_start_pos) = 0;
14851 }
14852
14853 return 1;
14854 }
14855
14856
14857 /* Run window scroll functions, if any, for WINDOW with new window
14858 start STARTP. Sets the window start of WINDOW to that position.
14859
14860 We assume that the window's buffer is really current. */
14861
14862 static struct text_pos
14863 run_window_scroll_functions (Lisp_Object window, struct text_pos startp)
14864 {
14865 struct window *w = XWINDOW (window);
14866 SET_MARKER_FROM_TEXT_POS (w->start, startp);
14867
14868 eassert (current_buffer == XBUFFER (w->contents));
14869
14870 if (!NILP (Vwindow_scroll_functions))
14871 {
14872 run_hook_with_args_2 (Qwindow_scroll_functions, window,
14873 make_number (CHARPOS (startp)));
14874 SET_TEXT_POS_FROM_MARKER (startp, w->start);
14875 /* In case the hook functions switch buffers. */
14876 set_buffer_internal (XBUFFER (w->contents));
14877 }
14878
14879 return startp;
14880 }
14881
14882
14883 /* Make sure the line containing the cursor is fully visible.
14884 A value of 1 means there is nothing to be done.
14885 (Either the line is fully visible, or it cannot be made so,
14886 or we cannot tell.)
14887
14888 If FORCE_P is non-zero, return 0 even if partial visible cursor row
14889 is higher than window.
14890
14891 If CURRENT_MATRIX_P is non-zero, use the information from the
14892 window's current glyph matrix; otherwise use the desired glyph
14893 matrix.
14894
14895 A value of 0 means the caller should do scrolling
14896 as if point had gone off the screen. */
14897
14898 static int
14899 cursor_row_fully_visible_p (struct window *w, int force_p, int current_matrix_p)
14900 {
14901 struct glyph_matrix *matrix;
14902 struct glyph_row *row;
14903 int window_height;
14904
14905 if (!make_cursor_line_fully_visible_p)
14906 return 1;
14907
14908 /* It's not always possible to find the cursor, e.g, when a window
14909 is full of overlay strings. Don't do anything in that case. */
14910 if (w->cursor.vpos < 0)
14911 return 1;
14912
14913 matrix = current_matrix_p ? w->current_matrix : w->desired_matrix;
14914 row = MATRIX_ROW (matrix, w->cursor.vpos);
14915
14916 /* If the cursor row is not partially visible, there's nothing to do. */
14917 if (!MATRIX_ROW_PARTIALLY_VISIBLE_P (w, row))
14918 return 1;
14919
14920 /* If the row the cursor is in is taller than the window's height,
14921 it's not clear what to do, so do nothing. */
14922 window_height = window_box_height (w);
14923 if (row->height >= window_height)
14924 {
14925 if (!force_p || MINI_WINDOW_P (w)
14926 || w->vscroll || w->cursor.vpos == 0)
14927 return 1;
14928 }
14929 return 0;
14930 }
14931
14932
14933 /* Try scrolling PT into view in window WINDOW. JUST_THIS_ONE_P
14934 non-zero means only WINDOW is redisplayed in redisplay_internal.
14935 TEMP_SCROLL_STEP has the same meaning as emacs_scroll_step, and is used
14936 in redisplay_window to bring a partially visible line into view in
14937 the case that only the cursor has moved.
14938
14939 LAST_LINE_MISFIT should be nonzero if we're scrolling because the
14940 last screen line's vertical height extends past the end of the screen.
14941
14942 Value is
14943
14944 1 if scrolling succeeded
14945
14946 0 if scrolling didn't find point.
14947
14948 -1 if new fonts have been loaded so that we must interrupt
14949 redisplay, adjust glyph matrices, and try again. */
14950
14951 enum
14952 {
14953 SCROLLING_SUCCESS,
14954 SCROLLING_FAILED,
14955 SCROLLING_NEED_LARGER_MATRICES
14956 };
14957
14958 /* If scroll-conservatively is more than this, never recenter.
14959
14960 If you change this, don't forget to update the doc string of
14961 `scroll-conservatively' and the Emacs manual. */
14962 #define SCROLL_LIMIT 100
14963
14964 static int
14965 try_scrolling (Lisp_Object window, int just_this_one_p,
14966 ptrdiff_t arg_scroll_conservatively, ptrdiff_t scroll_step,
14967 int temp_scroll_step, int last_line_misfit)
14968 {
14969 struct window *w = XWINDOW (window);
14970 struct frame *f = XFRAME (w->frame);
14971 struct text_pos pos, startp;
14972 struct it it;
14973 int this_scroll_margin, scroll_max, rc, height;
14974 int dy = 0, amount_to_scroll = 0, scroll_down_p = 0;
14975 int extra_scroll_margin_lines = last_line_misfit ? 1 : 0;
14976 Lisp_Object aggressive;
14977 /* We will never try scrolling more than this number of lines. */
14978 int scroll_limit = SCROLL_LIMIT;
14979 int frame_line_height = default_line_pixel_height (w);
14980 int window_total_lines
14981 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) / frame_line_height;
14982
14983 #ifdef GLYPH_DEBUG
14984 debug_method_add (w, "try_scrolling");
14985 #endif
14986
14987 SET_TEXT_POS_FROM_MARKER (startp, w->start);
14988
14989 /* Compute scroll margin height in pixels. We scroll when point is
14990 within this distance from the top or bottom of the window. */
14991 if (scroll_margin > 0)
14992 this_scroll_margin = min (scroll_margin, window_total_lines / 4)
14993 * frame_line_height;
14994 else
14995 this_scroll_margin = 0;
14996
14997 /* Force arg_scroll_conservatively to have a reasonable value, to
14998 avoid scrolling too far away with slow move_it_* functions. Note
14999 that the user can supply scroll-conservatively equal to
15000 `most-positive-fixnum', which can be larger than INT_MAX. */
15001 if (arg_scroll_conservatively > scroll_limit)
15002 {
15003 arg_scroll_conservatively = scroll_limit + 1;
15004 scroll_max = scroll_limit * frame_line_height;
15005 }
15006 else if (scroll_step || arg_scroll_conservatively || temp_scroll_step)
15007 /* Compute how much we should try to scroll maximally to bring
15008 point into view. */
15009 scroll_max = (max (scroll_step,
15010 max (arg_scroll_conservatively, temp_scroll_step))
15011 * frame_line_height);
15012 else if (NUMBERP (BVAR (current_buffer, scroll_down_aggressively))
15013 || NUMBERP (BVAR (current_buffer, scroll_up_aggressively)))
15014 /* We're trying to scroll because of aggressive scrolling but no
15015 scroll_step is set. Choose an arbitrary one. */
15016 scroll_max = 10 * frame_line_height;
15017 else
15018 scroll_max = 0;
15019
15020 too_near_end:
15021
15022 /* Decide whether to scroll down. */
15023 if (PT > CHARPOS (startp))
15024 {
15025 int scroll_margin_y;
15026
15027 /* Compute the pixel ypos of the scroll margin, then move IT to
15028 either that ypos or PT, whichever comes first. */
15029 start_display (&it, w, startp);
15030 scroll_margin_y = it.last_visible_y - this_scroll_margin
15031 - frame_line_height * extra_scroll_margin_lines;
15032 move_it_to (&it, PT, -1, scroll_margin_y - 1, -1,
15033 (MOVE_TO_POS | MOVE_TO_Y));
15034
15035 if (PT > CHARPOS (it.current.pos))
15036 {
15037 int y0 = line_bottom_y (&it);
15038 /* Compute how many pixels below window bottom to stop searching
15039 for PT. This avoids costly search for PT that is far away if
15040 the user limited scrolling by a small number of lines, but
15041 always finds PT if scroll_conservatively is set to a large
15042 number, such as most-positive-fixnum. */
15043 int slack = max (scroll_max, 10 * frame_line_height);
15044 int y_to_move = it.last_visible_y + slack;
15045
15046 /* Compute the distance from the scroll margin to PT or to
15047 the scroll limit, whichever comes first. This should
15048 include the height of the cursor line, to make that line
15049 fully visible. */
15050 move_it_to (&it, PT, -1, y_to_move,
15051 -1, MOVE_TO_POS | MOVE_TO_Y);
15052 dy = line_bottom_y (&it) - y0;
15053
15054 if (dy > scroll_max)
15055 return SCROLLING_FAILED;
15056
15057 if (dy > 0)
15058 scroll_down_p = 1;
15059 }
15060 }
15061
15062 if (scroll_down_p)
15063 {
15064 /* Point is in or below the bottom scroll margin, so move the
15065 window start down. If scrolling conservatively, move it just
15066 enough down to make point visible. If scroll_step is set,
15067 move it down by scroll_step. */
15068 if (arg_scroll_conservatively)
15069 amount_to_scroll
15070 = min (max (dy, frame_line_height),
15071 frame_line_height * arg_scroll_conservatively);
15072 else if (scroll_step || temp_scroll_step)
15073 amount_to_scroll = scroll_max;
15074 else
15075 {
15076 aggressive = BVAR (current_buffer, scroll_up_aggressively);
15077 height = WINDOW_BOX_TEXT_HEIGHT (w);
15078 if (NUMBERP (aggressive))
15079 {
15080 double float_amount = XFLOATINT (aggressive) * height;
15081 int aggressive_scroll = float_amount;
15082 if (aggressive_scroll == 0 && float_amount > 0)
15083 aggressive_scroll = 1;
15084 /* Don't let point enter the scroll margin near top of
15085 the window. This could happen if the value of
15086 scroll_up_aggressively is too large and there are
15087 non-zero margins, because scroll_up_aggressively
15088 means put point that fraction of window height
15089 _from_the_bottom_margin_. */
15090 if (aggressive_scroll + 2 * this_scroll_margin > height)
15091 aggressive_scroll = height - 2 * this_scroll_margin;
15092 amount_to_scroll = dy + aggressive_scroll;
15093 }
15094 }
15095
15096 if (amount_to_scroll <= 0)
15097 return SCROLLING_FAILED;
15098
15099 start_display (&it, w, startp);
15100 if (arg_scroll_conservatively <= scroll_limit)
15101 move_it_vertically (&it, amount_to_scroll);
15102 else
15103 {
15104 /* Extra precision for users who set scroll-conservatively
15105 to a large number: make sure the amount we scroll
15106 the window start is never less than amount_to_scroll,
15107 which was computed as distance from window bottom to
15108 point. This matters when lines at window top and lines
15109 below window bottom have different height. */
15110 struct it it1;
15111 void *it1data = NULL;
15112 /* We use a temporary it1 because line_bottom_y can modify
15113 its argument, if it moves one line down; see there. */
15114 int start_y;
15115
15116 SAVE_IT (it1, it, it1data);
15117 start_y = line_bottom_y (&it1);
15118 do {
15119 RESTORE_IT (&it, &it, it1data);
15120 move_it_by_lines (&it, 1);
15121 SAVE_IT (it1, it, it1data);
15122 } while (line_bottom_y (&it1) - start_y < amount_to_scroll);
15123 }
15124
15125 /* If STARTP is unchanged, move it down another screen line. */
15126 if (CHARPOS (it.current.pos) == CHARPOS (startp))
15127 move_it_by_lines (&it, 1);
15128 startp = it.current.pos;
15129 }
15130 else
15131 {
15132 struct text_pos scroll_margin_pos = startp;
15133 int y_offset = 0;
15134
15135 /* See if point is inside the scroll margin at the top of the
15136 window. */
15137 if (this_scroll_margin)
15138 {
15139 int y_start;
15140
15141 start_display (&it, w, startp);
15142 y_start = it.current_y;
15143 move_it_vertically (&it, this_scroll_margin);
15144 scroll_margin_pos = it.current.pos;
15145 /* If we didn't move enough before hitting ZV, request
15146 additional amount of scroll, to move point out of the
15147 scroll margin. */
15148 if (IT_CHARPOS (it) == ZV
15149 && it.current_y - y_start < this_scroll_margin)
15150 y_offset = this_scroll_margin - (it.current_y - y_start);
15151 }
15152
15153 if (PT < CHARPOS (scroll_margin_pos))
15154 {
15155 /* Point is in the scroll margin at the top of the window or
15156 above what is displayed in the window. */
15157 int y0, y_to_move;
15158
15159 /* Compute the vertical distance from PT to the scroll
15160 margin position. Move as far as scroll_max allows, or
15161 one screenful, or 10 screen lines, whichever is largest.
15162 Give up if distance is greater than scroll_max or if we
15163 didn't reach the scroll margin position. */
15164 SET_TEXT_POS (pos, PT, PT_BYTE);
15165 start_display (&it, w, pos);
15166 y0 = it.current_y;
15167 y_to_move = max (it.last_visible_y,
15168 max (scroll_max, 10 * frame_line_height));
15169 move_it_to (&it, CHARPOS (scroll_margin_pos), 0,
15170 y_to_move, -1,
15171 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
15172 dy = it.current_y - y0;
15173 if (dy > scroll_max
15174 || IT_CHARPOS (it) < CHARPOS (scroll_margin_pos))
15175 return SCROLLING_FAILED;
15176
15177 /* Additional scroll for when ZV was too close to point. */
15178 dy += y_offset;
15179
15180 /* Compute new window start. */
15181 start_display (&it, w, startp);
15182
15183 if (arg_scroll_conservatively)
15184 amount_to_scroll = max (dy, frame_line_height
15185 * max (scroll_step, temp_scroll_step));
15186 else if (scroll_step || temp_scroll_step)
15187 amount_to_scroll = scroll_max;
15188 else
15189 {
15190 aggressive = BVAR (current_buffer, scroll_down_aggressively);
15191 height = WINDOW_BOX_TEXT_HEIGHT (w);
15192 if (NUMBERP (aggressive))
15193 {
15194 double float_amount = XFLOATINT (aggressive) * height;
15195 int aggressive_scroll = float_amount;
15196 if (aggressive_scroll == 0 && float_amount > 0)
15197 aggressive_scroll = 1;
15198 /* Don't let point enter the scroll margin near
15199 bottom of the window, if the value of
15200 scroll_down_aggressively happens to be too
15201 large. */
15202 if (aggressive_scroll + 2 * this_scroll_margin > height)
15203 aggressive_scroll = height - 2 * this_scroll_margin;
15204 amount_to_scroll = dy + aggressive_scroll;
15205 }
15206 }
15207
15208 if (amount_to_scroll <= 0)
15209 return SCROLLING_FAILED;
15210
15211 move_it_vertically_backward (&it, amount_to_scroll);
15212 startp = it.current.pos;
15213 }
15214 }
15215
15216 /* Run window scroll functions. */
15217 startp = run_window_scroll_functions (window, startp);
15218
15219 /* Display the window. Give up if new fonts are loaded, or if point
15220 doesn't appear. */
15221 if (!try_window (window, startp, 0))
15222 rc = SCROLLING_NEED_LARGER_MATRICES;
15223 else if (w->cursor.vpos < 0)
15224 {
15225 clear_glyph_matrix (w->desired_matrix);
15226 rc = SCROLLING_FAILED;
15227 }
15228 else
15229 {
15230 /* Maybe forget recorded base line for line number display. */
15231 if (!just_this_one_p
15232 || current_buffer->clip_changed
15233 || BEG_UNCHANGED < CHARPOS (startp))
15234 w->base_line_number = 0;
15235
15236 /* If cursor ends up on a partially visible line,
15237 treat that as being off the bottom of the screen. */
15238 if (! cursor_row_fully_visible_p (w, extra_scroll_margin_lines <= 1, 0)
15239 /* It's possible that the cursor is on the first line of the
15240 buffer, which is partially obscured due to a vscroll
15241 (Bug#7537). In that case, avoid looping forever. */
15242 && extra_scroll_margin_lines < w->desired_matrix->nrows - 1)
15243 {
15244 clear_glyph_matrix (w->desired_matrix);
15245 ++extra_scroll_margin_lines;
15246 goto too_near_end;
15247 }
15248 rc = SCROLLING_SUCCESS;
15249 }
15250
15251 return rc;
15252 }
15253
15254
15255 /* Compute a suitable window start for window W if display of W starts
15256 on a continuation line. Value is non-zero if a new window start
15257 was computed.
15258
15259 The new window start will be computed, based on W's width, starting
15260 from the start of the continued line. It is the start of the
15261 screen line with the minimum distance from the old start W->start. */
15262
15263 static int
15264 compute_window_start_on_continuation_line (struct window *w)
15265 {
15266 struct text_pos pos, start_pos;
15267 int window_start_changed_p = 0;
15268
15269 SET_TEXT_POS_FROM_MARKER (start_pos, w->start);
15270
15271 /* If window start is on a continuation line... Window start may be
15272 < BEGV in case there's invisible text at the start of the
15273 buffer (M-x rmail, for example). */
15274 if (CHARPOS (start_pos) > BEGV
15275 && FETCH_BYTE (BYTEPOS (start_pos) - 1) != '\n')
15276 {
15277 struct it it;
15278 struct glyph_row *row;
15279
15280 /* Handle the case that the window start is out of range. */
15281 if (CHARPOS (start_pos) < BEGV)
15282 SET_TEXT_POS (start_pos, BEGV, BEGV_BYTE);
15283 else if (CHARPOS (start_pos) > ZV)
15284 SET_TEXT_POS (start_pos, ZV, ZV_BYTE);
15285
15286 /* Find the start of the continued line. This should be fast
15287 because find_newline is fast (newline cache). */
15288 row = w->desired_matrix->rows + (WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0);
15289 init_iterator (&it, w, CHARPOS (start_pos), BYTEPOS (start_pos),
15290 row, DEFAULT_FACE_ID);
15291 reseat_at_previous_visible_line_start (&it);
15292
15293 /* If the line start is "too far" away from the window start,
15294 say it takes too much time to compute a new window start. */
15295 if (CHARPOS (start_pos) - IT_CHARPOS (it)
15296 /* PXW: Do we need upper bounds here? */
15297 < WINDOW_TOTAL_LINES (w) * WINDOW_TOTAL_COLS (w))
15298 {
15299 int min_distance, distance;
15300
15301 /* Move forward by display lines to find the new window
15302 start. If window width was enlarged, the new start can
15303 be expected to be > the old start. If window width was
15304 decreased, the new window start will be < the old start.
15305 So, we're looking for the display line start with the
15306 minimum distance from the old window start. */
15307 pos = it.current.pos;
15308 min_distance = INFINITY;
15309 while ((distance = eabs (CHARPOS (start_pos) - IT_CHARPOS (it))),
15310 distance < min_distance)
15311 {
15312 min_distance = distance;
15313 pos = it.current.pos;
15314 if (it.line_wrap == WORD_WRAP)
15315 {
15316 /* Under WORD_WRAP, move_it_by_lines is likely to
15317 overshoot and stop not at the first, but the
15318 second character from the left margin. So in
15319 that case, we need a more tight control on the X
15320 coordinate of the iterator than move_it_by_lines
15321 promises in its contract. The method is to first
15322 go to the last (rightmost) visible character of a
15323 line, then move to the leftmost character on the
15324 next line in a separate call. */
15325 move_it_to (&it, ZV, it.last_visible_x, it.current_y, -1,
15326 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
15327 move_it_to (&it, ZV, 0,
15328 it.current_y + it.max_ascent + it.max_descent, -1,
15329 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
15330 }
15331 else
15332 move_it_by_lines (&it, 1);
15333 }
15334
15335 /* Set the window start there. */
15336 SET_MARKER_FROM_TEXT_POS (w->start, pos);
15337 window_start_changed_p = 1;
15338 }
15339 }
15340
15341 return window_start_changed_p;
15342 }
15343
15344
15345 /* Try cursor movement in case text has not changed in window WINDOW,
15346 with window start STARTP. Value is
15347
15348 CURSOR_MOVEMENT_SUCCESS if successful
15349
15350 CURSOR_MOVEMENT_CANNOT_BE_USED if this method cannot be used
15351
15352 CURSOR_MOVEMENT_MUST_SCROLL if we know we have to scroll the
15353 display. *SCROLL_STEP is set to 1, under certain circumstances, if
15354 we want to scroll as if scroll-step were set to 1. See the code.
15355
15356 CURSOR_MOVEMENT_NEED_LARGER_MATRICES if we need larger matrices, in
15357 which case we have to abort this redisplay, and adjust matrices
15358 first. */
15359
15360 enum
15361 {
15362 CURSOR_MOVEMENT_SUCCESS,
15363 CURSOR_MOVEMENT_CANNOT_BE_USED,
15364 CURSOR_MOVEMENT_MUST_SCROLL,
15365 CURSOR_MOVEMENT_NEED_LARGER_MATRICES
15366 };
15367
15368 static int
15369 try_cursor_movement (Lisp_Object window, struct text_pos startp, int *scroll_step)
15370 {
15371 struct window *w = XWINDOW (window);
15372 struct frame *f = XFRAME (w->frame);
15373 int rc = CURSOR_MOVEMENT_CANNOT_BE_USED;
15374
15375 #ifdef GLYPH_DEBUG
15376 if (inhibit_try_cursor_movement)
15377 return rc;
15378 #endif
15379
15380 /* Previously, there was a check for Lisp integer in the
15381 if-statement below. Now, this field is converted to
15382 ptrdiff_t, thus zero means invalid position in a buffer. */
15383 eassert (w->last_point > 0);
15384 /* Likewise there was a check whether window_end_vpos is nil or larger
15385 than the window. Now window_end_vpos is int and so never nil, but
15386 let's leave eassert to check whether it fits in the window. */
15387 eassert (!w->window_end_valid
15388 || w->window_end_vpos < w->current_matrix->nrows);
15389
15390 /* Handle case where text has not changed, only point, and it has
15391 not moved off the frame. */
15392 if (/* Point may be in this window. */
15393 PT >= CHARPOS (startp)
15394 /* Selective display hasn't changed. */
15395 && !current_buffer->clip_changed
15396 /* Function force-mode-line-update is used to force a thorough
15397 redisplay. It sets either windows_or_buffers_changed or
15398 update_mode_lines. So don't take a shortcut here for these
15399 cases. */
15400 && !update_mode_lines
15401 && !windows_or_buffers_changed
15402 && !f->cursor_type_changed
15403 && NILP (Vshow_trailing_whitespace)
15404 /* This code is not used for mini-buffer for the sake of the case
15405 of redisplaying to replace an echo area message; since in
15406 that case the mini-buffer contents per se are usually
15407 unchanged. This code is of no real use in the mini-buffer
15408 since the handling of this_line_start_pos, etc., in redisplay
15409 handles the same cases. */
15410 && !EQ (window, minibuf_window)
15411 && (FRAME_WINDOW_P (f)
15412 || !overlay_arrow_in_current_buffer_p ()))
15413 {
15414 int this_scroll_margin, top_scroll_margin;
15415 struct glyph_row *row = NULL;
15416 int frame_line_height = default_line_pixel_height (w);
15417 int window_total_lines
15418 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) / frame_line_height;
15419
15420 #ifdef GLYPH_DEBUG
15421 debug_method_add (w, "cursor movement");
15422 #endif
15423
15424 /* Scroll if point within this distance from the top or bottom
15425 of the window. This is a pixel value. */
15426 if (scroll_margin > 0)
15427 {
15428 this_scroll_margin = min (scroll_margin, window_total_lines / 4);
15429 this_scroll_margin *= frame_line_height;
15430 }
15431 else
15432 this_scroll_margin = 0;
15433
15434 top_scroll_margin = this_scroll_margin;
15435 if (WINDOW_WANTS_HEADER_LINE_P (w))
15436 top_scroll_margin += CURRENT_HEADER_LINE_HEIGHT (w);
15437
15438 /* Start with the row the cursor was displayed during the last
15439 not paused redisplay. Give up if that row is not valid. */
15440 if (w->last_cursor_vpos < 0
15441 || w->last_cursor_vpos >= w->current_matrix->nrows)
15442 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15443 else
15444 {
15445 row = MATRIX_ROW (w->current_matrix, w->last_cursor_vpos);
15446 if (row->mode_line_p)
15447 ++row;
15448 if (!row->enabled_p)
15449 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15450 }
15451
15452 if (rc == CURSOR_MOVEMENT_CANNOT_BE_USED)
15453 {
15454 int scroll_p = 0, must_scroll = 0;
15455 int last_y = window_text_bottom_y (w) - this_scroll_margin;
15456
15457 if (PT > w->last_point)
15458 {
15459 /* Point has moved forward. */
15460 while (MATRIX_ROW_END_CHARPOS (row) < PT
15461 && MATRIX_ROW_BOTTOM_Y (row) < last_y)
15462 {
15463 eassert (row->enabled_p);
15464 ++row;
15465 }
15466
15467 /* If the end position of a row equals the start
15468 position of the next row, and PT is at that position,
15469 we would rather display cursor in the next line. */
15470 while (MATRIX_ROW_BOTTOM_Y (row) < last_y
15471 && MATRIX_ROW_END_CHARPOS (row) == PT
15472 && row < MATRIX_MODE_LINE_ROW (w->current_matrix)
15473 && MATRIX_ROW_START_CHARPOS (row+1) == PT
15474 && !cursor_row_p (row))
15475 ++row;
15476
15477 /* If within the scroll margin, scroll. Note that
15478 MATRIX_ROW_BOTTOM_Y gives the pixel position at which
15479 the next line would be drawn, and that
15480 this_scroll_margin can be zero. */
15481 if (MATRIX_ROW_BOTTOM_Y (row) > last_y
15482 || PT > MATRIX_ROW_END_CHARPOS (row)
15483 /* Line is completely visible last line in window
15484 and PT is to be set in the next line. */
15485 || (MATRIX_ROW_BOTTOM_Y (row) == last_y
15486 && PT == MATRIX_ROW_END_CHARPOS (row)
15487 && !row->ends_at_zv_p
15488 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row)))
15489 scroll_p = 1;
15490 }
15491 else if (PT < w->last_point)
15492 {
15493 /* Cursor has to be moved backward. Note that PT >=
15494 CHARPOS (startp) because of the outer if-statement. */
15495 while (!row->mode_line_p
15496 && (MATRIX_ROW_START_CHARPOS (row) > PT
15497 || (MATRIX_ROW_START_CHARPOS (row) == PT
15498 && (MATRIX_ROW_STARTS_IN_MIDDLE_OF_CHAR_P (row)
15499 || (/* STARTS_IN_MIDDLE_OF_STRING_P (row) */
15500 row > w->current_matrix->rows
15501 && (row-1)->ends_in_newline_from_string_p))))
15502 && (row->y > top_scroll_margin
15503 || CHARPOS (startp) == BEGV))
15504 {
15505 eassert (row->enabled_p);
15506 --row;
15507 }
15508
15509 /* Consider the following case: Window starts at BEGV,
15510 there is invisible, intangible text at BEGV, so that
15511 display starts at some point START > BEGV. It can
15512 happen that we are called with PT somewhere between
15513 BEGV and START. Try to handle that case. */
15514 if (row < w->current_matrix->rows
15515 || row->mode_line_p)
15516 {
15517 row = w->current_matrix->rows;
15518 if (row->mode_line_p)
15519 ++row;
15520 }
15521
15522 /* Due to newlines in overlay strings, we may have to
15523 skip forward over overlay strings. */
15524 while (MATRIX_ROW_BOTTOM_Y (row) < last_y
15525 && MATRIX_ROW_END_CHARPOS (row) == PT
15526 && !cursor_row_p (row))
15527 ++row;
15528
15529 /* If within the scroll margin, scroll. */
15530 if (row->y < top_scroll_margin
15531 && CHARPOS (startp) != BEGV)
15532 scroll_p = 1;
15533 }
15534 else
15535 {
15536 /* Cursor did not move. So don't scroll even if cursor line
15537 is partially visible, as it was so before. */
15538 rc = CURSOR_MOVEMENT_SUCCESS;
15539 }
15540
15541 if (PT < MATRIX_ROW_START_CHARPOS (row)
15542 || PT > MATRIX_ROW_END_CHARPOS (row))
15543 {
15544 /* if PT is not in the glyph row, give up. */
15545 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15546 must_scroll = 1;
15547 }
15548 else if (rc != CURSOR_MOVEMENT_SUCCESS
15549 && !NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering)))
15550 {
15551 struct glyph_row *row1;
15552
15553 /* If rows are bidi-reordered and point moved, back up
15554 until we find a row that does not belong to a
15555 continuation line. This is because we must consider
15556 all rows of a continued line as candidates for the
15557 new cursor positioning, since row start and end
15558 positions change non-linearly with vertical position
15559 in such rows. */
15560 /* FIXME: Revisit this when glyph ``spilling'' in
15561 continuation lines' rows is implemented for
15562 bidi-reordered rows. */
15563 for (row1 = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
15564 MATRIX_ROW_CONTINUATION_LINE_P (row);
15565 --row)
15566 {
15567 /* If we hit the beginning of the displayed portion
15568 without finding the first row of a continued
15569 line, give up. */
15570 if (row <= row1)
15571 {
15572 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15573 break;
15574 }
15575 eassert (row->enabled_p);
15576 }
15577 }
15578 if (must_scroll)
15579 ;
15580 else if (rc != CURSOR_MOVEMENT_SUCCESS
15581 && MATRIX_ROW_PARTIALLY_VISIBLE_P (w, row)
15582 /* Make sure this isn't a header line by any chance, since
15583 then MATRIX_ROW_PARTIALLY_VISIBLE_P might yield non-zero. */
15584 && !row->mode_line_p
15585 && make_cursor_line_fully_visible_p)
15586 {
15587 if (PT == MATRIX_ROW_END_CHARPOS (row)
15588 && !row->ends_at_zv_p
15589 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))
15590 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15591 else if (row->height > window_box_height (w))
15592 {
15593 /* If we end up in a partially visible line, let's
15594 make it fully visible, except when it's taller
15595 than the window, in which case we can't do much
15596 about it. */
15597 *scroll_step = 1;
15598 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15599 }
15600 else
15601 {
15602 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
15603 if (!cursor_row_fully_visible_p (w, 0, 1))
15604 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15605 else
15606 rc = CURSOR_MOVEMENT_SUCCESS;
15607 }
15608 }
15609 else if (scroll_p)
15610 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15611 else if (rc != CURSOR_MOVEMENT_SUCCESS
15612 && !NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering)))
15613 {
15614 /* With bidi-reordered rows, there could be more than
15615 one candidate row whose start and end positions
15616 occlude point. We need to let set_cursor_from_row
15617 find the best candidate. */
15618 /* FIXME: Revisit this when glyph ``spilling'' in
15619 continuation lines' rows is implemented for
15620 bidi-reordered rows. */
15621 int rv = 0;
15622
15623 do
15624 {
15625 int at_zv_p = 0, exact_match_p = 0;
15626
15627 if (MATRIX_ROW_START_CHARPOS (row) <= PT
15628 && PT <= MATRIX_ROW_END_CHARPOS (row)
15629 && cursor_row_p (row))
15630 rv |= set_cursor_from_row (w, row, w->current_matrix,
15631 0, 0, 0, 0);
15632 /* As soon as we've found the exact match for point,
15633 or the first suitable row whose ends_at_zv_p flag
15634 is set, we are done. */
15635 if (rv)
15636 {
15637 at_zv_p = MATRIX_ROW (w->current_matrix,
15638 w->cursor.vpos)->ends_at_zv_p;
15639 if (!at_zv_p
15640 && w->cursor.hpos >= 0
15641 && w->cursor.hpos < MATRIX_ROW_USED (w->current_matrix,
15642 w->cursor.vpos))
15643 {
15644 struct glyph_row *candidate =
15645 MATRIX_ROW (w->current_matrix, w->cursor.vpos);
15646 struct glyph *g =
15647 candidate->glyphs[TEXT_AREA] + w->cursor.hpos;
15648 ptrdiff_t endpos = MATRIX_ROW_END_CHARPOS (candidate);
15649
15650 exact_match_p =
15651 (BUFFERP (g->object) && g->charpos == PT)
15652 || (NILP (g->object)
15653 && (g->charpos == PT
15654 || (g->charpos == 0 && endpos - 1 == PT)));
15655 }
15656 if (at_zv_p || exact_match_p)
15657 {
15658 rc = CURSOR_MOVEMENT_SUCCESS;
15659 break;
15660 }
15661 }
15662 if (MATRIX_ROW_BOTTOM_Y (row) == last_y)
15663 break;
15664 ++row;
15665 }
15666 while (((MATRIX_ROW_CONTINUATION_LINE_P (row)
15667 || row->continued_p)
15668 && MATRIX_ROW_BOTTOM_Y (row) <= last_y)
15669 || (MATRIX_ROW_START_CHARPOS (row) == PT
15670 && MATRIX_ROW_BOTTOM_Y (row) < last_y));
15671 /* If we didn't find any candidate rows, or exited the
15672 loop before all the candidates were examined, signal
15673 to the caller that this method failed. */
15674 if (rc != CURSOR_MOVEMENT_SUCCESS
15675 && !(rv
15676 && !MATRIX_ROW_CONTINUATION_LINE_P (row)
15677 && !row->continued_p))
15678 rc = CURSOR_MOVEMENT_MUST_SCROLL;
15679 else if (rv)
15680 rc = CURSOR_MOVEMENT_SUCCESS;
15681 }
15682 else
15683 {
15684 do
15685 {
15686 if (set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0))
15687 {
15688 rc = CURSOR_MOVEMENT_SUCCESS;
15689 break;
15690 }
15691 ++row;
15692 }
15693 while (MATRIX_ROW_BOTTOM_Y (row) < last_y
15694 && MATRIX_ROW_START_CHARPOS (row) == PT
15695 && cursor_row_p (row));
15696 }
15697 }
15698 }
15699
15700 return rc;
15701 }
15702
15703
15704 void
15705 set_vertical_scroll_bar (struct window *w)
15706 {
15707 ptrdiff_t start, end, whole;
15708
15709 /* Calculate the start and end positions for the current window.
15710 At some point, it would be nice to choose between scrollbars
15711 which reflect the whole buffer size, with special markers
15712 indicating narrowing, and scrollbars which reflect only the
15713 visible region.
15714
15715 Note that mini-buffers sometimes aren't displaying any text. */
15716 if (!MINI_WINDOW_P (w)
15717 || (w == XWINDOW (minibuf_window)
15718 && NILP (echo_area_buffer[0])))
15719 {
15720 struct buffer *buf = XBUFFER (w->contents);
15721 whole = BUF_ZV (buf) - BUF_BEGV (buf);
15722 start = marker_position (w->start) - BUF_BEGV (buf);
15723 /* I don't think this is guaranteed to be right. For the
15724 moment, we'll pretend it is. */
15725 end = BUF_Z (buf) - w->window_end_pos - BUF_BEGV (buf);
15726
15727 if (end < start)
15728 end = start;
15729 if (whole < (end - start))
15730 whole = end - start;
15731 }
15732 else
15733 start = end = whole = 0;
15734
15735 /* Indicate what this scroll bar ought to be displaying now. */
15736 if (FRAME_TERMINAL (XFRAME (w->frame))->set_vertical_scroll_bar_hook)
15737 (*FRAME_TERMINAL (XFRAME (w->frame))->set_vertical_scroll_bar_hook)
15738 (w, end - start, whole, start);
15739 }
15740
15741
15742 void
15743 set_horizontal_scroll_bar (struct window *w)
15744 {
15745 int start, end, whole, portion;
15746
15747 if (!MINI_WINDOW_P (w)
15748 || (w == XWINDOW (minibuf_window)
15749 && NILP (echo_area_buffer[0])))
15750 {
15751 struct buffer *b = XBUFFER (w->contents);
15752 struct buffer *old_buffer = NULL;
15753 struct it it;
15754 struct text_pos startp;
15755
15756 if (b != current_buffer)
15757 {
15758 old_buffer = current_buffer;
15759 set_buffer_internal (b);
15760 }
15761
15762 SET_TEXT_POS_FROM_MARKER (startp, w->start);
15763 start_display (&it, w, startp);
15764 it.last_visible_x = INT_MAX;
15765 whole = move_it_to (&it, -1, INT_MAX, window_box_height (w), -1,
15766 MOVE_TO_X | MOVE_TO_Y);
15767 /* whole = move_it_to (&it, w->window_end_pos, INT_MAX,
15768 window_box_height (w), -1,
15769 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y); */
15770
15771 start = w->hscroll * FRAME_COLUMN_WIDTH (WINDOW_XFRAME (w));
15772 end = start + window_box_width (w, TEXT_AREA);
15773 portion = end - start;
15774 /* After enlarging a horizontally scrolled window such that it
15775 gets at least as wide as the text it contains, make sure that
15776 the thumb doesn't fill the entire scroll bar so we can still
15777 drag it back to see the entire text. */
15778 whole = max (whole, end);
15779
15780 if (it.bidi_p)
15781 {
15782 Lisp_Object pdir;
15783
15784 pdir = Fcurrent_bidi_paragraph_direction (Qnil);
15785 if (EQ (pdir, Qright_to_left))
15786 {
15787 start = whole - end;
15788 end = start + portion;
15789 }
15790 }
15791
15792 if (old_buffer)
15793 set_buffer_internal (old_buffer);
15794 }
15795 else
15796 start = end = whole = portion = 0;
15797
15798 w->hscroll_whole = whole;
15799
15800 /* Indicate what this scroll bar ought to be displaying now. */
15801 if (FRAME_TERMINAL (XFRAME (w->frame))->set_horizontal_scroll_bar_hook)
15802 (*FRAME_TERMINAL (XFRAME (w->frame))->set_horizontal_scroll_bar_hook)
15803 (w, portion, whole, start);
15804 }
15805
15806
15807 /* Redisplay leaf window WINDOW. JUST_THIS_ONE_P non-zero means only
15808 selected_window is redisplayed.
15809
15810 We can return without actually redisplaying the window if fonts has been
15811 changed on window's frame. In that case, redisplay_internal will retry.
15812
15813 As one of the important parts of redisplaying a window, we need to
15814 decide whether the previous window-start position (stored in the
15815 window's w->start marker position) is still valid, and if it isn't,
15816 recompute it. Some details about that:
15817
15818 . The previous window-start could be in a continuation line, in
15819 which case we need to recompute it when the window width
15820 changes. See compute_window_start_on_continuation_line and its
15821 call below.
15822
15823 . The text that changed since last redisplay could include the
15824 previous window-start position. In that case, we try to salvage
15825 what we can from the current glyph matrix by calling
15826 try_scrolling, which see.
15827
15828 . Some Emacs command could force us to use a specific window-start
15829 position by setting the window's force_start flag, or gently
15830 propose doing that by setting the window's optional_new_start
15831 flag. In these cases, we try using the specified start point if
15832 that succeeds (i.e. the window desired matrix is successfully
15833 recomputed, and point location is within the window). In case
15834 of optional_new_start, we first check if the specified start
15835 position is feasible, i.e. if it will allow point to be
15836 displayed in the window. If using the specified start point
15837 fails, e.g., if new fonts are needed to be loaded, we abort the
15838 redisplay cycle and leave it up to the next cycle to figure out
15839 things.
15840
15841 . Note that the window's force_start flag is sometimes set by
15842 redisplay itself, when it decides that the previous window start
15843 point is fine and should be kept. Search for "goto force_start"
15844 below to see the details. Like the values of window-start
15845 specified outside of redisplay, these internally-deduced values
15846 are tested for feasibility, and ignored if found to be
15847 unfeasible.
15848
15849 . Note that the function try_window, used to completely redisplay
15850 a window, accepts the window's start point as its argument.
15851 This is used several times in the redisplay code to control
15852 where the window start will be, according to user options such
15853 as scroll-conservatively, and also to ensure the screen line
15854 showing point will be fully (as opposed to partially) visible on
15855 display. */
15856
15857 static void
15858 redisplay_window (Lisp_Object window, bool just_this_one_p)
15859 {
15860 struct window *w = XWINDOW (window);
15861 struct frame *f = XFRAME (w->frame);
15862 struct buffer *buffer = XBUFFER (w->contents);
15863 struct buffer *old = current_buffer;
15864 struct text_pos lpoint, opoint, startp;
15865 int update_mode_line;
15866 int tem;
15867 struct it it;
15868 /* Record it now because it's overwritten. */
15869 bool current_matrix_up_to_date_p = false;
15870 bool used_current_matrix_p = false;
15871 /* This is less strict than current_matrix_up_to_date_p.
15872 It indicates that the buffer contents and narrowing are unchanged. */
15873 bool buffer_unchanged_p = false;
15874 int temp_scroll_step = 0;
15875 ptrdiff_t count = SPECPDL_INDEX ();
15876 int rc;
15877 int centering_position = -1;
15878 int last_line_misfit = 0;
15879 ptrdiff_t beg_unchanged, end_unchanged;
15880 int frame_line_height;
15881
15882 SET_TEXT_POS (lpoint, PT, PT_BYTE);
15883 opoint = lpoint;
15884
15885 #ifdef GLYPH_DEBUG
15886 *w->desired_matrix->method = 0;
15887 #endif
15888
15889 if (!just_this_one_p
15890 && REDISPLAY_SOME_P ()
15891 && !w->redisplay
15892 && !f->redisplay
15893 && !buffer->text->redisplay
15894 && BUF_PT (buffer) == w->last_point)
15895 return;
15896
15897 /* Make sure that both W's markers are valid. */
15898 eassert (XMARKER (w->start)->buffer == buffer);
15899 eassert (XMARKER (w->pointm)->buffer == buffer);
15900
15901 /* We come here again if we need to run window-text-change-functions
15902 below. */
15903 restart:
15904 reconsider_clip_changes (w);
15905 frame_line_height = default_line_pixel_height (w);
15906
15907 /* Has the mode line to be updated? */
15908 update_mode_line = (w->update_mode_line
15909 || update_mode_lines
15910 || buffer->clip_changed
15911 || buffer->prevent_redisplay_optimizations_p);
15912
15913 if (!just_this_one_p)
15914 /* If `just_this_one_p' is set, we apparently set must_be_updated_p more
15915 cleverly elsewhere. */
15916 w->must_be_updated_p = true;
15917
15918 if (MINI_WINDOW_P (w))
15919 {
15920 if (w == XWINDOW (echo_area_window)
15921 && !NILP (echo_area_buffer[0]))
15922 {
15923 if (update_mode_line)
15924 /* We may have to update a tty frame's menu bar or a
15925 tool-bar. Example `M-x C-h C-h C-g'. */
15926 goto finish_menu_bars;
15927 else
15928 /* We've already displayed the echo area glyphs in this window. */
15929 goto finish_scroll_bars;
15930 }
15931 else if ((w != XWINDOW (minibuf_window)
15932 || minibuf_level == 0)
15933 /* When buffer is nonempty, redisplay window normally. */
15934 && BUF_Z (XBUFFER (w->contents)) == BUF_BEG (XBUFFER (w->contents))
15935 /* Quail displays non-mini buffers in minibuffer window.
15936 In that case, redisplay the window normally. */
15937 && !NILP (Fmemq (w->contents, Vminibuffer_list)))
15938 {
15939 /* W is a mini-buffer window, but it's not active, so clear
15940 it. */
15941 int yb = window_text_bottom_y (w);
15942 struct glyph_row *row;
15943 int y;
15944
15945 for (y = 0, row = w->desired_matrix->rows;
15946 y < yb;
15947 y += row->height, ++row)
15948 blank_row (w, row, y);
15949 goto finish_scroll_bars;
15950 }
15951
15952 clear_glyph_matrix (w->desired_matrix);
15953 }
15954
15955 /* Otherwise set up data on this window; select its buffer and point
15956 value. */
15957 /* Really select the buffer, for the sake of buffer-local
15958 variables. */
15959 set_buffer_internal_1 (XBUFFER (w->contents));
15960
15961 current_matrix_up_to_date_p
15962 = (w->window_end_valid
15963 && !current_buffer->clip_changed
15964 && !current_buffer->prevent_redisplay_optimizations_p
15965 && !window_outdated (w));
15966
15967 /* Run the window-text-change-functions
15968 if it is possible that the text on the screen has changed
15969 (either due to modification of the text, or any other reason). */
15970 if (!current_matrix_up_to_date_p
15971 && !NILP (Vwindow_text_change_functions))
15972 {
15973 safe_run_hooks (Qwindow_text_change_functions);
15974 goto restart;
15975 }
15976
15977 beg_unchanged = BEG_UNCHANGED;
15978 end_unchanged = END_UNCHANGED;
15979
15980 SET_TEXT_POS (opoint, PT, PT_BYTE);
15981
15982 specbind (Qinhibit_point_motion_hooks, Qt);
15983
15984 buffer_unchanged_p
15985 = (w->window_end_valid
15986 && !current_buffer->clip_changed
15987 && !window_outdated (w));
15988
15989 /* When windows_or_buffers_changed is non-zero, we can't rely
15990 on the window end being valid, so set it to zero there. */
15991 if (windows_or_buffers_changed)
15992 {
15993 /* If window starts on a continuation line, maybe adjust the
15994 window start in case the window's width changed. */
15995 if (XMARKER (w->start)->buffer == current_buffer)
15996 compute_window_start_on_continuation_line (w);
15997
15998 w->window_end_valid = false;
15999 /* If so, we also can't rely on current matrix
16000 and should not fool try_cursor_movement below. */
16001 current_matrix_up_to_date_p = false;
16002 }
16003
16004 /* Some sanity checks. */
16005 CHECK_WINDOW_END (w);
16006 if (Z == Z_BYTE && CHARPOS (opoint) != BYTEPOS (opoint))
16007 emacs_abort ();
16008 if (BYTEPOS (opoint) < CHARPOS (opoint))
16009 emacs_abort ();
16010
16011 if (mode_line_update_needed (w))
16012 update_mode_line = 1;
16013
16014 /* Point refers normally to the selected window. For any other
16015 window, set up appropriate value. */
16016 if (!EQ (window, selected_window))
16017 {
16018 ptrdiff_t new_pt = marker_position (w->pointm);
16019 ptrdiff_t new_pt_byte = marker_byte_position (w->pointm);
16020
16021 if (new_pt < BEGV)
16022 {
16023 new_pt = BEGV;
16024 new_pt_byte = BEGV_BYTE;
16025 set_marker_both (w->pointm, Qnil, BEGV, BEGV_BYTE);
16026 }
16027 else if (new_pt > (ZV - 1))
16028 {
16029 new_pt = ZV;
16030 new_pt_byte = ZV_BYTE;
16031 set_marker_both (w->pointm, Qnil, ZV, ZV_BYTE);
16032 }
16033
16034 /* We don't use SET_PT so that the point-motion hooks don't run. */
16035 TEMP_SET_PT_BOTH (new_pt, new_pt_byte);
16036 }
16037
16038 /* If any of the character widths specified in the display table
16039 have changed, invalidate the width run cache. It's true that
16040 this may be a bit late to catch such changes, but the rest of
16041 redisplay goes (non-fatally) haywire when the display table is
16042 changed, so why should we worry about doing any better? */
16043 if (current_buffer->width_run_cache
16044 || (current_buffer->base_buffer
16045 && current_buffer->base_buffer->width_run_cache))
16046 {
16047 struct Lisp_Char_Table *disptab = buffer_display_table ();
16048
16049 if (! disptab_matches_widthtab
16050 (disptab, XVECTOR (BVAR (current_buffer, width_table))))
16051 {
16052 struct buffer *buf = current_buffer;
16053
16054 if (buf->base_buffer)
16055 buf = buf->base_buffer;
16056 invalidate_region_cache (buf, buf->width_run_cache, BEG, Z);
16057 recompute_width_table (current_buffer, disptab);
16058 }
16059 }
16060
16061 /* If window-start is screwed up, choose a new one. */
16062 if (XMARKER (w->start)->buffer != current_buffer)
16063 goto recenter;
16064
16065 SET_TEXT_POS_FROM_MARKER (startp, w->start);
16066
16067 /* If someone specified a new starting point but did not insist,
16068 check whether it can be used. */
16069 if ((w->optional_new_start || window_frozen_p (w))
16070 && CHARPOS (startp) >= BEGV
16071 && CHARPOS (startp) <= ZV)
16072 {
16073 ptrdiff_t it_charpos;
16074
16075 w->optional_new_start = 0;
16076 start_display (&it, w, startp);
16077 move_it_to (&it, PT, 0, it.last_visible_y, -1,
16078 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
16079 /* Record IT's position now, since line_bottom_y might change
16080 that. */
16081 it_charpos = IT_CHARPOS (it);
16082 /* Make sure we set the force_start flag only if the cursor row
16083 will be fully visible. Otherwise, the code under force_start
16084 label below will try to move point back into view, which is
16085 not what the code which sets optional_new_start wants. */
16086 if ((it.current_y == 0 || line_bottom_y (&it) < it.last_visible_y)
16087 && !w->force_start)
16088 {
16089 if (it_charpos == PT)
16090 w->force_start = 1;
16091 /* IT may overshoot PT if text at PT is invisible. */
16092 else if (it_charpos > PT && CHARPOS (startp) <= PT)
16093 w->force_start = 1;
16094 #ifdef GLYPH_DEBUG
16095 if (w->force_start)
16096 {
16097 if (window_frozen_p (w))
16098 debug_method_add (w, "set force_start from frozen window start");
16099 else
16100 debug_method_add (w, "set force_start from optional_new_start");
16101 }
16102 #endif
16103 }
16104 }
16105
16106 force_start:
16107
16108 /* Handle case where place to start displaying has been specified,
16109 unless the specified location is outside the accessible range. */
16110 if (w->force_start)
16111 {
16112 /* We set this later on if we have to adjust point. */
16113 int new_vpos = -1;
16114
16115 w->force_start = 0;
16116 w->vscroll = 0;
16117 w->window_end_valid = 0;
16118
16119 /* Forget any recorded base line for line number display. */
16120 if (!buffer_unchanged_p)
16121 w->base_line_number = 0;
16122
16123 /* Redisplay the mode line. Select the buffer properly for that.
16124 Also, run the hook window-scroll-functions
16125 because we have scrolled. */
16126 /* Note, we do this after clearing force_start because
16127 if there's an error, it is better to forget about force_start
16128 than to get into an infinite loop calling the hook functions
16129 and having them get more errors. */
16130 if (!update_mode_line
16131 || ! NILP (Vwindow_scroll_functions))
16132 {
16133 update_mode_line = 1;
16134 w->update_mode_line = 1;
16135 startp = run_window_scroll_functions (window, startp);
16136 }
16137
16138 if (CHARPOS (startp) < BEGV)
16139 SET_TEXT_POS (startp, BEGV, BEGV_BYTE);
16140 else if (CHARPOS (startp) > ZV)
16141 SET_TEXT_POS (startp, ZV, ZV_BYTE);
16142
16143 /* Redisplay, then check if cursor has been set during the
16144 redisplay. Give up if new fonts were loaded. */
16145 /* We used to issue a CHECK_MARGINS argument to try_window here,
16146 but this causes scrolling to fail when point begins inside
16147 the scroll margin (bug#148) -- cyd */
16148 if (!try_window (window, startp, 0))
16149 {
16150 w->force_start = 1;
16151 clear_glyph_matrix (w->desired_matrix);
16152 goto need_larger_matrices;
16153 }
16154
16155 if (w->cursor.vpos < 0)
16156 {
16157 /* If point does not appear, try to move point so it does
16158 appear. The desired matrix has been built above, so we
16159 can use it here. */
16160 new_vpos = window_box_height (w) / 2;
16161 }
16162
16163 if (!cursor_row_fully_visible_p (w, 0, 0))
16164 {
16165 /* Point does appear, but on a line partly visible at end of window.
16166 Move it back to a fully-visible line. */
16167 new_vpos = window_box_height (w);
16168 /* But if window_box_height suggests a Y coordinate that is
16169 not less than we already have, that line will clearly not
16170 be fully visible, so give up and scroll the display.
16171 This can happen when the default face uses a font whose
16172 dimensions are different from the frame's default
16173 font. */
16174 if (new_vpos >= w->cursor.y)
16175 {
16176 w->cursor.vpos = -1;
16177 clear_glyph_matrix (w->desired_matrix);
16178 goto try_to_scroll;
16179 }
16180 }
16181 else if (w->cursor.vpos >= 0)
16182 {
16183 /* Some people insist on not letting point enter the scroll
16184 margin, even though this part handles windows that didn't
16185 scroll at all. */
16186 int window_total_lines
16187 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) / frame_line_height;
16188 int margin = min (scroll_margin, window_total_lines / 4);
16189 int pixel_margin = margin * frame_line_height;
16190 bool header_line = WINDOW_WANTS_HEADER_LINE_P (w);
16191
16192 /* Note: We add an extra FRAME_LINE_HEIGHT, because the loop
16193 below, which finds the row to move point to, advances by
16194 the Y coordinate of the _next_ row, see the definition of
16195 MATRIX_ROW_BOTTOM_Y. */
16196 if (w->cursor.vpos < margin + header_line)
16197 {
16198 w->cursor.vpos = -1;
16199 clear_glyph_matrix (w->desired_matrix);
16200 goto try_to_scroll;
16201 }
16202 else
16203 {
16204 int window_height = window_box_height (w);
16205
16206 if (header_line)
16207 window_height += CURRENT_HEADER_LINE_HEIGHT (w);
16208 if (w->cursor.y >= window_height - pixel_margin)
16209 {
16210 w->cursor.vpos = -1;
16211 clear_glyph_matrix (w->desired_matrix);
16212 goto try_to_scroll;
16213 }
16214 }
16215 }
16216
16217 /* If we need to move point for either of the above reasons,
16218 now actually do it. */
16219 if (new_vpos >= 0)
16220 {
16221 struct glyph_row *row;
16222
16223 row = MATRIX_FIRST_TEXT_ROW (w->desired_matrix);
16224 while (MATRIX_ROW_BOTTOM_Y (row) < new_vpos)
16225 ++row;
16226
16227 TEMP_SET_PT_BOTH (MATRIX_ROW_START_CHARPOS (row),
16228 MATRIX_ROW_START_BYTEPOS (row));
16229
16230 if (w != XWINDOW (selected_window))
16231 set_marker_both (w->pointm, Qnil, PT, PT_BYTE);
16232 else if (current_buffer == old)
16233 SET_TEXT_POS (lpoint, PT, PT_BYTE);
16234
16235 set_cursor_from_row (w, row, w->desired_matrix, 0, 0, 0, 0);
16236
16237 /* Re-run pre-redisplay-function so it can update the region
16238 according to the new position of point. */
16239 /* Other than the cursor, w's redisplay is done so we can set its
16240 redisplay to false. Also the buffer's redisplay can be set to
16241 false, since propagate_buffer_redisplay should have already
16242 propagated its info to `w' anyway. */
16243 w->redisplay = false;
16244 XBUFFER (w->contents)->text->redisplay = false;
16245 safe__call1 (true, Vpre_redisplay_function, Fcons (window, Qnil));
16246
16247 if (w->redisplay || XBUFFER (w->contents)->text->redisplay)
16248 {
16249 /* pre-redisplay-function made changes (e.g. move the region)
16250 that require another round of redisplay. */
16251 clear_glyph_matrix (w->desired_matrix);
16252 if (!try_window (window, startp, 0))
16253 goto need_larger_matrices;
16254 }
16255 }
16256 if (w->cursor.vpos < 0 || !cursor_row_fully_visible_p (w, 0, 0))
16257 {
16258 clear_glyph_matrix (w->desired_matrix);
16259 goto try_to_scroll;
16260 }
16261
16262 #ifdef GLYPH_DEBUG
16263 debug_method_add (w, "forced window start");
16264 #endif
16265 goto done;
16266 }
16267
16268 /* Handle case where text has not changed, only point, and it has
16269 not moved off the frame, and we are not retrying after hscroll.
16270 (current_matrix_up_to_date_p is nonzero when retrying.) */
16271 if (current_matrix_up_to_date_p
16272 && (rc = try_cursor_movement (window, startp, &temp_scroll_step),
16273 rc != CURSOR_MOVEMENT_CANNOT_BE_USED))
16274 {
16275 switch (rc)
16276 {
16277 case CURSOR_MOVEMENT_SUCCESS:
16278 used_current_matrix_p = 1;
16279 goto done;
16280
16281 case CURSOR_MOVEMENT_MUST_SCROLL:
16282 goto try_to_scroll;
16283
16284 default:
16285 emacs_abort ();
16286 }
16287 }
16288 /* If current starting point was originally the beginning of a line
16289 but no longer is, find a new starting point. */
16290 else if (w->start_at_line_beg
16291 && !(CHARPOS (startp) <= BEGV
16292 || FETCH_BYTE (BYTEPOS (startp) - 1) == '\n'))
16293 {
16294 #ifdef GLYPH_DEBUG
16295 debug_method_add (w, "recenter 1");
16296 #endif
16297 goto recenter;
16298 }
16299
16300 /* Try scrolling with try_window_id. Value is > 0 if update has
16301 been done, it is -1 if we know that the same window start will
16302 not work. It is 0 if unsuccessful for some other reason. */
16303 else if ((tem = try_window_id (w)) != 0)
16304 {
16305 #ifdef GLYPH_DEBUG
16306 debug_method_add (w, "try_window_id %d", tem);
16307 #endif
16308
16309 if (f->fonts_changed)
16310 goto need_larger_matrices;
16311 if (tem > 0)
16312 goto done;
16313
16314 /* Otherwise try_window_id has returned -1 which means that we
16315 don't want the alternative below this comment to execute. */
16316 }
16317 else if (CHARPOS (startp) >= BEGV
16318 && CHARPOS (startp) <= ZV
16319 && PT >= CHARPOS (startp)
16320 && (CHARPOS (startp) < ZV
16321 /* Avoid starting at end of buffer. */
16322 || CHARPOS (startp) == BEGV
16323 || !window_outdated (w)))
16324 {
16325 int d1, d2, d5, d6;
16326 int rtop, rbot;
16327
16328 /* If first window line is a continuation line, and window start
16329 is inside the modified region, but the first change is before
16330 current window start, we must select a new window start.
16331
16332 However, if this is the result of a down-mouse event (e.g. by
16333 extending the mouse-drag-overlay), we don't want to select a
16334 new window start, since that would change the position under
16335 the mouse, resulting in an unwanted mouse-movement rather
16336 than a simple mouse-click. */
16337 if (!w->start_at_line_beg
16338 && NILP (do_mouse_tracking)
16339 && CHARPOS (startp) > BEGV
16340 && CHARPOS (startp) > BEG + beg_unchanged
16341 && CHARPOS (startp) <= Z - end_unchanged
16342 /* Even if w->start_at_line_beg is nil, a new window may
16343 start at a line_beg, since that's how set_buffer_window
16344 sets it. So, we need to check the return value of
16345 compute_window_start_on_continuation_line. (See also
16346 bug#197). */
16347 && XMARKER (w->start)->buffer == current_buffer
16348 && compute_window_start_on_continuation_line (w)
16349 /* It doesn't make sense to force the window start like we
16350 do at label force_start if it is already known that point
16351 will not be fully visible in the resulting window, because
16352 doing so will move point from its correct position
16353 instead of scrolling the window to bring point into view.
16354 See bug#9324. */
16355 && pos_visible_p (w, PT, &d1, &d2, &rtop, &rbot, &d5, &d6)
16356 /* A very tall row could need more than the window height,
16357 in which case we accept that it is partially visible. */
16358 && (rtop != 0) == (rbot != 0))
16359 {
16360 w->force_start = 1;
16361 SET_TEXT_POS_FROM_MARKER (startp, w->start);
16362 #ifdef GLYPH_DEBUG
16363 debug_method_add (w, "recomputed window start in continuation line");
16364 #endif
16365 goto force_start;
16366 }
16367
16368 #ifdef GLYPH_DEBUG
16369 debug_method_add (w, "same window start");
16370 #endif
16371
16372 /* Try to redisplay starting at same place as before.
16373 If point has not moved off frame, accept the results. */
16374 if (!current_matrix_up_to_date_p
16375 /* Don't use try_window_reusing_current_matrix in this case
16376 because a window scroll function can have changed the
16377 buffer. */
16378 || !NILP (Vwindow_scroll_functions)
16379 || MINI_WINDOW_P (w)
16380 || !(used_current_matrix_p
16381 = try_window_reusing_current_matrix (w)))
16382 {
16383 IF_DEBUG (debug_method_add (w, "1"));
16384 if (try_window (window, startp, TRY_WINDOW_CHECK_MARGINS) < 0)
16385 /* -1 means we need to scroll.
16386 0 means we need new matrices, but fonts_changed
16387 is set in that case, so we will detect it below. */
16388 goto try_to_scroll;
16389 }
16390
16391 if (f->fonts_changed)
16392 goto need_larger_matrices;
16393
16394 if (w->cursor.vpos >= 0)
16395 {
16396 if (!just_this_one_p
16397 || current_buffer->clip_changed
16398 || BEG_UNCHANGED < CHARPOS (startp))
16399 /* Forget any recorded base line for line number display. */
16400 w->base_line_number = 0;
16401
16402 if (!cursor_row_fully_visible_p (w, 1, 0))
16403 {
16404 clear_glyph_matrix (w->desired_matrix);
16405 last_line_misfit = 1;
16406 }
16407 /* Drop through and scroll. */
16408 else
16409 goto done;
16410 }
16411 else
16412 clear_glyph_matrix (w->desired_matrix);
16413 }
16414
16415 try_to_scroll:
16416
16417 /* Redisplay the mode line. Select the buffer properly for that. */
16418 if (!update_mode_line)
16419 {
16420 update_mode_line = 1;
16421 w->update_mode_line = 1;
16422 }
16423
16424 /* Try to scroll by specified few lines. */
16425 if ((scroll_conservatively
16426 || emacs_scroll_step
16427 || temp_scroll_step
16428 || NUMBERP (BVAR (current_buffer, scroll_up_aggressively))
16429 || NUMBERP (BVAR (current_buffer, scroll_down_aggressively)))
16430 && CHARPOS (startp) >= BEGV
16431 && CHARPOS (startp) <= ZV)
16432 {
16433 /* The function returns -1 if new fonts were loaded, 1 if
16434 successful, 0 if not successful. */
16435 int ss = try_scrolling (window, just_this_one_p,
16436 scroll_conservatively,
16437 emacs_scroll_step,
16438 temp_scroll_step, last_line_misfit);
16439 switch (ss)
16440 {
16441 case SCROLLING_SUCCESS:
16442 goto done;
16443
16444 case SCROLLING_NEED_LARGER_MATRICES:
16445 goto need_larger_matrices;
16446
16447 case SCROLLING_FAILED:
16448 break;
16449
16450 default:
16451 emacs_abort ();
16452 }
16453 }
16454
16455 /* Finally, just choose a place to start which positions point
16456 according to user preferences. */
16457
16458 recenter:
16459
16460 #ifdef GLYPH_DEBUG
16461 debug_method_add (w, "recenter");
16462 #endif
16463
16464 /* Forget any previously recorded base line for line number display. */
16465 if (!buffer_unchanged_p)
16466 w->base_line_number = 0;
16467
16468 /* Determine the window start relative to point. */
16469 init_iterator (&it, w, PT, PT_BYTE, NULL, DEFAULT_FACE_ID);
16470 it.current_y = it.last_visible_y;
16471 if (centering_position < 0)
16472 {
16473 int window_total_lines
16474 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) / frame_line_height;
16475 int margin
16476 = scroll_margin > 0
16477 ? min (scroll_margin, window_total_lines / 4)
16478 : 0;
16479 ptrdiff_t margin_pos = CHARPOS (startp);
16480 Lisp_Object aggressive;
16481 int scrolling_up;
16482
16483 /* If there is a scroll margin at the top of the window, find
16484 its character position. */
16485 if (margin
16486 /* Cannot call start_display if startp is not in the
16487 accessible region of the buffer. This can happen when we
16488 have just switched to a different buffer and/or changed
16489 its restriction. In that case, startp is initialized to
16490 the character position 1 (BEGV) because we did not yet
16491 have chance to display the buffer even once. */
16492 && BEGV <= CHARPOS (startp) && CHARPOS (startp) <= ZV)
16493 {
16494 struct it it1;
16495 void *it1data = NULL;
16496
16497 SAVE_IT (it1, it, it1data);
16498 start_display (&it1, w, startp);
16499 move_it_vertically (&it1, margin * frame_line_height);
16500 margin_pos = IT_CHARPOS (it1);
16501 RESTORE_IT (&it, &it, it1data);
16502 }
16503 scrolling_up = PT > margin_pos;
16504 aggressive =
16505 scrolling_up
16506 ? BVAR (current_buffer, scroll_up_aggressively)
16507 : BVAR (current_buffer, scroll_down_aggressively);
16508
16509 if (!MINI_WINDOW_P (w)
16510 && (scroll_conservatively > SCROLL_LIMIT || NUMBERP (aggressive)))
16511 {
16512 int pt_offset = 0;
16513
16514 /* Setting scroll-conservatively overrides
16515 scroll-*-aggressively. */
16516 if (!scroll_conservatively && NUMBERP (aggressive))
16517 {
16518 double float_amount = XFLOATINT (aggressive);
16519
16520 pt_offset = float_amount * WINDOW_BOX_TEXT_HEIGHT (w);
16521 if (pt_offset == 0 && float_amount > 0)
16522 pt_offset = 1;
16523 if (pt_offset && margin > 0)
16524 margin -= 1;
16525 }
16526 /* Compute how much to move the window start backward from
16527 point so that point will be displayed where the user
16528 wants it. */
16529 if (scrolling_up)
16530 {
16531 centering_position = it.last_visible_y;
16532 if (pt_offset)
16533 centering_position -= pt_offset;
16534 centering_position -=
16535 frame_line_height * (1 + margin + (last_line_misfit != 0))
16536 + WINDOW_HEADER_LINE_HEIGHT (w);
16537 /* Don't let point enter the scroll margin near top of
16538 the window. */
16539 if (centering_position < margin * frame_line_height)
16540 centering_position = margin * frame_line_height;
16541 }
16542 else
16543 centering_position = margin * frame_line_height + pt_offset;
16544 }
16545 else
16546 /* Set the window start half the height of the window backward
16547 from point. */
16548 centering_position = window_box_height (w) / 2;
16549 }
16550 move_it_vertically_backward (&it, centering_position);
16551
16552 eassert (IT_CHARPOS (it) >= BEGV);
16553
16554 /* The function move_it_vertically_backward may move over more
16555 than the specified y-distance. If it->w is small, e.g. a
16556 mini-buffer window, we may end up in front of the window's
16557 display area. Start displaying at the start of the line
16558 containing PT in this case. */
16559 if (it.current_y <= 0)
16560 {
16561 init_iterator (&it, w, PT, PT_BYTE, NULL, DEFAULT_FACE_ID);
16562 move_it_vertically_backward (&it, 0);
16563 it.current_y = 0;
16564 }
16565
16566 it.current_x = it.hpos = 0;
16567
16568 /* Set the window start position here explicitly, to avoid an
16569 infinite loop in case the functions in window-scroll-functions
16570 get errors. */
16571 set_marker_both (w->start, Qnil, IT_CHARPOS (it), IT_BYTEPOS (it));
16572
16573 /* Run scroll hooks. */
16574 startp = run_window_scroll_functions (window, it.current.pos);
16575
16576 /* Redisplay the window. */
16577 if (!current_matrix_up_to_date_p
16578 || windows_or_buffers_changed
16579 || f->cursor_type_changed
16580 /* Don't use try_window_reusing_current_matrix in this case
16581 because it can have changed the buffer. */
16582 || !NILP (Vwindow_scroll_functions)
16583 || !just_this_one_p
16584 || MINI_WINDOW_P (w)
16585 || !(used_current_matrix_p
16586 = try_window_reusing_current_matrix (w)))
16587 try_window (window, startp, 0);
16588
16589 /* If new fonts have been loaded (due to fontsets), give up. We
16590 have to start a new redisplay since we need to re-adjust glyph
16591 matrices. */
16592 if (f->fonts_changed)
16593 goto need_larger_matrices;
16594
16595 /* If cursor did not appear assume that the middle of the window is
16596 in the first line of the window. Do it again with the next line.
16597 (Imagine a window of height 100, displaying two lines of height
16598 60. Moving back 50 from it->last_visible_y will end in the first
16599 line.) */
16600 if (w->cursor.vpos < 0)
16601 {
16602 if (w->window_end_valid && PT >= Z - w->window_end_pos)
16603 {
16604 clear_glyph_matrix (w->desired_matrix);
16605 move_it_by_lines (&it, 1);
16606 try_window (window, it.current.pos, 0);
16607 }
16608 else if (PT < IT_CHARPOS (it))
16609 {
16610 clear_glyph_matrix (w->desired_matrix);
16611 move_it_by_lines (&it, -1);
16612 try_window (window, it.current.pos, 0);
16613 }
16614 else
16615 {
16616 /* Not much we can do about it. */
16617 }
16618 }
16619
16620 /* Consider the following case: Window starts at BEGV, there is
16621 invisible, intangible text at BEGV, so that display starts at
16622 some point START > BEGV. It can happen that we are called with
16623 PT somewhere between BEGV and START. Try to handle that case,
16624 and similar ones. */
16625 if (w->cursor.vpos < 0)
16626 {
16627 /* First, try locating the proper glyph row for PT. */
16628 struct glyph_row *row =
16629 row_containing_pos (w, PT, w->current_matrix->rows, NULL, 0);
16630
16631 /* Sometimes point is at the beginning of invisible text that is
16632 before the 1st character displayed in the row. In that case,
16633 row_containing_pos fails to find the row, because no glyphs
16634 with appropriate buffer positions are present in the row.
16635 Therefore, we next try to find the row which shows the 1st
16636 position after the invisible text. */
16637 if (!row)
16638 {
16639 Lisp_Object val =
16640 get_char_property_and_overlay (make_number (PT), Qinvisible,
16641 Qnil, NULL);
16642
16643 if (TEXT_PROP_MEANS_INVISIBLE (val))
16644 {
16645 ptrdiff_t alt_pos;
16646 Lisp_Object invis_end =
16647 Fnext_single_char_property_change (make_number (PT), Qinvisible,
16648 Qnil, Qnil);
16649
16650 if (NATNUMP (invis_end))
16651 alt_pos = XFASTINT (invis_end);
16652 else
16653 alt_pos = ZV;
16654 row = row_containing_pos (w, alt_pos, w->current_matrix->rows,
16655 NULL, 0);
16656 }
16657 }
16658 /* Finally, fall back on the first row of the window after the
16659 header line (if any). This is slightly better than not
16660 displaying the cursor at all. */
16661 if (!row)
16662 {
16663 row = w->current_matrix->rows;
16664 if (row->mode_line_p)
16665 ++row;
16666 }
16667 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
16668 }
16669
16670 if (!cursor_row_fully_visible_p (w, 0, 0))
16671 {
16672 /* If vscroll is enabled, disable it and try again. */
16673 if (w->vscroll)
16674 {
16675 w->vscroll = 0;
16676 clear_glyph_matrix (w->desired_matrix);
16677 goto recenter;
16678 }
16679
16680 /* Users who set scroll-conservatively to a large number want
16681 point just above/below the scroll margin. If we ended up
16682 with point's row partially visible, move the window start to
16683 make that row fully visible and out of the margin. */
16684 if (scroll_conservatively > SCROLL_LIMIT)
16685 {
16686 int window_total_lines
16687 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) * frame_line_height;
16688 int margin =
16689 scroll_margin > 0
16690 ? min (scroll_margin, window_total_lines / 4)
16691 : 0;
16692 int move_down = w->cursor.vpos >= window_total_lines / 2;
16693
16694 move_it_by_lines (&it, move_down ? margin + 1 : -(margin + 1));
16695 clear_glyph_matrix (w->desired_matrix);
16696 if (1 == try_window (window, it.current.pos,
16697 TRY_WINDOW_CHECK_MARGINS))
16698 goto done;
16699 }
16700
16701 /* If centering point failed to make the whole line visible,
16702 put point at the top instead. That has to make the whole line
16703 visible, if it can be done. */
16704 if (centering_position == 0)
16705 goto done;
16706
16707 clear_glyph_matrix (w->desired_matrix);
16708 centering_position = 0;
16709 goto recenter;
16710 }
16711
16712 done:
16713
16714 SET_TEXT_POS_FROM_MARKER (startp, w->start);
16715 w->start_at_line_beg = (CHARPOS (startp) == BEGV
16716 || FETCH_BYTE (BYTEPOS (startp) - 1) == '\n');
16717
16718 /* Display the mode line, if we must. */
16719 if ((update_mode_line
16720 /* If window not full width, must redo its mode line
16721 if (a) the window to its side is being redone and
16722 (b) we do a frame-based redisplay. This is a consequence
16723 of how inverted lines are drawn in frame-based redisplay. */
16724 || (!just_this_one_p
16725 && !FRAME_WINDOW_P (f)
16726 && !WINDOW_FULL_WIDTH_P (w))
16727 /* Line number to display. */
16728 || w->base_line_pos > 0
16729 /* Column number is displayed and different from the one displayed. */
16730 || (w->column_number_displayed != -1
16731 && (w->column_number_displayed != current_column ())))
16732 /* This means that the window has a mode line. */
16733 && (WINDOW_WANTS_MODELINE_P (w)
16734 || WINDOW_WANTS_HEADER_LINE_P (w)))
16735 {
16736
16737 display_mode_lines (w);
16738
16739 /* If mode line height has changed, arrange for a thorough
16740 immediate redisplay using the correct mode line height. */
16741 if (WINDOW_WANTS_MODELINE_P (w)
16742 && CURRENT_MODE_LINE_HEIGHT (w) != DESIRED_MODE_LINE_HEIGHT (w))
16743 {
16744 f->fonts_changed = 1;
16745 w->mode_line_height = -1;
16746 MATRIX_MODE_LINE_ROW (w->current_matrix)->height
16747 = DESIRED_MODE_LINE_HEIGHT (w);
16748 }
16749
16750 /* If header line height has changed, arrange for a thorough
16751 immediate redisplay using the correct header line height. */
16752 if (WINDOW_WANTS_HEADER_LINE_P (w)
16753 && CURRENT_HEADER_LINE_HEIGHT (w) != DESIRED_HEADER_LINE_HEIGHT (w))
16754 {
16755 f->fonts_changed = 1;
16756 w->header_line_height = -1;
16757 MATRIX_HEADER_LINE_ROW (w->current_matrix)->height
16758 = DESIRED_HEADER_LINE_HEIGHT (w);
16759 }
16760
16761 if (f->fonts_changed)
16762 goto need_larger_matrices;
16763 }
16764
16765 if (!line_number_displayed && w->base_line_pos != -1)
16766 {
16767 w->base_line_pos = 0;
16768 w->base_line_number = 0;
16769 }
16770
16771 finish_menu_bars:
16772
16773 /* When we reach a frame's selected window, redo the frame's menu bar. */
16774 if (update_mode_line
16775 && EQ (FRAME_SELECTED_WINDOW (f), window))
16776 {
16777 int redisplay_menu_p = 0;
16778
16779 if (FRAME_WINDOW_P (f))
16780 {
16781 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) \
16782 || defined (HAVE_NS) || defined (USE_GTK)
16783 redisplay_menu_p = FRAME_EXTERNAL_MENU_BAR (f);
16784 #else
16785 redisplay_menu_p = FRAME_MENU_BAR_LINES (f) > 0;
16786 #endif
16787 }
16788 else
16789 redisplay_menu_p = FRAME_MENU_BAR_LINES (f) > 0;
16790
16791 if (redisplay_menu_p)
16792 display_menu_bar (w);
16793
16794 #ifdef HAVE_WINDOW_SYSTEM
16795 if (FRAME_WINDOW_P (f))
16796 {
16797 #if defined (USE_GTK) || defined (HAVE_NS)
16798 if (FRAME_EXTERNAL_TOOL_BAR (f))
16799 redisplay_tool_bar (f);
16800 #else
16801 if (WINDOWP (f->tool_bar_window)
16802 && (FRAME_TOOL_BAR_LINES (f) > 0
16803 || !NILP (Vauto_resize_tool_bars))
16804 && redisplay_tool_bar (f))
16805 ignore_mouse_drag_p = 1;
16806 #endif
16807 }
16808 #endif
16809 }
16810
16811 #ifdef HAVE_WINDOW_SYSTEM
16812 if (FRAME_WINDOW_P (f)
16813 && update_window_fringes (w, (just_this_one_p
16814 || (!used_current_matrix_p && !overlay_arrow_seen)
16815 || w->pseudo_window_p)))
16816 {
16817 update_begin (f);
16818 block_input ();
16819 if (draw_window_fringes (w, 1))
16820 {
16821 if (WINDOW_RIGHT_DIVIDER_WIDTH (w))
16822 x_draw_right_divider (w);
16823 else
16824 x_draw_vertical_border (w);
16825 }
16826 unblock_input ();
16827 update_end (f);
16828 }
16829
16830 if (WINDOW_BOTTOM_DIVIDER_WIDTH (w))
16831 x_draw_bottom_divider (w);
16832 #endif /* HAVE_WINDOW_SYSTEM */
16833
16834 /* We go to this label, with fonts_changed set, if it is
16835 necessary to try again using larger glyph matrices.
16836 We have to redeem the scroll bar even in this case,
16837 because the loop in redisplay_internal expects that. */
16838 need_larger_matrices:
16839 ;
16840 finish_scroll_bars:
16841
16842 if (WINDOW_HAS_VERTICAL_SCROLL_BAR (w) || WINDOW_HAS_HORIZONTAL_SCROLL_BAR (w))
16843 {
16844 if (WINDOW_HAS_VERTICAL_SCROLL_BAR (w))
16845 /* Set the thumb's position and size. */
16846 set_vertical_scroll_bar (w);
16847
16848 if (WINDOW_HAS_HORIZONTAL_SCROLL_BAR (w))
16849 /* Set the thumb's position and size. */
16850 set_horizontal_scroll_bar (w);
16851
16852 /* Note that we actually used the scroll bar attached to this
16853 window, so it shouldn't be deleted at the end of redisplay. */
16854 if (FRAME_TERMINAL (f)->redeem_scroll_bar_hook)
16855 (*FRAME_TERMINAL (f)->redeem_scroll_bar_hook) (w);
16856 }
16857
16858 /* Restore current_buffer and value of point in it. The window
16859 update may have changed the buffer, so first make sure `opoint'
16860 is still valid (Bug#6177). */
16861 if (CHARPOS (opoint) < BEGV)
16862 TEMP_SET_PT_BOTH (BEGV, BEGV_BYTE);
16863 else if (CHARPOS (opoint) > ZV)
16864 TEMP_SET_PT_BOTH (Z, Z_BYTE);
16865 else
16866 TEMP_SET_PT_BOTH (CHARPOS (opoint), BYTEPOS (opoint));
16867
16868 set_buffer_internal_1 (old);
16869 /* Avoid an abort in TEMP_SET_PT_BOTH if the buffer has become
16870 shorter. This can be caused by log truncation in *Messages*. */
16871 if (CHARPOS (lpoint) <= ZV)
16872 TEMP_SET_PT_BOTH (CHARPOS (lpoint), BYTEPOS (lpoint));
16873
16874 unbind_to (count, Qnil);
16875 }
16876
16877
16878 /* Build the complete desired matrix of WINDOW with a window start
16879 buffer position POS.
16880
16881 Value is 1 if successful. It is zero if fonts were loaded during
16882 redisplay which makes re-adjusting glyph matrices necessary, and -1
16883 if point would appear in the scroll margins.
16884 (We check the former only if TRY_WINDOW_IGNORE_FONTS_CHANGE is
16885 unset in FLAGS, and the latter only if TRY_WINDOW_CHECK_MARGINS is
16886 set in FLAGS.) */
16887
16888 int
16889 try_window (Lisp_Object window, struct text_pos pos, int flags)
16890 {
16891 struct window *w = XWINDOW (window);
16892 struct it it;
16893 struct glyph_row *last_text_row = NULL;
16894 struct frame *f = XFRAME (w->frame);
16895 int frame_line_height = default_line_pixel_height (w);
16896
16897 /* Make POS the new window start. */
16898 set_marker_both (w->start, Qnil, CHARPOS (pos), BYTEPOS (pos));
16899
16900 /* Mark cursor position as unknown. No overlay arrow seen. */
16901 w->cursor.vpos = -1;
16902 overlay_arrow_seen = 0;
16903
16904 /* Initialize iterator and info to start at POS. */
16905 start_display (&it, w, pos);
16906 it.glyph_row->reversed_p = false;
16907
16908 /* Display all lines of W. */
16909 while (it.current_y < it.last_visible_y)
16910 {
16911 if (display_line (&it))
16912 last_text_row = it.glyph_row - 1;
16913 if (f->fonts_changed && !(flags & TRY_WINDOW_IGNORE_FONTS_CHANGE))
16914 return 0;
16915 }
16916
16917 /* Don't let the cursor end in the scroll margins. */
16918 if ((flags & TRY_WINDOW_CHECK_MARGINS)
16919 && !MINI_WINDOW_P (w))
16920 {
16921 int this_scroll_margin;
16922 int window_total_lines
16923 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (f) / frame_line_height;
16924
16925 if (scroll_margin > 0)
16926 {
16927 this_scroll_margin = min (scroll_margin, window_total_lines / 4);
16928 this_scroll_margin *= frame_line_height;
16929 }
16930 else
16931 this_scroll_margin = 0;
16932
16933 if ((w->cursor.y >= 0 /* not vscrolled */
16934 && w->cursor.y < this_scroll_margin
16935 && CHARPOS (pos) > BEGV
16936 && IT_CHARPOS (it) < ZV)
16937 /* rms: considering make_cursor_line_fully_visible_p here
16938 seems to give wrong results. We don't want to recenter
16939 when the last line is partly visible, we want to allow
16940 that case to be handled in the usual way. */
16941 || w->cursor.y > it.last_visible_y - this_scroll_margin - 1)
16942 {
16943 w->cursor.vpos = -1;
16944 clear_glyph_matrix (w->desired_matrix);
16945 return -1;
16946 }
16947 }
16948
16949 /* If bottom moved off end of frame, change mode line percentage. */
16950 if (w->window_end_pos <= 0 && Z != IT_CHARPOS (it))
16951 w->update_mode_line = 1;
16952
16953 /* Set window_end_pos to the offset of the last character displayed
16954 on the window from the end of current_buffer. Set
16955 window_end_vpos to its row number. */
16956 if (last_text_row)
16957 {
16958 eassert (MATRIX_ROW_DISPLAYS_TEXT_P (last_text_row));
16959 adjust_window_ends (w, last_text_row, 0);
16960 eassert
16961 (MATRIX_ROW_DISPLAYS_TEXT_P (MATRIX_ROW (w->desired_matrix,
16962 w->window_end_vpos)));
16963 }
16964 else
16965 {
16966 w->window_end_bytepos = Z_BYTE - ZV_BYTE;
16967 w->window_end_pos = Z - ZV;
16968 w->window_end_vpos = 0;
16969 }
16970
16971 /* But that is not valid info until redisplay finishes. */
16972 w->window_end_valid = 0;
16973 return 1;
16974 }
16975
16976
16977 \f
16978 /************************************************************************
16979 Window redisplay reusing current matrix when buffer has not changed
16980 ************************************************************************/
16981
16982 /* Try redisplay of window W showing an unchanged buffer with a
16983 different window start than the last time it was displayed by
16984 reusing its current matrix. Value is non-zero if successful.
16985 W->start is the new window start. */
16986
16987 static int
16988 try_window_reusing_current_matrix (struct window *w)
16989 {
16990 struct frame *f = XFRAME (w->frame);
16991 struct glyph_row *bottom_row;
16992 struct it it;
16993 struct run run;
16994 struct text_pos start, new_start;
16995 int nrows_scrolled, i;
16996 struct glyph_row *last_text_row;
16997 struct glyph_row *last_reused_text_row;
16998 struct glyph_row *start_row;
16999 int start_vpos, min_y, max_y;
17000
17001 #ifdef GLYPH_DEBUG
17002 if (inhibit_try_window_reusing)
17003 return 0;
17004 #endif
17005
17006 if (/* This function doesn't handle terminal frames. */
17007 !FRAME_WINDOW_P (f)
17008 /* Don't try to reuse the display if windows have been split
17009 or such. */
17010 || windows_or_buffers_changed
17011 || f->cursor_type_changed)
17012 return 0;
17013
17014 /* Can't do this if showing trailing whitespace. */
17015 if (!NILP (Vshow_trailing_whitespace))
17016 return 0;
17017
17018 /* If top-line visibility has changed, give up. */
17019 if (WINDOW_WANTS_HEADER_LINE_P (w)
17020 != MATRIX_HEADER_LINE_ROW (w->current_matrix)->mode_line_p)
17021 return 0;
17022
17023 /* Give up if old or new display is scrolled vertically. We could
17024 make this function handle this, but right now it doesn't. */
17025 start_row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
17026 if (w->vscroll || MATRIX_ROW_PARTIALLY_VISIBLE_P (w, start_row))
17027 return 0;
17028
17029 /* The variable new_start now holds the new window start. The old
17030 start `start' can be determined from the current matrix. */
17031 SET_TEXT_POS_FROM_MARKER (new_start, w->start);
17032 start = start_row->minpos;
17033 start_vpos = MATRIX_ROW_VPOS (start_row, w->current_matrix);
17034
17035 /* Clear the desired matrix for the display below. */
17036 clear_glyph_matrix (w->desired_matrix);
17037
17038 if (CHARPOS (new_start) <= CHARPOS (start))
17039 {
17040 /* Don't use this method if the display starts with an ellipsis
17041 displayed for invisible text. It's not easy to handle that case
17042 below, and it's certainly not worth the effort since this is
17043 not a frequent case. */
17044 if (in_ellipses_for_invisible_text_p (&start_row->start, w))
17045 return 0;
17046
17047 IF_DEBUG (debug_method_add (w, "twu1"));
17048
17049 /* Display up to a row that can be reused. The variable
17050 last_text_row is set to the last row displayed that displays
17051 text. Note that it.vpos == 0 if or if not there is a
17052 header-line; it's not the same as the MATRIX_ROW_VPOS! */
17053 start_display (&it, w, new_start);
17054 w->cursor.vpos = -1;
17055 last_text_row = last_reused_text_row = NULL;
17056
17057 while (it.current_y < it.last_visible_y && !f->fonts_changed)
17058 {
17059 /* If we have reached into the characters in the START row,
17060 that means the line boundaries have changed. So we
17061 can't start copying with the row START. Maybe it will
17062 work to start copying with the following row. */
17063 while (IT_CHARPOS (it) > CHARPOS (start))
17064 {
17065 /* Advance to the next row as the "start". */
17066 start_row++;
17067 start = start_row->minpos;
17068 /* If there are no more rows to try, or just one, give up. */
17069 if (start_row == MATRIX_MODE_LINE_ROW (w->current_matrix) - 1
17070 || w->vscroll || MATRIX_ROW_PARTIALLY_VISIBLE_P (w, start_row)
17071 || CHARPOS (start) == ZV)
17072 {
17073 clear_glyph_matrix (w->desired_matrix);
17074 return 0;
17075 }
17076
17077 start_vpos = MATRIX_ROW_VPOS (start_row, w->current_matrix);
17078 }
17079 /* If we have reached alignment, we can copy the rest of the
17080 rows. */
17081 if (IT_CHARPOS (it) == CHARPOS (start)
17082 /* Don't accept "alignment" inside a display vector,
17083 since start_row could have started in the middle of
17084 that same display vector (thus their character
17085 positions match), and we have no way of telling if
17086 that is the case. */
17087 && it.current.dpvec_index < 0)
17088 break;
17089
17090 it.glyph_row->reversed_p = false;
17091 if (display_line (&it))
17092 last_text_row = it.glyph_row - 1;
17093
17094 }
17095
17096 /* A value of current_y < last_visible_y means that we stopped
17097 at the previous window start, which in turn means that we
17098 have at least one reusable row. */
17099 if (it.current_y < it.last_visible_y)
17100 {
17101 struct glyph_row *row;
17102
17103 /* IT.vpos always starts from 0; it counts text lines. */
17104 nrows_scrolled = it.vpos - (start_row - MATRIX_FIRST_TEXT_ROW (w->current_matrix));
17105
17106 /* Find PT if not already found in the lines displayed. */
17107 if (w->cursor.vpos < 0)
17108 {
17109 int dy = it.current_y - start_row->y;
17110
17111 row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
17112 row = row_containing_pos (w, PT, row, NULL, dy);
17113 if (row)
17114 set_cursor_from_row (w, row, w->current_matrix, 0, 0,
17115 dy, nrows_scrolled);
17116 else
17117 {
17118 clear_glyph_matrix (w->desired_matrix);
17119 return 0;
17120 }
17121 }
17122
17123 /* Scroll the display. Do it before the current matrix is
17124 changed. The problem here is that update has not yet
17125 run, i.e. part of the current matrix is not up to date.
17126 scroll_run_hook will clear the cursor, and use the
17127 current matrix to get the height of the row the cursor is
17128 in. */
17129 run.current_y = start_row->y;
17130 run.desired_y = it.current_y;
17131 run.height = it.last_visible_y - it.current_y;
17132
17133 if (run.height > 0 && run.current_y != run.desired_y)
17134 {
17135 update_begin (f);
17136 FRAME_RIF (f)->update_window_begin_hook (w);
17137 FRAME_RIF (f)->clear_window_mouse_face (w);
17138 FRAME_RIF (f)->scroll_run_hook (w, &run);
17139 FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
17140 update_end (f);
17141 }
17142
17143 /* Shift current matrix down by nrows_scrolled lines. */
17144 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
17145 rotate_matrix (w->current_matrix,
17146 start_vpos,
17147 MATRIX_ROW_VPOS (bottom_row, w->current_matrix),
17148 nrows_scrolled);
17149
17150 /* Disable lines that must be updated. */
17151 for (i = 0; i < nrows_scrolled; ++i)
17152 (start_row + i)->enabled_p = false;
17153
17154 /* Re-compute Y positions. */
17155 min_y = WINDOW_HEADER_LINE_HEIGHT (w);
17156 max_y = it.last_visible_y;
17157 for (row = start_row + nrows_scrolled;
17158 row < bottom_row;
17159 ++row)
17160 {
17161 row->y = it.current_y;
17162 row->visible_height = row->height;
17163
17164 if (row->y < min_y)
17165 row->visible_height -= min_y - row->y;
17166 if (row->y + row->height > max_y)
17167 row->visible_height -= row->y + row->height - max_y;
17168 if (row->fringe_bitmap_periodic_p)
17169 row->redraw_fringe_bitmaps_p = 1;
17170
17171 it.current_y += row->height;
17172
17173 if (MATRIX_ROW_DISPLAYS_TEXT_P (row))
17174 last_reused_text_row = row;
17175 if (MATRIX_ROW_BOTTOM_Y (row) >= it.last_visible_y)
17176 break;
17177 }
17178
17179 /* Disable lines in the current matrix which are now
17180 below the window. */
17181 for (++row; row < bottom_row; ++row)
17182 row->enabled_p = row->mode_line_p = 0;
17183 }
17184
17185 /* Update window_end_pos etc.; last_reused_text_row is the last
17186 reused row from the current matrix containing text, if any.
17187 The value of last_text_row is the last displayed line
17188 containing text. */
17189 if (last_reused_text_row)
17190 adjust_window_ends (w, last_reused_text_row, 1);
17191 else if (last_text_row)
17192 adjust_window_ends (w, last_text_row, 0);
17193 else
17194 {
17195 /* This window must be completely empty. */
17196 w->window_end_bytepos = Z_BYTE - ZV_BYTE;
17197 w->window_end_pos = Z - ZV;
17198 w->window_end_vpos = 0;
17199 }
17200 w->window_end_valid = 0;
17201
17202 /* Update hint: don't try scrolling again in update_window. */
17203 w->desired_matrix->no_scrolling_p = 1;
17204
17205 #ifdef GLYPH_DEBUG
17206 debug_method_add (w, "try_window_reusing_current_matrix 1");
17207 #endif
17208 return 1;
17209 }
17210 else if (CHARPOS (new_start) > CHARPOS (start))
17211 {
17212 struct glyph_row *pt_row, *row;
17213 struct glyph_row *first_reusable_row;
17214 struct glyph_row *first_row_to_display;
17215 int dy;
17216 int yb = window_text_bottom_y (w);
17217
17218 /* Find the row starting at new_start, if there is one. Don't
17219 reuse a partially visible line at the end. */
17220 first_reusable_row = start_row;
17221 while (first_reusable_row->enabled_p
17222 && MATRIX_ROW_BOTTOM_Y (first_reusable_row) < yb
17223 && (MATRIX_ROW_START_CHARPOS (first_reusable_row)
17224 < CHARPOS (new_start)))
17225 ++first_reusable_row;
17226
17227 /* Give up if there is no row to reuse. */
17228 if (MATRIX_ROW_BOTTOM_Y (first_reusable_row) >= yb
17229 || !first_reusable_row->enabled_p
17230 || (MATRIX_ROW_START_CHARPOS (first_reusable_row)
17231 != CHARPOS (new_start)))
17232 return 0;
17233
17234 /* We can reuse fully visible rows beginning with
17235 first_reusable_row to the end of the window. Set
17236 first_row_to_display to the first row that cannot be reused.
17237 Set pt_row to the row containing point, if there is any. */
17238 pt_row = NULL;
17239 for (first_row_to_display = first_reusable_row;
17240 MATRIX_ROW_BOTTOM_Y (first_row_to_display) < yb;
17241 ++first_row_to_display)
17242 {
17243 if (PT >= MATRIX_ROW_START_CHARPOS (first_row_to_display)
17244 && (PT < MATRIX_ROW_END_CHARPOS (first_row_to_display)
17245 || (PT == MATRIX_ROW_END_CHARPOS (first_row_to_display)
17246 && first_row_to_display->ends_at_zv_p
17247 && pt_row == NULL)))
17248 pt_row = first_row_to_display;
17249 }
17250
17251 /* Start displaying at the start of first_row_to_display. */
17252 eassert (first_row_to_display->y < yb);
17253 init_to_row_start (&it, w, first_row_to_display);
17254
17255 nrows_scrolled = (MATRIX_ROW_VPOS (first_reusable_row, w->current_matrix)
17256 - start_vpos);
17257 it.vpos = (MATRIX_ROW_VPOS (first_row_to_display, w->current_matrix)
17258 - nrows_scrolled);
17259 it.current_y = (first_row_to_display->y - first_reusable_row->y
17260 + WINDOW_HEADER_LINE_HEIGHT (w));
17261
17262 /* Display lines beginning with first_row_to_display in the
17263 desired matrix. Set last_text_row to the last row displayed
17264 that displays text. */
17265 it.glyph_row = MATRIX_ROW (w->desired_matrix, it.vpos);
17266 if (pt_row == NULL)
17267 w->cursor.vpos = -1;
17268 last_text_row = NULL;
17269 while (it.current_y < it.last_visible_y && !f->fonts_changed)
17270 if (display_line (&it))
17271 last_text_row = it.glyph_row - 1;
17272
17273 /* If point is in a reused row, adjust y and vpos of the cursor
17274 position. */
17275 if (pt_row)
17276 {
17277 w->cursor.vpos -= nrows_scrolled;
17278 w->cursor.y -= first_reusable_row->y - start_row->y;
17279 }
17280
17281 /* Give up if point isn't in a row displayed or reused. (This
17282 also handles the case where w->cursor.vpos < nrows_scrolled
17283 after the calls to display_line, which can happen with scroll
17284 margins. See bug#1295.) */
17285 if (w->cursor.vpos < 0)
17286 {
17287 clear_glyph_matrix (w->desired_matrix);
17288 return 0;
17289 }
17290
17291 /* Scroll the display. */
17292 run.current_y = first_reusable_row->y;
17293 run.desired_y = WINDOW_HEADER_LINE_HEIGHT (w);
17294 run.height = it.last_visible_y - run.current_y;
17295 dy = run.current_y - run.desired_y;
17296
17297 if (run.height)
17298 {
17299 update_begin (f);
17300 FRAME_RIF (f)->update_window_begin_hook (w);
17301 FRAME_RIF (f)->clear_window_mouse_face (w);
17302 FRAME_RIF (f)->scroll_run_hook (w, &run);
17303 FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
17304 update_end (f);
17305 }
17306
17307 /* Adjust Y positions of reused rows. */
17308 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
17309 min_y = WINDOW_HEADER_LINE_HEIGHT (w);
17310 max_y = it.last_visible_y;
17311 for (row = first_reusable_row; row < first_row_to_display; ++row)
17312 {
17313 row->y -= dy;
17314 row->visible_height = row->height;
17315 if (row->y < min_y)
17316 row->visible_height -= min_y - row->y;
17317 if (row->y + row->height > max_y)
17318 row->visible_height -= row->y + row->height - max_y;
17319 if (row->fringe_bitmap_periodic_p)
17320 row->redraw_fringe_bitmaps_p = 1;
17321 }
17322
17323 /* Scroll the current matrix. */
17324 eassert (nrows_scrolled > 0);
17325 rotate_matrix (w->current_matrix,
17326 start_vpos,
17327 MATRIX_ROW_VPOS (bottom_row, w->current_matrix),
17328 -nrows_scrolled);
17329
17330 /* Disable rows not reused. */
17331 for (row -= nrows_scrolled; row < bottom_row; ++row)
17332 row->enabled_p = false;
17333
17334 /* Point may have moved to a different line, so we cannot assume that
17335 the previous cursor position is valid; locate the correct row. */
17336 if (pt_row)
17337 {
17338 for (row = MATRIX_ROW (w->current_matrix, w->cursor.vpos);
17339 row < bottom_row
17340 && PT >= MATRIX_ROW_END_CHARPOS (row)
17341 && !row->ends_at_zv_p;
17342 row++)
17343 {
17344 w->cursor.vpos++;
17345 w->cursor.y = row->y;
17346 }
17347 if (row < bottom_row)
17348 {
17349 /* Can't simply scan the row for point with
17350 bidi-reordered glyph rows. Let set_cursor_from_row
17351 figure out where to put the cursor, and if it fails,
17352 give up. */
17353 if (!NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering)))
17354 {
17355 if (!set_cursor_from_row (w, row, w->current_matrix,
17356 0, 0, 0, 0))
17357 {
17358 clear_glyph_matrix (w->desired_matrix);
17359 return 0;
17360 }
17361 }
17362 else
17363 {
17364 struct glyph *glyph = row->glyphs[TEXT_AREA] + w->cursor.hpos;
17365 struct glyph *end = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA];
17366
17367 for (; glyph < end
17368 && (!BUFFERP (glyph->object)
17369 || glyph->charpos < PT);
17370 glyph++)
17371 {
17372 w->cursor.hpos++;
17373 w->cursor.x += glyph->pixel_width;
17374 }
17375 }
17376 }
17377 }
17378
17379 /* Adjust window end. A null value of last_text_row means that
17380 the window end is in reused rows which in turn means that
17381 only its vpos can have changed. */
17382 if (last_text_row)
17383 adjust_window_ends (w, last_text_row, 0);
17384 else
17385 w->window_end_vpos -= nrows_scrolled;
17386
17387 w->window_end_valid = 0;
17388 w->desired_matrix->no_scrolling_p = 1;
17389
17390 #ifdef GLYPH_DEBUG
17391 debug_method_add (w, "try_window_reusing_current_matrix 2");
17392 #endif
17393 return 1;
17394 }
17395
17396 return 0;
17397 }
17398
17399
17400 \f
17401 /************************************************************************
17402 Window redisplay reusing current matrix when buffer has changed
17403 ************************************************************************/
17404
17405 static struct glyph_row *find_last_unchanged_at_beg_row (struct window *);
17406 static struct glyph_row *find_first_unchanged_at_end_row (struct window *,
17407 ptrdiff_t *, ptrdiff_t *);
17408 static struct glyph_row *
17409 find_last_row_displaying_text (struct glyph_matrix *, struct it *,
17410 struct glyph_row *);
17411
17412
17413 /* Return the last row in MATRIX displaying text. If row START is
17414 non-null, start searching with that row. IT gives the dimensions
17415 of the display. Value is null if matrix is empty; otherwise it is
17416 a pointer to the row found. */
17417
17418 static struct glyph_row *
17419 find_last_row_displaying_text (struct glyph_matrix *matrix, struct it *it,
17420 struct glyph_row *start)
17421 {
17422 struct glyph_row *row, *row_found;
17423
17424 /* Set row_found to the last row in IT->w's current matrix
17425 displaying text. The loop looks funny but think of partially
17426 visible lines. */
17427 row_found = NULL;
17428 row = start ? start : MATRIX_FIRST_TEXT_ROW (matrix);
17429 while (MATRIX_ROW_DISPLAYS_TEXT_P (row))
17430 {
17431 eassert (row->enabled_p);
17432 row_found = row;
17433 if (MATRIX_ROW_BOTTOM_Y (row) >= it->last_visible_y)
17434 break;
17435 ++row;
17436 }
17437
17438 return row_found;
17439 }
17440
17441
17442 /* Return the last row in the current matrix of W that is not affected
17443 by changes at the start of current_buffer that occurred since W's
17444 current matrix was built. Value is null if no such row exists.
17445
17446 BEG_UNCHANGED us the number of characters unchanged at the start of
17447 current_buffer. BEG + BEG_UNCHANGED is the buffer position of the
17448 first changed character in current_buffer. Characters at positions <
17449 BEG + BEG_UNCHANGED are at the same buffer positions as they were
17450 when the current matrix was built. */
17451
17452 static struct glyph_row *
17453 find_last_unchanged_at_beg_row (struct window *w)
17454 {
17455 ptrdiff_t first_changed_pos = BEG + BEG_UNCHANGED;
17456 struct glyph_row *row;
17457 struct glyph_row *row_found = NULL;
17458 int yb = window_text_bottom_y (w);
17459
17460 /* Find the last row displaying unchanged text. */
17461 for (row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
17462 MATRIX_ROW_DISPLAYS_TEXT_P (row)
17463 && MATRIX_ROW_START_CHARPOS (row) < first_changed_pos;
17464 ++row)
17465 {
17466 if (/* If row ends before first_changed_pos, it is unchanged,
17467 except in some case. */
17468 MATRIX_ROW_END_CHARPOS (row) <= first_changed_pos
17469 /* When row ends in ZV and we write at ZV it is not
17470 unchanged. */
17471 && !row->ends_at_zv_p
17472 /* When first_changed_pos is the end of a continued line,
17473 row is not unchanged because it may be no longer
17474 continued. */
17475 && !(MATRIX_ROW_END_CHARPOS (row) == first_changed_pos
17476 && (row->continued_p
17477 || row->exact_window_width_line_p))
17478 /* If ROW->end is beyond ZV, then ROW->end is outdated and
17479 needs to be recomputed, so don't consider this row as
17480 unchanged. This happens when the last line was
17481 bidi-reordered and was killed immediately before this
17482 redisplay cycle. In that case, ROW->end stores the
17483 buffer position of the first visual-order character of
17484 the killed text, which is now beyond ZV. */
17485 && CHARPOS (row->end.pos) <= ZV)
17486 row_found = row;
17487
17488 /* Stop if last visible row. */
17489 if (MATRIX_ROW_BOTTOM_Y (row) >= yb)
17490 break;
17491 }
17492
17493 return row_found;
17494 }
17495
17496
17497 /* Find the first glyph row in the current matrix of W that is not
17498 affected by changes at the end of current_buffer since the
17499 time W's current matrix was built.
17500
17501 Return in *DELTA the number of chars by which buffer positions in
17502 unchanged text at the end of current_buffer must be adjusted.
17503
17504 Return in *DELTA_BYTES the corresponding number of bytes.
17505
17506 Value is null if no such row exists, i.e. all rows are affected by
17507 changes. */
17508
17509 static struct glyph_row *
17510 find_first_unchanged_at_end_row (struct window *w,
17511 ptrdiff_t *delta, ptrdiff_t *delta_bytes)
17512 {
17513 struct glyph_row *row;
17514 struct glyph_row *row_found = NULL;
17515
17516 *delta = *delta_bytes = 0;
17517
17518 /* Display must not have been paused, otherwise the current matrix
17519 is not up to date. */
17520 eassert (w->window_end_valid);
17521
17522 /* A value of window_end_pos >= END_UNCHANGED means that the window
17523 end is in the range of changed text. If so, there is no
17524 unchanged row at the end of W's current matrix. */
17525 if (w->window_end_pos >= END_UNCHANGED)
17526 return NULL;
17527
17528 /* Set row to the last row in W's current matrix displaying text. */
17529 row = MATRIX_ROW (w->current_matrix, w->window_end_vpos);
17530
17531 /* If matrix is entirely empty, no unchanged row exists. */
17532 if (MATRIX_ROW_DISPLAYS_TEXT_P (row))
17533 {
17534 /* The value of row is the last glyph row in the matrix having a
17535 meaningful buffer position in it. The end position of row
17536 corresponds to window_end_pos. This allows us to translate
17537 buffer positions in the current matrix to current buffer
17538 positions for characters not in changed text. */
17539 ptrdiff_t Z_old =
17540 MATRIX_ROW_END_CHARPOS (row) + w->window_end_pos;
17541 ptrdiff_t Z_BYTE_old =
17542 MATRIX_ROW_END_BYTEPOS (row) + w->window_end_bytepos;
17543 ptrdiff_t last_unchanged_pos, last_unchanged_pos_old;
17544 struct glyph_row *first_text_row
17545 = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
17546
17547 *delta = Z - Z_old;
17548 *delta_bytes = Z_BYTE - Z_BYTE_old;
17549
17550 /* Set last_unchanged_pos to the buffer position of the last
17551 character in the buffer that has not been changed. Z is the
17552 index + 1 of the last character in current_buffer, i.e. by
17553 subtracting END_UNCHANGED we get the index of the last
17554 unchanged character, and we have to add BEG to get its buffer
17555 position. */
17556 last_unchanged_pos = Z - END_UNCHANGED + BEG;
17557 last_unchanged_pos_old = last_unchanged_pos - *delta;
17558
17559 /* Search backward from ROW for a row displaying a line that
17560 starts at a minimum position >= last_unchanged_pos_old. */
17561 for (; row > first_text_row; --row)
17562 {
17563 /* This used to abort, but it can happen.
17564 It is ok to just stop the search instead here. KFS. */
17565 if (!row->enabled_p || !MATRIX_ROW_DISPLAYS_TEXT_P (row))
17566 break;
17567
17568 if (MATRIX_ROW_START_CHARPOS (row) >= last_unchanged_pos_old)
17569 row_found = row;
17570 }
17571 }
17572
17573 eassert (!row_found || MATRIX_ROW_DISPLAYS_TEXT_P (row_found));
17574
17575 return row_found;
17576 }
17577
17578
17579 /* Make sure that glyph rows in the current matrix of window W
17580 reference the same glyph memory as corresponding rows in the
17581 frame's frame matrix. This function is called after scrolling W's
17582 current matrix on a terminal frame in try_window_id and
17583 try_window_reusing_current_matrix. */
17584
17585 static void
17586 sync_frame_with_window_matrix_rows (struct window *w)
17587 {
17588 struct frame *f = XFRAME (w->frame);
17589 struct glyph_row *window_row, *window_row_end, *frame_row;
17590
17591 /* Preconditions: W must be a leaf window and full-width. Its frame
17592 must have a frame matrix. */
17593 eassert (BUFFERP (w->contents));
17594 eassert (WINDOW_FULL_WIDTH_P (w));
17595 eassert (!FRAME_WINDOW_P (f));
17596
17597 /* If W is a full-width window, glyph pointers in W's current matrix
17598 have, by definition, to be the same as glyph pointers in the
17599 corresponding frame matrix. Note that frame matrices have no
17600 marginal areas (see build_frame_matrix). */
17601 window_row = w->current_matrix->rows;
17602 window_row_end = window_row + w->current_matrix->nrows;
17603 frame_row = f->current_matrix->rows + WINDOW_TOP_EDGE_LINE (w);
17604 while (window_row < window_row_end)
17605 {
17606 struct glyph *start = window_row->glyphs[LEFT_MARGIN_AREA];
17607 struct glyph *end = window_row->glyphs[LAST_AREA];
17608
17609 frame_row->glyphs[LEFT_MARGIN_AREA] = start;
17610 frame_row->glyphs[TEXT_AREA] = start;
17611 frame_row->glyphs[RIGHT_MARGIN_AREA] = end;
17612 frame_row->glyphs[LAST_AREA] = end;
17613
17614 /* Disable frame rows whose corresponding window rows have
17615 been disabled in try_window_id. */
17616 if (!window_row->enabled_p)
17617 frame_row->enabled_p = false;
17618
17619 ++window_row, ++frame_row;
17620 }
17621 }
17622
17623
17624 /* Find the glyph row in window W containing CHARPOS. Consider all
17625 rows between START and END (not inclusive). END null means search
17626 all rows to the end of the display area of W. Value is the row
17627 containing CHARPOS or null. */
17628
17629 struct glyph_row *
17630 row_containing_pos (struct window *w, ptrdiff_t charpos,
17631 struct glyph_row *start, struct glyph_row *end, int dy)
17632 {
17633 struct glyph_row *row = start;
17634 struct glyph_row *best_row = NULL;
17635 ptrdiff_t mindif = BUF_ZV (XBUFFER (w->contents)) + 1;
17636 int last_y;
17637
17638 /* If we happen to start on a header-line, skip that. */
17639 if (row->mode_line_p)
17640 ++row;
17641
17642 if ((end && row >= end) || !row->enabled_p)
17643 return NULL;
17644
17645 last_y = window_text_bottom_y (w) - dy;
17646
17647 while (1)
17648 {
17649 /* Give up if we have gone too far. */
17650 if (end && row >= end)
17651 return NULL;
17652 /* This formerly returned if they were equal.
17653 I think that both quantities are of a "last plus one" type;
17654 if so, when they are equal, the row is within the screen. -- rms. */
17655 if (MATRIX_ROW_BOTTOM_Y (row) > last_y)
17656 return NULL;
17657
17658 /* If it is in this row, return this row. */
17659 if (! (MATRIX_ROW_END_CHARPOS (row) < charpos
17660 || (MATRIX_ROW_END_CHARPOS (row) == charpos
17661 /* The end position of a row equals the start
17662 position of the next row. If CHARPOS is there, we
17663 would rather consider it displayed in the next
17664 line, except when this line ends in ZV. */
17665 && !row_for_charpos_p (row, charpos)))
17666 && charpos >= MATRIX_ROW_START_CHARPOS (row))
17667 {
17668 struct glyph *g;
17669
17670 if (NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering))
17671 || (!best_row && !row->continued_p))
17672 return row;
17673 /* In bidi-reordered rows, there could be several rows whose
17674 edges surround CHARPOS, all of these rows belonging to
17675 the same continued line. We need to find the row which
17676 fits CHARPOS the best. */
17677 for (g = row->glyphs[TEXT_AREA];
17678 g < row->glyphs[TEXT_AREA] + row->used[TEXT_AREA];
17679 g++)
17680 {
17681 if (!STRINGP (g->object))
17682 {
17683 if (g->charpos > 0 && eabs (g->charpos - charpos) < mindif)
17684 {
17685 mindif = eabs (g->charpos - charpos);
17686 best_row = row;
17687 /* Exact match always wins. */
17688 if (mindif == 0)
17689 return best_row;
17690 }
17691 }
17692 }
17693 }
17694 else if (best_row && !row->continued_p)
17695 return best_row;
17696 ++row;
17697 }
17698 }
17699
17700
17701 /* Try to redisplay window W by reusing its existing display. W's
17702 current matrix must be up to date when this function is called,
17703 i.e. window_end_valid must be nonzero.
17704
17705 Value is
17706
17707 >= 1 if successful, i.e. display has been updated
17708 specifically:
17709 1 means the changes were in front of a newline that precedes
17710 the window start, and the whole current matrix was reused
17711 2 means the changes were after the last position displayed
17712 in the window, and the whole current matrix was reused
17713 3 means portions of the current matrix were reused, while
17714 some of the screen lines were redrawn
17715 -1 if redisplay with same window start is known not to succeed
17716 0 if otherwise unsuccessful
17717
17718 The following steps are performed:
17719
17720 1. Find the last row in the current matrix of W that is not
17721 affected by changes at the start of current_buffer. If no such row
17722 is found, give up.
17723
17724 2. Find the first row in W's current matrix that is not affected by
17725 changes at the end of current_buffer. Maybe there is no such row.
17726
17727 3. Display lines beginning with the row + 1 found in step 1 to the
17728 row found in step 2 or, if step 2 didn't find a row, to the end of
17729 the window.
17730
17731 4. If cursor is not known to appear on the window, give up.
17732
17733 5. If display stopped at the row found in step 2, scroll the
17734 display and current matrix as needed.
17735
17736 6. Maybe display some lines at the end of W, if we must. This can
17737 happen under various circumstances, like a partially visible line
17738 becoming fully visible, or because newly displayed lines are displayed
17739 in smaller font sizes.
17740
17741 7. Update W's window end information. */
17742
17743 static int
17744 try_window_id (struct window *w)
17745 {
17746 struct frame *f = XFRAME (w->frame);
17747 struct glyph_matrix *current_matrix = w->current_matrix;
17748 struct glyph_matrix *desired_matrix = w->desired_matrix;
17749 struct glyph_row *last_unchanged_at_beg_row;
17750 struct glyph_row *first_unchanged_at_end_row;
17751 struct glyph_row *row;
17752 struct glyph_row *bottom_row;
17753 int bottom_vpos;
17754 struct it it;
17755 ptrdiff_t delta = 0, delta_bytes = 0, stop_pos;
17756 int dvpos, dy;
17757 struct text_pos start_pos;
17758 struct run run;
17759 int first_unchanged_at_end_vpos = 0;
17760 struct glyph_row *last_text_row, *last_text_row_at_end;
17761 struct text_pos start;
17762 ptrdiff_t first_changed_charpos, last_changed_charpos;
17763
17764 #ifdef GLYPH_DEBUG
17765 if (inhibit_try_window_id)
17766 return 0;
17767 #endif
17768
17769 /* This is handy for debugging. */
17770 #if 0
17771 #define GIVE_UP(X) \
17772 do { \
17773 fprintf (stderr, "try_window_id give up %d\n", (X)); \
17774 return 0; \
17775 } while (0)
17776 #else
17777 #define GIVE_UP(X) return 0
17778 #endif
17779
17780 SET_TEXT_POS_FROM_MARKER (start, w->start);
17781
17782 /* Don't use this for mini-windows because these can show
17783 messages and mini-buffers, and we don't handle that here. */
17784 if (MINI_WINDOW_P (w))
17785 GIVE_UP (1);
17786
17787 /* This flag is used to prevent redisplay optimizations. */
17788 if (windows_or_buffers_changed || f->cursor_type_changed)
17789 GIVE_UP (2);
17790
17791 /* This function's optimizations cannot be used if overlays have
17792 changed in the buffer displayed by the window, so give up if they
17793 have. */
17794 if (w->last_overlay_modified != OVERLAY_MODIFF)
17795 GIVE_UP (21);
17796
17797 /* Verify that narrowing has not changed.
17798 Also verify that we were not told to prevent redisplay optimizations.
17799 It would be nice to further
17800 reduce the number of cases where this prevents try_window_id. */
17801 if (current_buffer->clip_changed
17802 || current_buffer->prevent_redisplay_optimizations_p)
17803 GIVE_UP (3);
17804
17805 /* Window must either use window-based redisplay or be full width. */
17806 if (!FRAME_WINDOW_P (f)
17807 && (!FRAME_LINE_INS_DEL_OK (f)
17808 || !WINDOW_FULL_WIDTH_P (w)))
17809 GIVE_UP (4);
17810
17811 /* Give up if point is known NOT to appear in W. */
17812 if (PT < CHARPOS (start))
17813 GIVE_UP (5);
17814
17815 /* Another way to prevent redisplay optimizations. */
17816 if (w->last_modified == 0)
17817 GIVE_UP (6);
17818
17819 /* Verify that window is not hscrolled. */
17820 if (w->hscroll != 0)
17821 GIVE_UP (7);
17822
17823 /* Verify that display wasn't paused. */
17824 if (!w->window_end_valid)
17825 GIVE_UP (8);
17826
17827 /* Likewise if highlighting trailing whitespace. */
17828 if (!NILP (Vshow_trailing_whitespace))
17829 GIVE_UP (11);
17830
17831 /* Can't use this if overlay arrow position and/or string have
17832 changed. */
17833 if (overlay_arrows_changed_p ())
17834 GIVE_UP (12);
17835
17836 /* When word-wrap is on, adding a space to the first word of a
17837 wrapped line can change the wrap position, altering the line
17838 above it. It might be worthwhile to handle this more
17839 intelligently, but for now just redisplay from scratch. */
17840 if (!NILP (BVAR (XBUFFER (w->contents), word_wrap)))
17841 GIVE_UP (21);
17842
17843 /* Under bidi reordering, adding or deleting a character in the
17844 beginning of a paragraph, before the first strong directional
17845 character, can change the base direction of the paragraph (unless
17846 the buffer specifies a fixed paragraph direction), which will
17847 require to redisplay the whole paragraph. It might be worthwhile
17848 to find the paragraph limits and widen the range of redisplayed
17849 lines to that, but for now just give up this optimization and
17850 redisplay from scratch. */
17851 if (!NILP (BVAR (XBUFFER (w->contents), bidi_display_reordering))
17852 && NILP (BVAR (XBUFFER (w->contents), bidi_paragraph_direction)))
17853 GIVE_UP (22);
17854
17855 /* Make sure beg_unchanged and end_unchanged are up to date. Do it
17856 only if buffer has really changed. The reason is that the gap is
17857 initially at Z for freshly visited files. The code below would
17858 set end_unchanged to 0 in that case. */
17859 if (MODIFF > SAVE_MODIFF
17860 /* This seems to happen sometimes after saving a buffer. */
17861 || BEG_UNCHANGED + END_UNCHANGED > Z_BYTE)
17862 {
17863 if (GPT - BEG < BEG_UNCHANGED)
17864 BEG_UNCHANGED = GPT - BEG;
17865 if (Z - GPT < END_UNCHANGED)
17866 END_UNCHANGED = Z - GPT;
17867 }
17868
17869 /* The position of the first and last character that has been changed. */
17870 first_changed_charpos = BEG + BEG_UNCHANGED;
17871 last_changed_charpos = Z - END_UNCHANGED;
17872
17873 /* If window starts after a line end, and the last change is in
17874 front of that newline, then changes don't affect the display.
17875 This case happens with stealth-fontification. Note that although
17876 the display is unchanged, glyph positions in the matrix have to
17877 be adjusted, of course. */
17878 row = MATRIX_ROW (w->current_matrix, w->window_end_vpos);
17879 if (MATRIX_ROW_DISPLAYS_TEXT_P (row)
17880 && ((last_changed_charpos < CHARPOS (start)
17881 && CHARPOS (start) == BEGV)
17882 || (last_changed_charpos < CHARPOS (start) - 1
17883 && FETCH_BYTE (BYTEPOS (start) - 1) == '\n')))
17884 {
17885 ptrdiff_t Z_old, Z_delta, Z_BYTE_old, Z_delta_bytes;
17886 struct glyph_row *r0;
17887
17888 /* Compute how many chars/bytes have been added to or removed
17889 from the buffer. */
17890 Z_old = MATRIX_ROW_END_CHARPOS (row) + w->window_end_pos;
17891 Z_BYTE_old = MATRIX_ROW_END_BYTEPOS (row) + w->window_end_bytepos;
17892 Z_delta = Z - Z_old;
17893 Z_delta_bytes = Z_BYTE - Z_BYTE_old;
17894
17895 /* Give up if PT is not in the window. Note that it already has
17896 been checked at the start of try_window_id that PT is not in
17897 front of the window start. */
17898 if (PT >= MATRIX_ROW_END_CHARPOS (row) + Z_delta)
17899 GIVE_UP (13);
17900
17901 /* If window start is unchanged, we can reuse the whole matrix
17902 as is, after adjusting glyph positions. No need to compute
17903 the window end again, since its offset from Z hasn't changed. */
17904 r0 = MATRIX_FIRST_TEXT_ROW (current_matrix);
17905 if (CHARPOS (start) == MATRIX_ROW_START_CHARPOS (r0) + Z_delta
17906 && BYTEPOS (start) == MATRIX_ROW_START_BYTEPOS (r0) + Z_delta_bytes
17907 /* PT must not be in a partially visible line. */
17908 && !(PT >= MATRIX_ROW_START_CHARPOS (row) + Z_delta
17909 && MATRIX_ROW_BOTTOM_Y (row) > window_text_bottom_y (w)))
17910 {
17911 /* Adjust positions in the glyph matrix. */
17912 if (Z_delta || Z_delta_bytes)
17913 {
17914 struct glyph_row *r1
17915 = MATRIX_BOTTOM_TEXT_ROW (current_matrix, w);
17916 increment_matrix_positions (w->current_matrix,
17917 MATRIX_ROW_VPOS (r0, current_matrix),
17918 MATRIX_ROW_VPOS (r1, current_matrix),
17919 Z_delta, Z_delta_bytes);
17920 }
17921
17922 /* Set the cursor. */
17923 row = row_containing_pos (w, PT, r0, NULL, 0);
17924 if (row)
17925 set_cursor_from_row (w, row, current_matrix, 0, 0, 0, 0);
17926 return 1;
17927 }
17928 }
17929
17930 /* Handle the case that changes are all below what is displayed in
17931 the window, and that PT is in the window. This shortcut cannot
17932 be taken if ZV is visible in the window, and text has been added
17933 there that is visible in the window. */
17934 if (first_changed_charpos >= MATRIX_ROW_END_CHARPOS (row)
17935 /* ZV is not visible in the window, or there are no
17936 changes at ZV, actually. */
17937 && (current_matrix->zv > MATRIX_ROW_END_CHARPOS (row)
17938 || first_changed_charpos == last_changed_charpos))
17939 {
17940 struct glyph_row *r0;
17941
17942 /* Give up if PT is not in the window. Note that it already has
17943 been checked at the start of try_window_id that PT is not in
17944 front of the window start. */
17945 if (PT >= MATRIX_ROW_END_CHARPOS (row))
17946 GIVE_UP (14);
17947
17948 /* If window start is unchanged, we can reuse the whole matrix
17949 as is, without changing glyph positions since no text has
17950 been added/removed in front of the window end. */
17951 r0 = MATRIX_FIRST_TEXT_ROW (current_matrix);
17952 if (TEXT_POS_EQUAL_P (start, r0->minpos)
17953 /* PT must not be in a partially visible line. */
17954 && !(PT >= MATRIX_ROW_START_CHARPOS (row)
17955 && MATRIX_ROW_BOTTOM_Y (row) > window_text_bottom_y (w)))
17956 {
17957 /* We have to compute the window end anew since text
17958 could have been added/removed after it. */
17959 w->window_end_pos = Z - MATRIX_ROW_END_CHARPOS (row);
17960 w->window_end_bytepos = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
17961
17962 /* Set the cursor. */
17963 row = row_containing_pos (w, PT, r0, NULL, 0);
17964 if (row)
17965 set_cursor_from_row (w, row, current_matrix, 0, 0, 0, 0);
17966 return 2;
17967 }
17968 }
17969
17970 /* Give up if window start is in the changed area.
17971
17972 The condition used to read
17973
17974 (BEG_UNCHANGED + END_UNCHANGED != Z - BEG && ...)
17975
17976 but why that was tested escapes me at the moment. */
17977 if (CHARPOS (start) >= first_changed_charpos
17978 && CHARPOS (start) <= last_changed_charpos)
17979 GIVE_UP (15);
17980
17981 /* Check that window start agrees with the start of the first glyph
17982 row in its current matrix. Check this after we know the window
17983 start is not in changed text, otherwise positions would not be
17984 comparable. */
17985 row = MATRIX_FIRST_TEXT_ROW (current_matrix);
17986 if (!TEXT_POS_EQUAL_P (start, row->minpos))
17987 GIVE_UP (16);
17988
17989 /* Give up if the window ends in strings. Overlay strings
17990 at the end are difficult to handle, so don't try. */
17991 row = MATRIX_ROW (current_matrix, w->window_end_vpos);
17992 if (MATRIX_ROW_START_CHARPOS (row) == MATRIX_ROW_END_CHARPOS (row))
17993 GIVE_UP (20);
17994
17995 /* Compute the position at which we have to start displaying new
17996 lines. Some of the lines at the top of the window might be
17997 reusable because they are not displaying changed text. Find the
17998 last row in W's current matrix not affected by changes at the
17999 start of current_buffer. Value is null if changes start in the
18000 first line of window. */
18001 last_unchanged_at_beg_row = find_last_unchanged_at_beg_row (w);
18002 if (last_unchanged_at_beg_row)
18003 {
18004 /* Avoid starting to display in the middle of a character, a TAB
18005 for instance. This is easier than to set up the iterator
18006 exactly, and it's not a frequent case, so the additional
18007 effort wouldn't really pay off. */
18008 while ((MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (last_unchanged_at_beg_row)
18009 || last_unchanged_at_beg_row->ends_in_newline_from_string_p)
18010 && last_unchanged_at_beg_row > w->current_matrix->rows)
18011 --last_unchanged_at_beg_row;
18012
18013 if (MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (last_unchanged_at_beg_row))
18014 GIVE_UP (17);
18015
18016 if (init_to_row_end (&it, w, last_unchanged_at_beg_row) == 0)
18017 GIVE_UP (18);
18018 start_pos = it.current.pos;
18019
18020 /* Start displaying new lines in the desired matrix at the same
18021 vpos we would use in the current matrix, i.e. below
18022 last_unchanged_at_beg_row. */
18023 it.vpos = 1 + MATRIX_ROW_VPOS (last_unchanged_at_beg_row,
18024 current_matrix);
18025 it.glyph_row = MATRIX_ROW (desired_matrix, it.vpos);
18026 it.current_y = MATRIX_ROW_BOTTOM_Y (last_unchanged_at_beg_row);
18027
18028 eassert (it.hpos == 0 && it.current_x == 0);
18029 }
18030 else
18031 {
18032 /* There are no reusable lines at the start of the window.
18033 Start displaying in the first text line. */
18034 start_display (&it, w, start);
18035 it.vpos = it.first_vpos;
18036 start_pos = it.current.pos;
18037 }
18038
18039 /* Find the first row that is not affected by changes at the end of
18040 the buffer. Value will be null if there is no unchanged row, in
18041 which case we must redisplay to the end of the window. delta
18042 will be set to the value by which buffer positions beginning with
18043 first_unchanged_at_end_row have to be adjusted due to text
18044 changes. */
18045 first_unchanged_at_end_row
18046 = find_first_unchanged_at_end_row (w, &delta, &delta_bytes);
18047 IF_DEBUG (debug_delta = delta);
18048 IF_DEBUG (debug_delta_bytes = delta_bytes);
18049
18050 /* Set stop_pos to the buffer position up to which we will have to
18051 display new lines. If first_unchanged_at_end_row != NULL, this
18052 is the buffer position of the start of the line displayed in that
18053 row. For first_unchanged_at_end_row == NULL, use 0 to indicate
18054 that we don't stop at a buffer position. */
18055 stop_pos = 0;
18056 if (first_unchanged_at_end_row)
18057 {
18058 eassert (last_unchanged_at_beg_row == NULL
18059 || first_unchanged_at_end_row >= last_unchanged_at_beg_row);
18060
18061 /* If this is a continuation line, move forward to the next one
18062 that isn't. Changes in lines above affect this line.
18063 Caution: this may move first_unchanged_at_end_row to a row
18064 not displaying text. */
18065 while (MATRIX_ROW_CONTINUATION_LINE_P (first_unchanged_at_end_row)
18066 && MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row)
18067 && (MATRIX_ROW_BOTTOM_Y (first_unchanged_at_end_row)
18068 < it.last_visible_y))
18069 ++first_unchanged_at_end_row;
18070
18071 if (!MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row)
18072 || (MATRIX_ROW_BOTTOM_Y (first_unchanged_at_end_row)
18073 >= it.last_visible_y))
18074 first_unchanged_at_end_row = NULL;
18075 else
18076 {
18077 stop_pos = (MATRIX_ROW_START_CHARPOS (first_unchanged_at_end_row)
18078 + delta);
18079 first_unchanged_at_end_vpos
18080 = MATRIX_ROW_VPOS (first_unchanged_at_end_row, current_matrix);
18081 eassert (stop_pos >= Z - END_UNCHANGED);
18082 }
18083 }
18084 else if (last_unchanged_at_beg_row == NULL)
18085 GIVE_UP (19);
18086
18087
18088 #ifdef GLYPH_DEBUG
18089
18090 /* Either there is no unchanged row at the end, or the one we have
18091 now displays text. This is a necessary condition for the window
18092 end pos calculation at the end of this function. */
18093 eassert (first_unchanged_at_end_row == NULL
18094 || MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row));
18095
18096 debug_last_unchanged_at_beg_vpos
18097 = (last_unchanged_at_beg_row
18098 ? MATRIX_ROW_VPOS (last_unchanged_at_beg_row, current_matrix)
18099 : -1);
18100 debug_first_unchanged_at_end_vpos = first_unchanged_at_end_vpos;
18101
18102 #endif /* GLYPH_DEBUG */
18103
18104
18105 /* Display new lines. Set last_text_row to the last new line
18106 displayed which has text on it, i.e. might end up as being the
18107 line where the window_end_vpos is. */
18108 w->cursor.vpos = -1;
18109 last_text_row = NULL;
18110 overlay_arrow_seen = 0;
18111 if (it.current_y < it.last_visible_y
18112 && !f->fonts_changed
18113 && (first_unchanged_at_end_row == NULL
18114 || IT_CHARPOS (it) < stop_pos))
18115 it.glyph_row->reversed_p = false;
18116 while (it.current_y < it.last_visible_y
18117 && !f->fonts_changed
18118 && (first_unchanged_at_end_row == NULL
18119 || IT_CHARPOS (it) < stop_pos))
18120 {
18121 if (display_line (&it))
18122 last_text_row = it.glyph_row - 1;
18123 }
18124
18125 if (f->fonts_changed)
18126 return -1;
18127
18128 /* The redisplay iterations in display_line above could have
18129 triggered font-lock, which could have done something that
18130 invalidates IT->w window's end-point information, on which we
18131 rely below. E.g., one package, which will remain unnamed, used
18132 to install a font-lock-fontify-region-function that called
18133 bury-buffer, whose side effect is to switch the buffer displayed
18134 by IT->w, and that predictably resets IT->w's window_end_valid
18135 flag, which we already tested at the entry to this function.
18136 Amply punish such packages/modes by giving up on this
18137 optimization in those cases. */
18138 if (!w->window_end_valid)
18139 {
18140 clear_glyph_matrix (w->desired_matrix);
18141 return -1;
18142 }
18143
18144 /* Compute differences in buffer positions, y-positions etc. for
18145 lines reused at the bottom of the window. Compute what we can
18146 scroll. */
18147 if (first_unchanged_at_end_row
18148 /* No lines reused because we displayed everything up to the
18149 bottom of the window. */
18150 && it.current_y < it.last_visible_y)
18151 {
18152 dvpos = (it.vpos
18153 - MATRIX_ROW_VPOS (first_unchanged_at_end_row,
18154 current_matrix));
18155 dy = it.current_y - first_unchanged_at_end_row->y;
18156 run.current_y = first_unchanged_at_end_row->y;
18157 run.desired_y = run.current_y + dy;
18158 run.height = it.last_visible_y - max (run.current_y, run.desired_y);
18159 }
18160 else
18161 {
18162 delta = delta_bytes = dvpos = dy
18163 = run.current_y = run.desired_y = run.height = 0;
18164 first_unchanged_at_end_row = NULL;
18165 }
18166 IF_DEBUG ((debug_dvpos = dvpos, debug_dy = dy));
18167
18168
18169 /* Find the cursor if not already found. We have to decide whether
18170 PT will appear on this window (it sometimes doesn't, but this is
18171 not a very frequent case.) This decision has to be made before
18172 the current matrix is altered. A value of cursor.vpos < 0 means
18173 that PT is either in one of the lines beginning at
18174 first_unchanged_at_end_row or below the window. Don't care for
18175 lines that might be displayed later at the window end; as
18176 mentioned, this is not a frequent case. */
18177 if (w->cursor.vpos < 0)
18178 {
18179 /* Cursor in unchanged rows at the top? */
18180 if (PT < CHARPOS (start_pos)
18181 && last_unchanged_at_beg_row)
18182 {
18183 row = row_containing_pos (w, PT,
18184 MATRIX_FIRST_TEXT_ROW (w->current_matrix),
18185 last_unchanged_at_beg_row + 1, 0);
18186 if (row)
18187 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
18188 }
18189
18190 /* Start from first_unchanged_at_end_row looking for PT. */
18191 else if (first_unchanged_at_end_row)
18192 {
18193 row = row_containing_pos (w, PT - delta,
18194 first_unchanged_at_end_row, NULL, 0);
18195 if (row)
18196 set_cursor_from_row (w, row, w->current_matrix, delta,
18197 delta_bytes, dy, dvpos);
18198 }
18199
18200 /* Give up if cursor was not found. */
18201 if (w->cursor.vpos < 0)
18202 {
18203 clear_glyph_matrix (w->desired_matrix);
18204 return -1;
18205 }
18206 }
18207
18208 /* Don't let the cursor end in the scroll margins. */
18209 {
18210 int this_scroll_margin, cursor_height;
18211 int frame_line_height = default_line_pixel_height (w);
18212 int window_total_lines
18213 = WINDOW_TOTAL_LINES (w) * FRAME_LINE_HEIGHT (it.f) / frame_line_height;
18214
18215 this_scroll_margin =
18216 max (0, min (scroll_margin, window_total_lines / 4));
18217 this_scroll_margin *= frame_line_height;
18218 cursor_height = MATRIX_ROW (w->desired_matrix, w->cursor.vpos)->height;
18219
18220 if ((w->cursor.y < this_scroll_margin
18221 && CHARPOS (start) > BEGV)
18222 /* Old redisplay didn't take scroll margin into account at the bottom,
18223 but then global-hl-line-mode doesn't scroll. KFS 2004-06-14 */
18224 || (w->cursor.y + (make_cursor_line_fully_visible_p
18225 ? cursor_height + this_scroll_margin
18226 : 1)) > it.last_visible_y)
18227 {
18228 w->cursor.vpos = -1;
18229 clear_glyph_matrix (w->desired_matrix);
18230 return -1;
18231 }
18232 }
18233
18234 /* Scroll the display. Do it before changing the current matrix so
18235 that xterm.c doesn't get confused about where the cursor glyph is
18236 found. */
18237 if (dy && run.height)
18238 {
18239 update_begin (f);
18240
18241 if (FRAME_WINDOW_P (f))
18242 {
18243 FRAME_RIF (f)->update_window_begin_hook (w);
18244 FRAME_RIF (f)->clear_window_mouse_face (w);
18245 FRAME_RIF (f)->scroll_run_hook (w, &run);
18246 FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
18247 }
18248 else
18249 {
18250 /* Terminal frame. In this case, dvpos gives the number of
18251 lines to scroll by; dvpos < 0 means scroll up. */
18252 int from_vpos
18253 = MATRIX_ROW_VPOS (first_unchanged_at_end_row, w->current_matrix);
18254 int from = WINDOW_TOP_EDGE_LINE (w) + from_vpos;
18255 int end = (WINDOW_TOP_EDGE_LINE (w)
18256 + (WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0)
18257 + window_internal_height (w));
18258
18259 #if defined (HAVE_GPM) || defined (MSDOS)
18260 x_clear_window_mouse_face (w);
18261 #endif
18262 /* Perform the operation on the screen. */
18263 if (dvpos > 0)
18264 {
18265 /* Scroll last_unchanged_at_beg_row to the end of the
18266 window down dvpos lines. */
18267 set_terminal_window (f, end);
18268
18269 /* On dumb terminals delete dvpos lines at the end
18270 before inserting dvpos empty lines. */
18271 if (!FRAME_SCROLL_REGION_OK (f))
18272 ins_del_lines (f, end - dvpos, -dvpos);
18273
18274 /* Insert dvpos empty lines in front of
18275 last_unchanged_at_beg_row. */
18276 ins_del_lines (f, from, dvpos);
18277 }
18278 else if (dvpos < 0)
18279 {
18280 /* Scroll up last_unchanged_at_beg_vpos to the end of
18281 the window to last_unchanged_at_beg_vpos - |dvpos|. */
18282 set_terminal_window (f, end);
18283
18284 /* Delete dvpos lines in front of
18285 last_unchanged_at_beg_vpos. ins_del_lines will set
18286 the cursor to the given vpos and emit |dvpos| delete
18287 line sequences. */
18288 ins_del_lines (f, from + dvpos, dvpos);
18289
18290 /* On a dumb terminal insert dvpos empty lines at the
18291 end. */
18292 if (!FRAME_SCROLL_REGION_OK (f))
18293 ins_del_lines (f, end + dvpos, -dvpos);
18294 }
18295
18296 set_terminal_window (f, 0);
18297 }
18298
18299 update_end (f);
18300 }
18301
18302 /* Shift reused rows of the current matrix to the right position.
18303 BOTTOM_ROW is the last + 1 row in the current matrix reserved for
18304 text. */
18305 bottom_row = MATRIX_BOTTOM_TEXT_ROW (current_matrix, w);
18306 bottom_vpos = MATRIX_ROW_VPOS (bottom_row, current_matrix);
18307 if (dvpos < 0)
18308 {
18309 rotate_matrix (current_matrix, first_unchanged_at_end_vpos + dvpos,
18310 bottom_vpos, dvpos);
18311 clear_glyph_matrix_rows (current_matrix, bottom_vpos + dvpos,
18312 bottom_vpos);
18313 }
18314 else if (dvpos > 0)
18315 {
18316 rotate_matrix (current_matrix, first_unchanged_at_end_vpos,
18317 bottom_vpos, dvpos);
18318 clear_glyph_matrix_rows (current_matrix, first_unchanged_at_end_vpos,
18319 first_unchanged_at_end_vpos + dvpos);
18320 }
18321
18322 /* For frame-based redisplay, make sure that current frame and window
18323 matrix are in sync with respect to glyph memory. */
18324 if (!FRAME_WINDOW_P (f))
18325 sync_frame_with_window_matrix_rows (w);
18326
18327 /* Adjust buffer positions in reused rows. */
18328 if (delta || delta_bytes)
18329 increment_matrix_positions (current_matrix,
18330 first_unchanged_at_end_vpos + dvpos,
18331 bottom_vpos, delta, delta_bytes);
18332
18333 /* Adjust Y positions. */
18334 if (dy)
18335 shift_glyph_matrix (w, current_matrix,
18336 first_unchanged_at_end_vpos + dvpos,
18337 bottom_vpos, dy);
18338
18339 if (first_unchanged_at_end_row)
18340 {
18341 first_unchanged_at_end_row += dvpos;
18342 if (first_unchanged_at_end_row->y >= it.last_visible_y
18343 || !MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row))
18344 first_unchanged_at_end_row = NULL;
18345 }
18346
18347 /* If scrolling up, there may be some lines to display at the end of
18348 the window. */
18349 last_text_row_at_end = NULL;
18350 if (dy < 0)
18351 {
18352 /* Scrolling up can leave for example a partially visible line
18353 at the end of the window to be redisplayed. */
18354 /* Set last_row to the glyph row in the current matrix where the
18355 window end line is found. It has been moved up or down in
18356 the matrix by dvpos. */
18357 int last_vpos = w->window_end_vpos + dvpos;
18358 struct glyph_row *last_row = MATRIX_ROW (current_matrix, last_vpos);
18359
18360 /* If last_row is the window end line, it should display text. */
18361 eassert (MATRIX_ROW_DISPLAYS_TEXT_P (last_row));
18362
18363 /* If window end line was partially visible before, begin
18364 displaying at that line. Otherwise begin displaying with the
18365 line following it. */
18366 if (MATRIX_ROW_BOTTOM_Y (last_row) - dy >= it.last_visible_y)
18367 {
18368 init_to_row_start (&it, w, last_row);
18369 it.vpos = last_vpos;
18370 it.current_y = last_row->y;
18371 }
18372 else
18373 {
18374 init_to_row_end (&it, w, last_row);
18375 it.vpos = 1 + last_vpos;
18376 it.current_y = MATRIX_ROW_BOTTOM_Y (last_row);
18377 ++last_row;
18378 }
18379
18380 /* We may start in a continuation line. If so, we have to
18381 get the right continuation_lines_width and current_x. */
18382 it.continuation_lines_width = last_row->continuation_lines_width;
18383 it.hpos = it.current_x = 0;
18384
18385 /* Display the rest of the lines at the window end. */
18386 it.glyph_row = MATRIX_ROW (desired_matrix, it.vpos);
18387 while (it.current_y < it.last_visible_y && !f->fonts_changed)
18388 {
18389 /* Is it always sure that the display agrees with lines in
18390 the current matrix? I don't think so, so we mark rows
18391 displayed invalid in the current matrix by setting their
18392 enabled_p flag to zero. */
18393 SET_MATRIX_ROW_ENABLED_P (w->current_matrix, it.vpos, false);
18394 if (display_line (&it))
18395 last_text_row_at_end = it.glyph_row - 1;
18396 }
18397 }
18398
18399 /* Update window_end_pos and window_end_vpos. */
18400 if (first_unchanged_at_end_row && !last_text_row_at_end)
18401 {
18402 /* Window end line if one of the preserved rows from the current
18403 matrix. Set row to the last row displaying text in current
18404 matrix starting at first_unchanged_at_end_row, after
18405 scrolling. */
18406 eassert (MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row));
18407 row = find_last_row_displaying_text (w->current_matrix, &it,
18408 first_unchanged_at_end_row);
18409 eassert (row && MATRIX_ROW_DISPLAYS_TEXT_P (row));
18410 adjust_window_ends (w, row, 1);
18411 eassert (w->window_end_bytepos >= 0);
18412 IF_DEBUG (debug_method_add (w, "A"));
18413 }
18414 else if (last_text_row_at_end)
18415 {
18416 adjust_window_ends (w, last_text_row_at_end, 0);
18417 eassert (w->window_end_bytepos >= 0);
18418 IF_DEBUG (debug_method_add (w, "B"));
18419 }
18420 else if (last_text_row)
18421 {
18422 /* We have displayed either to the end of the window or at the
18423 end of the window, i.e. the last row with text is to be found
18424 in the desired matrix. */
18425 adjust_window_ends (w, last_text_row, 0);
18426 eassert (w->window_end_bytepos >= 0);
18427 }
18428 else if (first_unchanged_at_end_row == NULL
18429 && last_text_row == NULL
18430 && last_text_row_at_end == NULL)
18431 {
18432 /* Displayed to end of window, but no line containing text was
18433 displayed. Lines were deleted at the end of the window. */
18434 int first_vpos = WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0;
18435 int vpos = w->window_end_vpos;
18436 struct glyph_row *current_row = current_matrix->rows + vpos;
18437 struct glyph_row *desired_row = desired_matrix->rows + vpos;
18438
18439 for (row = NULL;
18440 row == NULL && vpos >= first_vpos;
18441 --vpos, --current_row, --desired_row)
18442 {
18443 if (desired_row->enabled_p)
18444 {
18445 if (MATRIX_ROW_DISPLAYS_TEXT_P (desired_row))
18446 row = desired_row;
18447 }
18448 else if (MATRIX_ROW_DISPLAYS_TEXT_P (current_row))
18449 row = current_row;
18450 }
18451
18452 eassert (row != NULL);
18453 w->window_end_vpos = vpos + 1;
18454 w->window_end_pos = Z - MATRIX_ROW_END_CHARPOS (row);
18455 w->window_end_bytepos = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
18456 eassert (w->window_end_bytepos >= 0);
18457 IF_DEBUG (debug_method_add (w, "C"));
18458 }
18459 else
18460 emacs_abort ();
18461
18462 IF_DEBUG ((debug_end_pos = w->window_end_pos,
18463 debug_end_vpos = w->window_end_vpos));
18464
18465 /* Record that display has not been completed. */
18466 w->window_end_valid = 0;
18467 w->desired_matrix->no_scrolling_p = 1;
18468 return 3;
18469
18470 #undef GIVE_UP
18471 }
18472
18473
18474 \f
18475 /***********************************************************************
18476 More debugging support
18477 ***********************************************************************/
18478
18479 #ifdef GLYPH_DEBUG
18480
18481 void dump_glyph_row (struct glyph_row *, int, int) EXTERNALLY_VISIBLE;
18482 void dump_glyph_matrix (struct glyph_matrix *, int) EXTERNALLY_VISIBLE;
18483 void dump_glyph (struct glyph_row *, struct glyph *, int) EXTERNALLY_VISIBLE;
18484
18485
18486 /* Dump the contents of glyph matrix MATRIX on stderr.
18487
18488 GLYPHS 0 means don't show glyph contents.
18489 GLYPHS 1 means show glyphs in short form
18490 GLYPHS > 1 means show glyphs in long form. */
18491
18492 void
18493 dump_glyph_matrix (struct glyph_matrix *matrix, int glyphs)
18494 {
18495 int i;
18496 for (i = 0; i < matrix->nrows; ++i)
18497 dump_glyph_row (MATRIX_ROW (matrix, i), i, glyphs);
18498 }
18499
18500
18501 /* Dump contents of glyph GLYPH to stderr. ROW and AREA are
18502 the glyph row and area where the glyph comes from. */
18503
18504 void
18505 dump_glyph (struct glyph_row *row, struct glyph *glyph, int area)
18506 {
18507 if (glyph->type == CHAR_GLYPH
18508 || glyph->type == GLYPHLESS_GLYPH)
18509 {
18510 fprintf (stderr,
18511 " %5"pD"d %c %9"pI"d %c %3d 0x%06x %c %4d %1.1d%1.1d\n",
18512 glyph - row->glyphs[TEXT_AREA],
18513 (glyph->type == CHAR_GLYPH
18514 ? 'C'
18515 : 'G'),
18516 glyph->charpos,
18517 (BUFFERP (glyph->object)
18518 ? 'B'
18519 : (STRINGP (glyph->object)
18520 ? 'S'
18521 : (NILP (glyph->object)
18522 ? '0'
18523 : '-'))),
18524 glyph->pixel_width,
18525 glyph->u.ch,
18526 (glyph->u.ch < 0x80 && glyph->u.ch >= ' '
18527 ? glyph->u.ch
18528 : '.'),
18529 glyph->face_id,
18530 glyph->left_box_line_p,
18531 glyph->right_box_line_p);
18532 }
18533 else if (glyph->type == STRETCH_GLYPH)
18534 {
18535 fprintf (stderr,
18536 " %5"pD"d %c %9"pI"d %c %3d 0x%06x %c %4d %1.1d%1.1d\n",
18537 glyph - row->glyphs[TEXT_AREA],
18538 'S',
18539 glyph->charpos,
18540 (BUFFERP (glyph->object)
18541 ? 'B'
18542 : (STRINGP (glyph->object)
18543 ? 'S'
18544 : (NILP (glyph->object)
18545 ? '0'
18546 : '-'))),
18547 glyph->pixel_width,
18548 0,
18549 ' ',
18550 glyph->face_id,
18551 glyph->left_box_line_p,
18552 glyph->right_box_line_p);
18553 }
18554 else if (glyph->type == IMAGE_GLYPH)
18555 {
18556 fprintf (stderr,
18557 " %5"pD"d %c %9"pI"d %c %3d 0x%06x %c %4d %1.1d%1.1d\n",
18558 glyph - row->glyphs[TEXT_AREA],
18559 'I',
18560 glyph->charpos,
18561 (BUFFERP (glyph->object)
18562 ? 'B'
18563 : (STRINGP (glyph->object)
18564 ? 'S'
18565 : (NILP (glyph->object)
18566 ? '0'
18567 : '-'))),
18568 glyph->pixel_width,
18569 glyph->u.img_id,
18570 '.',
18571 glyph->face_id,
18572 glyph->left_box_line_p,
18573 glyph->right_box_line_p);
18574 }
18575 else if (glyph->type == COMPOSITE_GLYPH)
18576 {
18577 fprintf (stderr,
18578 " %5"pD"d %c %9"pI"d %c %3d 0x%06x",
18579 glyph - row->glyphs[TEXT_AREA],
18580 '+',
18581 glyph->charpos,
18582 (BUFFERP (glyph->object)
18583 ? 'B'
18584 : (STRINGP (glyph->object)
18585 ? 'S'
18586 : (NILP (glyph->object)
18587 ? '0'
18588 : '-'))),
18589 glyph->pixel_width,
18590 glyph->u.cmp.id);
18591 if (glyph->u.cmp.automatic)
18592 fprintf (stderr,
18593 "[%d-%d]",
18594 glyph->slice.cmp.from, glyph->slice.cmp.to);
18595 fprintf (stderr, " . %4d %1.1d%1.1d\n",
18596 glyph->face_id,
18597 glyph->left_box_line_p,
18598 glyph->right_box_line_p);
18599 }
18600 }
18601
18602
18603 /* Dump the contents of glyph row at VPOS in MATRIX to stderr.
18604 GLYPHS 0 means don't show glyph contents.
18605 GLYPHS 1 means show glyphs in short form
18606 GLYPHS > 1 means show glyphs in long form. */
18607
18608 void
18609 dump_glyph_row (struct glyph_row *row, int vpos, int glyphs)
18610 {
18611 if (glyphs != 1)
18612 {
18613 fprintf (stderr, "Row Start End Used oE><\\CTZFesm X Y W H V A P\n");
18614 fprintf (stderr, "==============================================================================\n");
18615
18616 fprintf (stderr, "%3d %9"pI"d %9"pI"d %4d %1.1d%1.1d%1.1d%1.1d\
18617 %1.1d%1.1d%1.1d%1.1d%1.1d%1.1d%1.1d%1.1d %4d %4d %4d %4d %4d %4d %4d\n",
18618 vpos,
18619 MATRIX_ROW_START_CHARPOS (row),
18620 MATRIX_ROW_END_CHARPOS (row),
18621 row->used[TEXT_AREA],
18622 row->contains_overlapping_glyphs_p,
18623 row->enabled_p,
18624 row->truncated_on_left_p,
18625 row->truncated_on_right_p,
18626 row->continued_p,
18627 MATRIX_ROW_CONTINUATION_LINE_P (row),
18628 MATRIX_ROW_DISPLAYS_TEXT_P (row),
18629 row->ends_at_zv_p,
18630 row->fill_line_p,
18631 row->ends_in_middle_of_char_p,
18632 row->starts_in_middle_of_char_p,
18633 row->mouse_face_p,
18634 row->x,
18635 row->y,
18636 row->pixel_width,
18637 row->height,
18638 row->visible_height,
18639 row->ascent,
18640 row->phys_ascent);
18641 /* The next 3 lines should align to "Start" in the header. */
18642 fprintf (stderr, " %9"pD"d %9"pD"d\t%5d\n", row->start.overlay_string_index,
18643 row->end.overlay_string_index,
18644 row->continuation_lines_width);
18645 fprintf (stderr, " %9"pI"d %9"pI"d\n",
18646 CHARPOS (row->start.string_pos),
18647 CHARPOS (row->end.string_pos));
18648 fprintf (stderr, " %9d %9d\n", row->start.dpvec_index,
18649 row->end.dpvec_index);
18650 }
18651
18652 if (glyphs > 1)
18653 {
18654 int area;
18655
18656 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
18657 {
18658 struct glyph *glyph = row->glyphs[area];
18659 struct glyph *glyph_end = glyph + row->used[area];
18660
18661 /* Glyph for a line end in text. */
18662 if (area == TEXT_AREA && glyph == glyph_end && glyph->charpos > 0)
18663 ++glyph_end;
18664
18665 if (glyph < glyph_end)
18666 fprintf (stderr, " Glyph# Type Pos O W Code C Face LR\n");
18667
18668 for (; glyph < glyph_end; ++glyph)
18669 dump_glyph (row, glyph, area);
18670 }
18671 }
18672 else if (glyphs == 1)
18673 {
18674 int area;
18675 char s[SHRT_MAX + 4];
18676
18677 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
18678 {
18679 int i;
18680
18681 for (i = 0; i < row->used[area]; ++i)
18682 {
18683 struct glyph *glyph = row->glyphs[area] + i;
18684 if (i == row->used[area] - 1
18685 && area == TEXT_AREA
18686 && NILP (glyph->object)
18687 && glyph->type == CHAR_GLYPH
18688 && glyph->u.ch == ' ')
18689 {
18690 strcpy (&s[i], "[\\n]");
18691 i += 4;
18692 }
18693 else if (glyph->type == CHAR_GLYPH
18694 && glyph->u.ch < 0x80
18695 && glyph->u.ch >= ' ')
18696 s[i] = glyph->u.ch;
18697 else
18698 s[i] = '.';
18699 }
18700
18701 s[i] = '\0';
18702 fprintf (stderr, "%3d: (%d) '%s'\n", vpos, row->enabled_p, s);
18703 }
18704 }
18705 }
18706
18707
18708 DEFUN ("dump-glyph-matrix", Fdump_glyph_matrix,
18709 Sdump_glyph_matrix, 0, 1, "p",
18710 doc: /* Dump the current matrix of the selected window to stderr.
18711 Shows contents of glyph row structures. With non-nil
18712 parameter GLYPHS, dump glyphs as well. If GLYPHS is 1 show
18713 glyphs in short form, otherwise show glyphs in long form.
18714
18715 Interactively, no argument means show glyphs in short form;
18716 with numeric argument, its value is passed as the GLYPHS flag. */)
18717 (Lisp_Object glyphs)
18718 {
18719 struct window *w = XWINDOW (selected_window);
18720 struct buffer *buffer = XBUFFER (w->contents);
18721
18722 fprintf (stderr, "PT = %"pI"d, BEGV = %"pI"d. ZV = %"pI"d\n",
18723 BUF_PT (buffer), BUF_BEGV (buffer), BUF_ZV (buffer));
18724 fprintf (stderr, "Cursor x = %d, y = %d, hpos = %d, vpos = %d\n",
18725 w->cursor.x, w->cursor.y, w->cursor.hpos, w->cursor.vpos);
18726 fprintf (stderr, "=============================================\n");
18727 dump_glyph_matrix (w->current_matrix,
18728 TYPE_RANGED_INTEGERP (int, glyphs) ? XINT (glyphs) : 0);
18729 return Qnil;
18730 }
18731
18732
18733 DEFUN ("dump-frame-glyph-matrix", Fdump_frame_glyph_matrix,
18734 Sdump_frame_glyph_matrix, 0, 0, "", doc: /* Dump the current glyph matrix of the selected frame to stderr.
18735 Only text-mode frames have frame glyph matrices. */)
18736 (void)
18737 {
18738 struct frame *f = XFRAME (selected_frame);
18739
18740 if (f->current_matrix)
18741 dump_glyph_matrix (f->current_matrix, 1);
18742 else
18743 fprintf (stderr, "*** This frame doesn't have a frame glyph matrix ***\n");
18744 return Qnil;
18745 }
18746
18747
18748 DEFUN ("dump-glyph-row", Fdump_glyph_row, Sdump_glyph_row, 1, 2, "",
18749 doc: /* Dump glyph row ROW to stderr.
18750 GLYPH 0 means don't dump glyphs.
18751 GLYPH 1 means dump glyphs in short form.
18752 GLYPH > 1 or omitted means dump glyphs in long form. */)
18753 (Lisp_Object row, Lisp_Object glyphs)
18754 {
18755 struct glyph_matrix *matrix;
18756 EMACS_INT vpos;
18757
18758 CHECK_NUMBER (row);
18759 matrix = XWINDOW (selected_window)->current_matrix;
18760 vpos = XINT (row);
18761 if (vpos >= 0 && vpos < matrix->nrows)
18762 dump_glyph_row (MATRIX_ROW (matrix, vpos),
18763 vpos,
18764 TYPE_RANGED_INTEGERP (int, glyphs) ? XINT (glyphs) : 2);
18765 return Qnil;
18766 }
18767
18768
18769 DEFUN ("dump-tool-bar-row", Fdump_tool_bar_row, Sdump_tool_bar_row, 1, 2, "",
18770 doc: /* Dump glyph row ROW of the tool-bar of the current frame to stderr.
18771 GLYPH 0 means don't dump glyphs.
18772 GLYPH 1 means dump glyphs in short form.
18773 GLYPH > 1 or omitted means dump glyphs in long form.
18774
18775 If there's no tool-bar, or if the tool-bar is not drawn by Emacs,
18776 do nothing. */)
18777 (Lisp_Object row, Lisp_Object glyphs)
18778 {
18779 #if defined (HAVE_WINDOW_SYSTEM) && ! defined (USE_GTK) && ! defined (HAVE_NS)
18780 struct frame *sf = SELECTED_FRAME ();
18781 struct glyph_matrix *m = XWINDOW (sf->tool_bar_window)->current_matrix;
18782 EMACS_INT vpos;
18783
18784 CHECK_NUMBER (row);
18785 vpos = XINT (row);
18786 if (vpos >= 0 && vpos < m->nrows)
18787 dump_glyph_row (MATRIX_ROW (m, vpos), vpos,
18788 TYPE_RANGED_INTEGERP (int, glyphs) ? XINT (glyphs) : 2);
18789 #endif
18790 return Qnil;
18791 }
18792
18793
18794 DEFUN ("trace-redisplay", Ftrace_redisplay, Strace_redisplay, 0, 1, "P",
18795 doc: /* Toggle tracing of redisplay.
18796 With ARG, turn tracing on if and only if ARG is positive. */)
18797 (Lisp_Object arg)
18798 {
18799 if (NILP (arg))
18800 trace_redisplay_p = !trace_redisplay_p;
18801 else
18802 {
18803 arg = Fprefix_numeric_value (arg);
18804 trace_redisplay_p = XINT (arg) > 0;
18805 }
18806
18807 return Qnil;
18808 }
18809
18810
18811 DEFUN ("trace-to-stderr", Ftrace_to_stderr, Strace_to_stderr, 1, MANY, "",
18812 doc: /* Like `format', but print result to stderr.
18813 usage: (trace-to-stderr STRING &rest OBJECTS) */)
18814 (ptrdiff_t nargs, Lisp_Object *args)
18815 {
18816 Lisp_Object s = Fformat (nargs, args);
18817 fwrite (SDATA (s), 1, SBYTES (s), stderr);
18818 return Qnil;
18819 }
18820
18821 #endif /* GLYPH_DEBUG */
18822
18823
18824 \f
18825 /***********************************************************************
18826 Building Desired Matrix Rows
18827 ***********************************************************************/
18828
18829 /* Return a temporary glyph row holding the glyphs of an overlay arrow.
18830 Used for non-window-redisplay windows, and for windows w/o left fringe. */
18831
18832 static struct glyph_row *
18833 get_overlay_arrow_glyph_row (struct window *w, Lisp_Object overlay_arrow_string)
18834 {
18835 struct frame *f = XFRAME (WINDOW_FRAME (w));
18836 struct buffer *buffer = XBUFFER (w->contents);
18837 struct buffer *old = current_buffer;
18838 const unsigned char *arrow_string = SDATA (overlay_arrow_string);
18839 ptrdiff_t arrow_len = SCHARS (overlay_arrow_string);
18840 const unsigned char *arrow_end = arrow_string + arrow_len;
18841 const unsigned char *p;
18842 struct it it;
18843 bool multibyte_p;
18844 int n_glyphs_before;
18845
18846 set_buffer_temp (buffer);
18847 init_iterator (&it, w, -1, -1, &scratch_glyph_row, DEFAULT_FACE_ID);
18848 scratch_glyph_row.reversed_p = false;
18849 it.glyph_row->used[TEXT_AREA] = 0;
18850 SET_TEXT_POS (it.position, 0, 0);
18851
18852 multibyte_p = !NILP (BVAR (buffer, enable_multibyte_characters));
18853 p = arrow_string;
18854 while (p < arrow_end)
18855 {
18856 Lisp_Object face, ilisp;
18857
18858 /* Get the next character. */
18859 if (multibyte_p)
18860 it.c = it.char_to_display = string_char_and_length (p, &it.len);
18861 else
18862 {
18863 it.c = it.char_to_display = *p, it.len = 1;
18864 if (! ASCII_CHAR_P (it.c))
18865 it.char_to_display = BYTE8_TO_CHAR (it.c);
18866 }
18867 p += it.len;
18868
18869 /* Get its face. */
18870 ilisp = make_number (p - arrow_string);
18871 face = Fget_text_property (ilisp, Qface, overlay_arrow_string);
18872 it.face_id = compute_char_face (f, it.char_to_display, face);
18873
18874 /* Compute its width, get its glyphs. */
18875 n_glyphs_before = it.glyph_row->used[TEXT_AREA];
18876 SET_TEXT_POS (it.position, -1, -1);
18877 PRODUCE_GLYPHS (&it);
18878
18879 /* If this character doesn't fit any more in the line, we have
18880 to remove some glyphs. */
18881 if (it.current_x > it.last_visible_x)
18882 {
18883 it.glyph_row->used[TEXT_AREA] = n_glyphs_before;
18884 break;
18885 }
18886 }
18887
18888 set_buffer_temp (old);
18889 return it.glyph_row;
18890 }
18891
18892
18893 /* Insert truncation glyphs at the start of IT->glyph_row. Which
18894 glyphs to insert is determined by produce_special_glyphs. */
18895
18896 static void
18897 insert_left_trunc_glyphs (struct it *it)
18898 {
18899 struct it truncate_it;
18900 struct glyph *from, *end, *to, *toend;
18901
18902 eassert (!FRAME_WINDOW_P (it->f)
18903 || (!it->glyph_row->reversed_p
18904 && WINDOW_LEFT_FRINGE_WIDTH (it->w) == 0)
18905 || (it->glyph_row->reversed_p
18906 && WINDOW_RIGHT_FRINGE_WIDTH (it->w) == 0));
18907
18908 /* Get the truncation glyphs. */
18909 truncate_it = *it;
18910 truncate_it.current_x = 0;
18911 truncate_it.face_id = DEFAULT_FACE_ID;
18912 truncate_it.glyph_row = &scratch_glyph_row;
18913 truncate_it.area = TEXT_AREA;
18914 truncate_it.glyph_row->used[TEXT_AREA] = 0;
18915 CHARPOS (truncate_it.position) = BYTEPOS (truncate_it.position) = -1;
18916 truncate_it.object = Qnil;
18917 produce_special_glyphs (&truncate_it, IT_TRUNCATION);
18918
18919 /* Overwrite glyphs from IT with truncation glyphs. */
18920 if (!it->glyph_row->reversed_p)
18921 {
18922 short tused = truncate_it.glyph_row->used[TEXT_AREA];
18923
18924 from = truncate_it.glyph_row->glyphs[TEXT_AREA];
18925 end = from + tused;
18926 to = it->glyph_row->glyphs[TEXT_AREA];
18927 toend = to + it->glyph_row->used[TEXT_AREA];
18928 if (FRAME_WINDOW_P (it->f))
18929 {
18930 /* On GUI frames, when variable-size fonts are displayed,
18931 the truncation glyphs may need more pixels than the row's
18932 glyphs they overwrite. We overwrite more glyphs to free
18933 enough screen real estate, and enlarge the stretch glyph
18934 on the right (see display_line), if there is one, to
18935 preserve the screen position of the truncation glyphs on
18936 the right. */
18937 int w = 0;
18938 struct glyph *g = to;
18939 short used;
18940
18941 /* The first glyph could be partially visible, in which case
18942 it->glyph_row->x will be negative. But we want the left
18943 truncation glyphs to be aligned at the left margin of the
18944 window, so we override the x coordinate at which the row
18945 will begin. */
18946 it->glyph_row->x = 0;
18947 while (g < toend && w < it->truncation_pixel_width)
18948 {
18949 w += g->pixel_width;
18950 ++g;
18951 }
18952 if (g - to - tused > 0)
18953 {
18954 memmove (to + tused, g, (toend - g) * sizeof(*g));
18955 it->glyph_row->used[TEXT_AREA] -= g - to - tused;
18956 }
18957 used = it->glyph_row->used[TEXT_AREA];
18958 if (it->glyph_row->truncated_on_right_p
18959 && WINDOW_RIGHT_FRINGE_WIDTH (it->w) == 0
18960 && it->glyph_row->glyphs[TEXT_AREA][used - 2].type
18961 == STRETCH_GLYPH)
18962 {
18963 int extra = w - it->truncation_pixel_width;
18964
18965 it->glyph_row->glyphs[TEXT_AREA][used - 2].pixel_width += extra;
18966 }
18967 }
18968
18969 while (from < end)
18970 *to++ = *from++;
18971
18972 /* There may be padding glyphs left over. Overwrite them too. */
18973 if (!FRAME_WINDOW_P (it->f))
18974 {
18975 while (to < toend && CHAR_GLYPH_PADDING_P (*to))
18976 {
18977 from = truncate_it.glyph_row->glyphs[TEXT_AREA];
18978 while (from < end)
18979 *to++ = *from++;
18980 }
18981 }
18982
18983 if (to > toend)
18984 it->glyph_row->used[TEXT_AREA] = to - it->glyph_row->glyphs[TEXT_AREA];
18985 }
18986 else
18987 {
18988 short tused = truncate_it.glyph_row->used[TEXT_AREA];
18989
18990 /* In R2L rows, overwrite the last (rightmost) glyphs, and do
18991 that back to front. */
18992 end = truncate_it.glyph_row->glyphs[TEXT_AREA];
18993 from = end + truncate_it.glyph_row->used[TEXT_AREA] - 1;
18994 toend = it->glyph_row->glyphs[TEXT_AREA];
18995 to = toend + it->glyph_row->used[TEXT_AREA] - 1;
18996 if (FRAME_WINDOW_P (it->f))
18997 {
18998 int w = 0;
18999 struct glyph *g = to;
19000
19001 while (g >= toend && w < it->truncation_pixel_width)
19002 {
19003 w += g->pixel_width;
19004 --g;
19005 }
19006 if (to - g - tused > 0)
19007 to = g + tused;
19008 if (it->glyph_row->truncated_on_right_p
19009 && WINDOW_LEFT_FRINGE_WIDTH (it->w) == 0
19010 && it->glyph_row->glyphs[TEXT_AREA][1].type == STRETCH_GLYPH)
19011 {
19012 int extra = w - it->truncation_pixel_width;
19013
19014 it->glyph_row->glyphs[TEXT_AREA][1].pixel_width += extra;
19015 }
19016 }
19017
19018 while (from >= end && to >= toend)
19019 *to-- = *from--;
19020 if (!FRAME_WINDOW_P (it->f))
19021 {
19022 while (to >= toend && CHAR_GLYPH_PADDING_P (*to))
19023 {
19024 from =
19025 truncate_it.glyph_row->glyphs[TEXT_AREA]
19026 + truncate_it.glyph_row->used[TEXT_AREA] - 1;
19027 while (from >= end && to >= toend)
19028 *to-- = *from--;
19029 }
19030 }
19031 if (from >= end)
19032 {
19033 /* Need to free some room before prepending additional
19034 glyphs. */
19035 int move_by = from - end + 1;
19036 struct glyph *g0 = it->glyph_row->glyphs[TEXT_AREA];
19037 struct glyph *g = g0 + it->glyph_row->used[TEXT_AREA] - 1;
19038
19039 for ( ; g >= g0; g--)
19040 g[move_by] = *g;
19041 while (from >= end)
19042 *to-- = *from--;
19043 it->glyph_row->used[TEXT_AREA] += move_by;
19044 }
19045 }
19046 }
19047
19048 /* Compute the hash code for ROW. */
19049 unsigned
19050 row_hash (struct glyph_row *row)
19051 {
19052 int area, k;
19053 unsigned hashval = 0;
19054
19055 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
19056 for (k = 0; k < row->used[area]; ++k)
19057 hashval = ((((hashval << 4) + (hashval >> 24)) & 0x0fffffff)
19058 + row->glyphs[area][k].u.val
19059 + row->glyphs[area][k].face_id
19060 + row->glyphs[area][k].padding_p
19061 + (row->glyphs[area][k].type << 2));
19062
19063 return hashval;
19064 }
19065
19066 /* Compute the pixel height and width of IT->glyph_row.
19067
19068 Most of the time, ascent and height of a display line will be equal
19069 to the max_ascent and max_height values of the display iterator
19070 structure. This is not the case if
19071
19072 1. We hit ZV without displaying anything. In this case, max_ascent
19073 and max_height will be zero.
19074
19075 2. We have some glyphs that don't contribute to the line height.
19076 (The glyph row flag contributes_to_line_height_p is for future
19077 pixmap extensions).
19078
19079 The first case is easily covered by using default values because in
19080 these cases, the line height does not really matter, except that it
19081 must not be zero. */
19082
19083 static void
19084 compute_line_metrics (struct it *it)
19085 {
19086 struct glyph_row *row = it->glyph_row;
19087
19088 if (FRAME_WINDOW_P (it->f))
19089 {
19090 int i, min_y, max_y;
19091
19092 /* The line may consist of one space only, that was added to
19093 place the cursor on it. If so, the row's height hasn't been
19094 computed yet. */
19095 if (row->height == 0)
19096 {
19097 if (it->max_ascent + it->max_descent == 0)
19098 it->max_descent = it->max_phys_descent = FRAME_LINE_HEIGHT (it->f);
19099 row->ascent = it->max_ascent;
19100 row->height = it->max_ascent + it->max_descent;
19101 row->phys_ascent = it->max_phys_ascent;
19102 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
19103 row->extra_line_spacing = it->max_extra_line_spacing;
19104 }
19105
19106 /* Compute the width of this line. */
19107 row->pixel_width = row->x;
19108 for (i = 0; i < row->used[TEXT_AREA]; ++i)
19109 row->pixel_width += row->glyphs[TEXT_AREA][i].pixel_width;
19110
19111 eassert (row->pixel_width >= 0);
19112 eassert (row->ascent >= 0 && row->height > 0);
19113
19114 row->overlapping_p = (MATRIX_ROW_OVERLAPS_SUCC_P (row)
19115 || MATRIX_ROW_OVERLAPS_PRED_P (row));
19116
19117 /* If first line's physical ascent is larger than its logical
19118 ascent, use the physical ascent, and make the row taller.
19119 This makes accented characters fully visible. */
19120 if (row == MATRIX_FIRST_TEXT_ROW (it->w->desired_matrix)
19121 && row->phys_ascent > row->ascent)
19122 {
19123 row->height += row->phys_ascent - row->ascent;
19124 row->ascent = row->phys_ascent;
19125 }
19126
19127 /* Compute how much of the line is visible. */
19128 row->visible_height = row->height;
19129
19130 min_y = WINDOW_HEADER_LINE_HEIGHT (it->w);
19131 max_y = WINDOW_BOX_HEIGHT_NO_MODE_LINE (it->w);
19132
19133 if (row->y < min_y)
19134 row->visible_height -= min_y - row->y;
19135 if (row->y + row->height > max_y)
19136 row->visible_height -= row->y + row->height - max_y;
19137 }
19138 else
19139 {
19140 row->pixel_width = row->used[TEXT_AREA];
19141 if (row->continued_p)
19142 row->pixel_width -= it->continuation_pixel_width;
19143 else if (row->truncated_on_right_p)
19144 row->pixel_width -= it->truncation_pixel_width;
19145 row->ascent = row->phys_ascent = 0;
19146 row->height = row->phys_height = row->visible_height = 1;
19147 row->extra_line_spacing = 0;
19148 }
19149
19150 /* Compute a hash code for this row. */
19151 row->hash = row_hash (row);
19152
19153 it->max_ascent = it->max_descent = 0;
19154 it->max_phys_ascent = it->max_phys_descent = 0;
19155 }
19156
19157
19158 /* Append one space to the glyph row of iterator IT if doing a
19159 window-based redisplay. The space has the same face as
19160 IT->face_id. Value is non-zero if a space was added.
19161
19162 This function is called to make sure that there is always one glyph
19163 at the end of a glyph row that the cursor can be set on under
19164 window-systems. (If there weren't such a glyph we would not know
19165 how wide and tall a box cursor should be displayed).
19166
19167 At the same time this space let's a nicely handle clearing to the
19168 end of the line if the row ends in italic text. */
19169
19170 static int
19171 append_space_for_newline (struct it *it, int default_face_p)
19172 {
19173 if (FRAME_WINDOW_P (it->f))
19174 {
19175 int n = it->glyph_row->used[TEXT_AREA];
19176
19177 if (it->glyph_row->glyphs[TEXT_AREA] + n
19178 < it->glyph_row->glyphs[1 + TEXT_AREA])
19179 {
19180 /* Save some values that must not be changed.
19181 Must save IT->c and IT->len because otherwise
19182 ITERATOR_AT_END_P wouldn't work anymore after
19183 append_space_for_newline has been called. */
19184 enum display_element_type saved_what = it->what;
19185 int saved_c = it->c, saved_len = it->len;
19186 int saved_char_to_display = it->char_to_display;
19187 int saved_x = it->current_x;
19188 int saved_face_id = it->face_id;
19189 int saved_box_end = it->end_of_box_run_p;
19190 struct text_pos saved_pos;
19191 Lisp_Object saved_object;
19192 struct face *face;
19193
19194 saved_object = it->object;
19195 saved_pos = it->position;
19196
19197 it->what = IT_CHARACTER;
19198 memset (&it->position, 0, sizeof it->position);
19199 it->object = Qnil;
19200 it->c = it->char_to_display = ' ';
19201 it->len = 1;
19202
19203 /* If the default face was remapped, be sure to use the
19204 remapped face for the appended newline. */
19205 if (default_face_p)
19206 it->face_id = lookup_basic_face (it->f, DEFAULT_FACE_ID);
19207 else if (it->face_before_selective_p)
19208 it->face_id = it->saved_face_id;
19209 face = FACE_FROM_ID (it->f, it->face_id);
19210 it->face_id = FACE_FOR_CHAR (it->f, face, 0, -1, Qnil);
19211 /* In R2L rows, we will prepend a stretch glyph that will
19212 have the end_of_box_run_p flag set for it, so there's no
19213 need for the appended newline glyph to have that flag
19214 set. */
19215 if (it->glyph_row->reversed_p
19216 /* But if the appended newline glyph goes all the way to
19217 the end of the row, there will be no stretch glyph,
19218 so leave the box flag set. */
19219 && saved_x + FRAME_COLUMN_WIDTH (it->f) < it->last_visible_x)
19220 it->end_of_box_run_p = 0;
19221
19222 PRODUCE_GLYPHS (it);
19223
19224 it->override_ascent = -1;
19225 it->constrain_row_ascent_descent_p = 0;
19226 it->current_x = saved_x;
19227 it->object = saved_object;
19228 it->position = saved_pos;
19229 it->what = saved_what;
19230 it->face_id = saved_face_id;
19231 it->len = saved_len;
19232 it->c = saved_c;
19233 it->char_to_display = saved_char_to_display;
19234 it->end_of_box_run_p = saved_box_end;
19235 return 1;
19236 }
19237 }
19238
19239 return 0;
19240 }
19241
19242
19243 /* Extend the face of the last glyph in the text area of IT->glyph_row
19244 to the end of the display line. Called from display_line. If the
19245 glyph row is empty, add a space glyph to it so that we know the
19246 face to draw. Set the glyph row flag fill_line_p. If the glyph
19247 row is R2L, prepend a stretch glyph to cover the empty space to the
19248 left of the leftmost glyph. */
19249
19250 static void
19251 extend_face_to_end_of_line (struct it *it)
19252 {
19253 struct face *face, *default_face;
19254 struct frame *f = it->f;
19255
19256 /* If line is already filled, do nothing. Non window-system frames
19257 get a grace of one more ``pixel'' because their characters are
19258 1-``pixel'' wide, so they hit the equality too early. This grace
19259 is needed only for R2L rows that are not continued, to produce
19260 one extra blank where we could display the cursor. */
19261 if ((it->current_x >= it->last_visible_x
19262 + (!FRAME_WINDOW_P (f)
19263 && it->glyph_row->reversed_p
19264 && !it->glyph_row->continued_p))
19265 /* If the window has display margins, we will need to extend
19266 their face even if the text area is filled. */
19267 && !(WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
19268 || WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0))
19269 return;
19270
19271 /* The default face, possibly remapped. */
19272 default_face = FACE_FROM_ID (f, lookup_basic_face (f, DEFAULT_FACE_ID));
19273
19274 /* Face extension extends the background and box of IT->face_id
19275 to the end of the line. If the background equals the background
19276 of the frame, we don't have to do anything. */
19277 if (it->face_before_selective_p)
19278 face = FACE_FROM_ID (f, it->saved_face_id);
19279 else
19280 face = FACE_FROM_ID (f, it->face_id);
19281
19282 if (FRAME_WINDOW_P (f)
19283 && MATRIX_ROW_DISPLAYS_TEXT_P (it->glyph_row)
19284 && face->box == FACE_NO_BOX
19285 && face->background == FRAME_BACKGROUND_PIXEL (f)
19286 #ifdef HAVE_WINDOW_SYSTEM
19287 && !face->stipple
19288 #endif
19289 && !it->glyph_row->reversed_p)
19290 return;
19291
19292 /* Set the glyph row flag indicating that the face of the last glyph
19293 in the text area has to be drawn to the end of the text area. */
19294 it->glyph_row->fill_line_p = 1;
19295
19296 /* If current character of IT is not ASCII, make sure we have the
19297 ASCII face. This will be automatically undone the next time
19298 get_next_display_element returns a multibyte character. Note
19299 that the character will always be single byte in unibyte
19300 text. */
19301 if (!ASCII_CHAR_P (it->c))
19302 {
19303 it->face_id = FACE_FOR_CHAR (f, face, 0, -1, Qnil);
19304 }
19305
19306 if (FRAME_WINDOW_P (f))
19307 {
19308 /* If the row is empty, add a space with the current face of IT,
19309 so that we know which face to draw. */
19310 if (it->glyph_row->used[TEXT_AREA] == 0)
19311 {
19312 it->glyph_row->glyphs[TEXT_AREA][0] = space_glyph;
19313 it->glyph_row->glyphs[TEXT_AREA][0].face_id = face->id;
19314 it->glyph_row->used[TEXT_AREA] = 1;
19315 }
19316 /* Mode line and the header line don't have margins, and
19317 likewise the frame's tool-bar window, if there is any. */
19318 if (!(it->glyph_row->mode_line_p
19319 #if defined (HAVE_WINDOW_SYSTEM) && ! defined (USE_GTK) && ! defined (HAVE_NS)
19320 || (WINDOWP (f->tool_bar_window)
19321 && it->w == XWINDOW (f->tool_bar_window))
19322 #endif
19323 ))
19324 {
19325 if (WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
19326 && it->glyph_row->used[LEFT_MARGIN_AREA] == 0)
19327 {
19328 it->glyph_row->glyphs[LEFT_MARGIN_AREA][0] = space_glyph;
19329 it->glyph_row->glyphs[LEFT_MARGIN_AREA][0].face_id =
19330 default_face->id;
19331 it->glyph_row->used[LEFT_MARGIN_AREA] = 1;
19332 }
19333 if (WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0
19334 && it->glyph_row->used[RIGHT_MARGIN_AREA] == 0)
19335 {
19336 it->glyph_row->glyphs[RIGHT_MARGIN_AREA][0] = space_glyph;
19337 it->glyph_row->glyphs[RIGHT_MARGIN_AREA][0].face_id =
19338 default_face->id;
19339 it->glyph_row->used[RIGHT_MARGIN_AREA] = 1;
19340 }
19341 }
19342 #ifdef HAVE_WINDOW_SYSTEM
19343 if (it->glyph_row->reversed_p)
19344 {
19345 /* Prepend a stretch glyph to the row, such that the
19346 rightmost glyph will be drawn flushed all the way to the
19347 right margin of the window. The stretch glyph that will
19348 occupy the empty space, if any, to the left of the
19349 glyphs. */
19350 struct font *font = face->font ? face->font : FRAME_FONT (f);
19351 struct glyph *row_start = it->glyph_row->glyphs[TEXT_AREA];
19352 struct glyph *row_end = row_start + it->glyph_row->used[TEXT_AREA];
19353 struct glyph *g;
19354 int row_width, stretch_ascent, stretch_width;
19355 struct text_pos saved_pos;
19356 int saved_face_id, saved_avoid_cursor, saved_box_start;
19357
19358 for (row_width = 0, g = row_start; g < row_end; g++)
19359 row_width += g->pixel_width;
19360
19361 /* FIXME: There are various minor display glitches in R2L
19362 rows when only one of the fringes is missing. The
19363 strange condition below produces the least bad effect. */
19364 if ((WINDOW_LEFT_FRINGE_WIDTH (it->w) == 0)
19365 == (WINDOW_RIGHT_FRINGE_WIDTH (it->w) == 0)
19366 || WINDOW_RIGHT_FRINGE_WIDTH (it->w) != 0)
19367 stretch_width = window_box_width (it->w, TEXT_AREA);
19368 else
19369 stretch_width = it->last_visible_x - it->first_visible_x;
19370 stretch_width -= row_width;
19371
19372 if (stretch_width > 0)
19373 {
19374 stretch_ascent =
19375 (((it->ascent + it->descent)
19376 * FONT_BASE (font)) / FONT_HEIGHT (font));
19377 saved_pos = it->position;
19378 memset (&it->position, 0, sizeof it->position);
19379 saved_avoid_cursor = it->avoid_cursor_p;
19380 it->avoid_cursor_p = 1;
19381 saved_face_id = it->face_id;
19382 saved_box_start = it->start_of_box_run_p;
19383 /* The last row's stretch glyph should get the default
19384 face, to avoid painting the rest of the window with
19385 the region face, if the region ends at ZV. */
19386 if (it->glyph_row->ends_at_zv_p)
19387 it->face_id = default_face->id;
19388 else
19389 it->face_id = face->id;
19390 it->start_of_box_run_p = 0;
19391 append_stretch_glyph (it, Qnil, stretch_width,
19392 it->ascent + it->descent, stretch_ascent);
19393 it->position = saved_pos;
19394 it->avoid_cursor_p = saved_avoid_cursor;
19395 it->face_id = saved_face_id;
19396 it->start_of_box_run_p = saved_box_start;
19397 }
19398 /* If stretch_width comes out negative, it means that the
19399 last glyph is only partially visible. In R2L rows, we
19400 want the leftmost glyph to be partially visible, so we
19401 need to give the row the corresponding left offset. */
19402 if (stretch_width < 0)
19403 it->glyph_row->x = stretch_width;
19404 }
19405 #endif /* HAVE_WINDOW_SYSTEM */
19406 }
19407 else
19408 {
19409 /* Save some values that must not be changed. */
19410 int saved_x = it->current_x;
19411 struct text_pos saved_pos;
19412 Lisp_Object saved_object;
19413 enum display_element_type saved_what = it->what;
19414 int saved_face_id = it->face_id;
19415
19416 saved_object = it->object;
19417 saved_pos = it->position;
19418
19419 it->what = IT_CHARACTER;
19420 memset (&it->position, 0, sizeof it->position);
19421 it->object = Qnil;
19422 it->c = it->char_to_display = ' ';
19423 it->len = 1;
19424
19425 if (WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
19426 && (it->glyph_row->used[LEFT_MARGIN_AREA]
19427 < WINDOW_LEFT_MARGIN_WIDTH (it->w))
19428 && !it->glyph_row->mode_line_p
19429 && default_face->background != FRAME_BACKGROUND_PIXEL (f))
19430 {
19431 struct glyph *g = it->glyph_row->glyphs[LEFT_MARGIN_AREA];
19432 struct glyph *e = g + it->glyph_row->used[LEFT_MARGIN_AREA];
19433
19434 for (it->current_x = 0; g < e; g++)
19435 it->current_x += g->pixel_width;
19436
19437 it->area = LEFT_MARGIN_AREA;
19438 it->face_id = default_face->id;
19439 while (it->glyph_row->used[LEFT_MARGIN_AREA]
19440 < WINDOW_LEFT_MARGIN_WIDTH (it->w))
19441 {
19442 PRODUCE_GLYPHS (it);
19443 /* term.c:produce_glyphs advances it->current_x only for
19444 TEXT_AREA. */
19445 it->current_x += it->pixel_width;
19446 }
19447
19448 it->current_x = saved_x;
19449 it->area = TEXT_AREA;
19450 }
19451
19452 /* The last row's blank glyphs should get the default face, to
19453 avoid painting the rest of the window with the region face,
19454 if the region ends at ZV. */
19455 if (it->glyph_row->ends_at_zv_p)
19456 it->face_id = default_face->id;
19457 else
19458 it->face_id = face->id;
19459 PRODUCE_GLYPHS (it);
19460
19461 while (it->current_x <= it->last_visible_x)
19462 PRODUCE_GLYPHS (it);
19463
19464 if (WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0
19465 && (it->glyph_row->used[RIGHT_MARGIN_AREA]
19466 < WINDOW_RIGHT_MARGIN_WIDTH (it->w))
19467 && !it->glyph_row->mode_line_p
19468 && default_face->background != FRAME_BACKGROUND_PIXEL (f))
19469 {
19470 struct glyph *g = it->glyph_row->glyphs[RIGHT_MARGIN_AREA];
19471 struct glyph *e = g + it->glyph_row->used[RIGHT_MARGIN_AREA];
19472
19473 for ( ; g < e; g++)
19474 it->current_x += g->pixel_width;
19475
19476 it->area = RIGHT_MARGIN_AREA;
19477 it->face_id = default_face->id;
19478 while (it->glyph_row->used[RIGHT_MARGIN_AREA]
19479 < WINDOW_RIGHT_MARGIN_WIDTH (it->w))
19480 {
19481 PRODUCE_GLYPHS (it);
19482 it->current_x += it->pixel_width;
19483 }
19484
19485 it->area = TEXT_AREA;
19486 }
19487
19488 /* Don't count these blanks really. It would let us insert a left
19489 truncation glyph below and make us set the cursor on them, maybe. */
19490 it->current_x = saved_x;
19491 it->object = saved_object;
19492 it->position = saved_pos;
19493 it->what = saved_what;
19494 it->face_id = saved_face_id;
19495 }
19496 }
19497
19498
19499 /* Value is non-zero if text starting at CHARPOS in current_buffer is
19500 trailing whitespace. */
19501
19502 static int
19503 trailing_whitespace_p (ptrdiff_t charpos)
19504 {
19505 ptrdiff_t bytepos = CHAR_TO_BYTE (charpos);
19506 int c = 0;
19507
19508 while (bytepos < ZV_BYTE
19509 && (c = FETCH_CHAR (bytepos),
19510 c == ' ' || c == '\t'))
19511 ++bytepos;
19512
19513 if (bytepos >= ZV_BYTE || c == '\n' || c == '\r')
19514 {
19515 if (bytepos != PT_BYTE)
19516 return 1;
19517 }
19518 return 0;
19519 }
19520
19521
19522 /* Highlight trailing whitespace, if any, in ROW. */
19523
19524 static void
19525 highlight_trailing_whitespace (struct frame *f, struct glyph_row *row)
19526 {
19527 int used = row->used[TEXT_AREA];
19528
19529 if (used)
19530 {
19531 struct glyph *start = row->glyphs[TEXT_AREA];
19532 struct glyph *glyph = start + used - 1;
19533
19534 if (row->reversed_p)
19535 {
19536 /* Right-to-left rows need to be processed in the opposite
19537 direction, so swap the edge pointers. */
19538 glyph = start;
19539 start = row->glyphs[TEXT_AREA] + used - 1;
19540 }
19541
19542 /* Skip over glyphs inserted to display the cursor at the
19543 end of a line, for extending the face of the last glyph
19544 to the end of the line on terminals, and for truncation
19545 and continuation glyphs. */
19546 if (!row->reversed_p)
19547 {
19548 while (glyph >= start
19549 && glyph->type == CHAR_GLYPH
19550 && NILP (glyph->object))
19551 --glyph;
19552 }
19553 else
19554 {
19555 while (glyph <= start
19556 && glyph->type == CHAR_GLYPH
19557 && NILP (glyph->object))
19558 ++glyph;
19559 }
19560
19561 /* If last glyph is a space or stretch, and it's trailing
19562 whitespace, set the face of all trailing whitespace glyphs in
19563 IT->glyph_row to `trailing-whitespace'. */
19564 if ((row->reversed_p ? glyph <= start : glyph >= start)
19565 && BUFFERP (glyph->object)
19566 && (glyph->type == STRETCH_GLYPH
19567 || (glyph->type == CHAR_GLYPH
19568 && glyph->u.ch == ' '))
19569 && trailing_whitespace_p (glyph->charpos))
19570 {
19571 int face_id = lookup_named_face (f, Qtrailing_whitespace, false);
19572 if (face_id < 0)
19573 return;
19574
19575 if (!row->reversed_p)
19576 {
19577 while (glyph >= start
19578 && BUFFERP (glyph->object)
19579 && (glyph->type == STRETCH_GLYPH
19580 || (glyph->type == CHAR_GLYPH
19581 && glyph->u.ch == ' ')))
19582 (glyph--)->face_id = face_id;
19583 }
19584 else
19585 {
19586 while (glyph <= start
19587 && BUFFERP (glyph->object)
19588 && (glyph->type == STRETCH_GLYPH
19589 || (glyph->type == CHAR_GLYPH
19590 && glyph->u.ch == ' ')))
19591 (glyph++)->face_id = face_id;
19592 }
19593 }
19594 }
19595 }
19596
19597
19598 /* Value is non-zero if glyph row ROW should be
19599 considered to hold the buffer position CHARPOS. */
19600
19601 static int
19602 row_for_charpos_p (struct glyph_row *row, ptrdiff_t charpos)
19603 {
19604 int result = 1;
19605
19606 if (charpos == CHARPOS (row->end.pos)
19607 || charpos == MATRIX_ROW_END_CHARPOS (row))
19608 {
19609 /* Suppose the row ends on a string.
19610 Unless the row is continued, that means it ends on a newline
19611 in the string. If it's anything other than a display string
19612 (e.g., a before-string from an overlay), we don't want the
19613 cursor there. (This heuristic seems to give the optimal
19614 behavior for the various types of multi-line strings.)
19615 One exception: if the string has `cursor' property on one of
19616 its characters, we _do_ want the cursor there. */
19617 if (CHARPOS (row->end.string_pos) >= 0)
19618 {
19619 if (row->continued_p)
19620 result = 1;
19621 else
19622 {
19623 /* Check for `display' property. */
19624 struct glyph *beg = row->glyphs[TEXT_AREA];
19625 struct glyph *end = beg + row->used[TEXT_AREA] - 1;
19626 struct glyph *glyph;
19627
19628 result = 0;
19629 for (glyph = end; glyph >= beg; --glyph)
19630 if (STRINGP (glyph->object))
19631 {
19632 Lisp_Object prop
19633 = Fget_char_property (make_number (charpos),
19634 Qdisplay, Qnil);
19635 result =
19636 (!NILP (prop)
19637 && display_prop_string_p (prop, glyph->object));
19638 /* If there's a `cursor' property on one of the
19639 string's characters, this row is a cursor row,
19640 even though this is not a display string. */
19641 if (!result)
19642 {
19643 Lisp_Object s = glyph->object;
19644
19645 for ( ; glyph >= beg && EQ (glyph->object, s); --glyph)
19646 {
19647 ptrdiff_t gpos = glyph->charpos;
19648
19649 if (!NILP (Fget_char_property (make_number (gpos),
19650 Qcursor, s)))
19651 {
19652 result = 1;
19653 break;
19654 }
19655 }
19656 }
19657 break;
19658 }
19659 }
19660 }
19661 else if (MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))
19662 {
19663 /* If the row ends in middle of a real character,
19664 and the line is continued, we want the cursor here.
19665 That's because CHARPOS (ROW->end.pos) would equal
19666 PT if PT is before the character. */
19667 if (!row->ends_in_ellipsis_p)
19668 result = row->continued_p;
19669 else
19670 /* If the row ends in an ellipsis, then
19671 CHARPOS (ROW->end.pos) will equal point after the
19672 invisible text. We want that position to be displayed
19673 after the ellipsis. */
19674 result = 0;
19675 }
19676 /* If the row ends at ZV, display the cursor at the end of that
19677 row instead of at the start of the row below. */
19678 else if (row->ends_at_zv_p)
19679 result = 1;
19680 else
19681 result = 0;
19682 }
19683
19684 return result;
19685 }
19686
19687 /* Value is non-zero if glyph row ROW should be
19688 used to hold the cursor. */
19689
19690 static int
19691 cursor_row_p (struct glyph_row *row)
19692 {
19693 return row_for_charpos_p (row, PT);
19694 }
19695
19696 \f
19697
19698 /* Push the property PROP so that it will be rendered at the current
19699 position in IT. Return 1 if PROP was successfully pushed, 0
19700 otherwise. Called from handle_line_prefix to handle the
19701 `line-prefix' and `wrap-prefix' properties. */
19702
19703 static int
19704 push_prefix_prop (struct it *it, Lisp_Object prop)
19705 {
19706 struct text_pos pos =
19707 STRINGP (it->string) ? it->current.string_pos : it->current.pos;
19708
19709 eassert (it->method == GET_FROM_BUFFER
19710 || it->method == GET_FROM_DISPLAY_VECTOR
19711 || it->method == GET_FROM_STRING);
19712
19713 /* We need to save the current buffer/string position, so it will be
19714 restored by pop_it, because iterate_out_of_display_property
19715 depends on that being set correctly, but some situations leave
19716 it->position not yet set when this function is called. */
19717 push_it (it, &pos);
19718
19719 if (STRINGP (prop))
19720 {
19721 if (SCHARS (prop) == 0)
19722 {
19723 pop_it (it);
19724 return 0;
19725 }
19726
19727 it->string = prop;
19728 it->string_from_prefix_prop_p = 1;
19729 it->multibyte_p = STRING_MULTIBYTE (it->string);
19730 it->current.overlay_string_index = -1;
19731 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = 0;
19732 it->end_charpos = it->string_nchars = SCHARS (it->string);
19733 it->method = GET_FROM_STRING;
19734 it->stop_charpos = 0;
19735 it->prev_stop = 0;
19736 it->base_level_stop = 0;
19737
19738 /* Force paragraph direction to be that of the parent
19739 buffer/string. */
19740 if (it->bidi_p && it->bidi_it.paragraph_dir == R2L)
19741 it->paragraph_embedding = it->bidi_it.paragraph_dir;
19742 else
19743 it->paragraph_embedding = L2R;
19744
19745 /* Set up the bidi iterator for this display string. */
19746 if (it->bidi_p)
19747 {
19748 it->bidi_it.string.lstring = it->string;
19749 it->bidi_it.string.s = NULL;
19750 it->bidi_it.string.schars = it->end_charpos;
19751 it->bidi_it.string.bufpos = IT_CHARPOS (*it);
19752 it->bidi_it.string.from_disp_str = it->string_from_display_prop_p;
19753 it->bidi_it.string.unibyte = !it->multibyte_p;
19754 it->bidi_it.w = it->w;
19755 bidi_init_it (0, 0, FRAME_WINDOW_P (it->f), &it->bidi_it);
19756 }
19757 }
19758 else if (CONSP (prop) && EQ (XCAR (prop), Qspace))
19759 {
19760 it->method = GET_FROM_STRETCH;
19761 it->object = prop;
19762 }
19763 #ifdef HAVE_WINDOW_SYSTEM
19764 else if (IMAGEP (prop))
19765 {
19766 it->what = IT_IMAGE;
19767 it->image_id = lookup_image (it->f, prop);
19768 it->method = GET_FROM_IMAGE;
19769 }
19770 #endif /* HAVE_WINDOW_SYSTEM */
19771 else
19772 {
19773 pop_it (it); /* bogus display property, give up */
19774 return 0;
19775 }
19776
19777 return 1;
19778 }
19779
19780 /* Return the character-property PROP at the current position in IT. */
19781
19782 static Lisp_Object
19783 get_it_property (struct it *it, Lisp_Object prop)
19784 {
19785 Lisp_Object position, object = it->object;
19786
19787 if (STRINGP (object))
19788 position = make_number (IT_STRING_CHARPOS (*it));
19789 else if (BUFFERP (object))
19790 {
19791 position = make_number (IT_CHARPOS (*it));
19792 object = it->window;
19793 }
19794 else
19795 return Qnil;
19796
19797 return Fget_char_property (position, prop, object);
19798 }
19799
19800 /* See if there's a line- or wrap-prefix, and if so, push it on IT. */
19801
19802 static void
19803 handle_line_prefix (struct it *it)
19804 {
19805 Lisp_Object prefix;
19806
19807 if (it->continuation_lines_width > 0)
19808 {
19809 prefix = get_it_property (it, Qwrap_prefix);
19810 if (NILP (prefix))
19811 prefix = Vwrap_prefix;
19812 }
19813 else
19814 {
19815 prefix = get_it_property (it, Qline_prefix);
19816 if (NILP (prefix))
19817 prefix = Vline_prefix;
19818 }
19819 if (! NILP (prefix) && push_prefix_prop (it, prefix))
19820 {
19821 /* If the prefix is wider than the window, and we try to wrap
19822 it, it would acquire its own wrap prefix, and so on till the
19823 iterator stack overflows. So, don't wrap the prefix. */
19824 it->line_wrap = TRUNCATE;
19825 it->avoid_cursor_p = 1;
19826 }
19827 }
19828
19829 \f
19830
19831 /* Remove N glyphs at the start of a reversed IT->glyph_row. Called
19832 only for R2L lines from display_line and display_string, when they
19833 decide that too many glyphs were produced by PRODUCE_GLYPHS, and
19834 the line/string needs to be continued on the next glyph row. */
19835 static void
19836 unproduce_glyphs (struct it *it, int n)
19837 {
19838 struct glyph *glyph, *end;
19839
19840 eassert (it->glyph_row);
19841 eassert (it->glyph_row->reversed_p);
19842 eassert (it->area == TEXT_AREA);
19843 eassert (n <= it->glyph_row->used[TEXT_AREA]);
19844
19845 if (n > it->glyph_row->used[TEXT_AREA])
19846 n = it->glyph_row->used[TEXT_AREA];
19847 glyph = it->glyph_row->glyphs[TEXT_AREA] + n;
19848 end = it->glyph_row->glyphs[TEXT_AREA] + it->glyph_row->used[TEXT_AREA];
19849 for ( ; glyph < end; glyph++)
19850 glyph[-n] = *glyph;
19851 }
19852
19853 /* Find the positions in a bidi-reordered ROW to serve as ROW->minpos
19854 and ROW->maxpos. */
19855 static void
19856 find_row_edges (struct it *it, struct glyph_row *row,
19857 ptrdiff_t min_pos, ptrdiff_t min_bpos,
19858 ptrdiff_t max_pos, ptrdiff_t max_bpos)
19859 {
19860 /* FIXME: Revisit this when glyph ``spilling'' in continuation
19861 lines' rows is implemented for bidi-reordered rows. */
19862
19863 /* ROW->minpos is the value of min_pos, the minimal buffer position
19864 we have in ROW, or ROW->start.pos if that is smaller. */
19865 if (min_pos <= ZV && min_pos < row->start.pos.charpos)
19866 SET_TEXT_POS (row->minpos, min_pos, min_bpos);
19867 else
19868 /* We didn't find buffer positions smaller than ROW->start, or
19869 didn't find _any_ valid buffer positions in any of the glyphs,
19870 so we must trust the iterator's computed positions. */
19871 row->minpos = row->start.pos;
19872 if (max_pos <= 0)
19873 {
19874 max_pos = CHARPOS (it->current.pos);
19875 max_bpos = BYTEPOS (it->current.pos);
19876 }
19877
19878 /* Here are the various use-cases for ending the row, and the
19879 corresponding values for ROW->maxpos:
19880
19881 Line ends in a newline from buffer eol_pos + 1
19882 Line is continued from buffer max_pos + 1
19883 Line is truncated on right it->current.pos
19884 Line ends in a newline from string max_pos + 1(*)
19885 (*) + 1 only when line ends in a forward scan
19886 Line is continued from string max_pos
19887 Line is continued from display vector max_pos
19888 Line is entirely from a string min_pos == max_pos
19889 Line is entirely from a display vector min_pos == max_pos
19890 Line that ends at ZV ZV
19891
19892 If you discover other use-cases, please add them here as
19893 appropriate. */
19894 if (row->ends_at_zv_p)
19895 row->maxpos = it->current.pos;
19896 else if (row->used[TEXT_AREA])
19897 {
19898 int seen_this_string = 0;
19899 struct glyph_row *r1 = row - 1;
19900
19901 /* Did we see the same display string on the previous row? */
19902 if (STRINGP (it->object)
19903 /* this is not the first row */
19904 && row > it->w->desired_matrix->rows
19905 /* previous row is not the header line */
19906 && !r1->mode_line_p
19907 /* previous row also ends in a newline from a string */
19908 && r1->ends_in_newline_from_string_p)
19909 {
19910 struct glyph *start, *end;
19911
19912 /* Search for the last glyph of the previous row that came
19913 from buffer or string. Depending on whether the row is
19914 L2R or R2L, we need to process it front to back or the
19915 other way round. */
19916 if (!r1->reversed_p)
19917 {
19918 start = r1->glyphs[TEXT_AREA];
19919 end = start + r1->used[TEXT_AREA];
19920 /* Glyphs inserted by redisplay have nil as their object. */
19921 while (end > start
19922 && NILP ((end - 1)->object)
19923 && (end - 1)->charpos <= 0)
19924 --end;
19925 if (end > start)
19926 {
19927 if (EQ ((end - 1)->object, it->object))
19928 seen_this_string = 1;
19929 }
19930 else
19931 /* If all the glyphs of the previous row were inserted
19932 by redisplay, it means the previous row was
19933 produced from a single newline, which is only
19934 possible if that newline came from the same string
19935 as the one which produced this ROW. */
19936 seen_this_string = 1;
19937 }
19938 else
19939 {
19940 end = r1->glyphs[TEXT_AREA] - 1;
19941 start = end + r1->used[TEXT_AREA];
19942 while (end < start
19943 && NILP ((end + 1)->object)
19944 && (end + 1)->charpos <= 0)
19945 ++end;
19946 if (end < start)
19947 {
19948 if (EQ ((end + 1)->object, it->object))
19949 seen_this_string = 1;
19950 }
19951 else
19952 seen_this_string = 1;
19953 }
19954 }
19955 /* Take note of each display string that covers a newline only
19956 once, the first time we see it. This is for when a display
19957 string includes more than one newline in it. */
19958 if (row->ends_in_newline_from_string_p && !seen_this_string)
19959 {
19960 /* If we were scanning the buffer forward when we displayed
19961 the string, we want to account for at least one buffer
19962 position that belongs to this row (position covered by
19963 the display string), so that cursor positioning will
19964 consider this row as a candidate when point is at the end
19965 of the visual line represented by this row. This is not
19966 required when scanning back, because max_pos will already
19967 have a much larger value. */
19968 if (CHARPOS (row->end.pos) > max_pos)
19969 INC_BOTH (max_pos, max_bpos);
19970 SET_TEXT_POS (row->maxpos, max_pos, max_bpos);
19971 }
19972 else if (CHARPOS (it->eol_pos) > 0)
19973 SET_TEXT_POS (row->maxpos,
19974 CHARPOS (it->eol_pos) + 1, BYTEPOS (it->eol_pos) + 1);
19975 else if (row->continued_p)
19976 {
19977 /* If max_pos is different from IT's current position, it
19978 means IT->method does not belong to the display element
19979 at max_pos. However, it also means that the display
19980 element at max_pos was displayed in its entirety on this
19981 line, which is equivalent to saying that the next line
19982 starts at the next buffer position. */
19983 if (IT_CHARPOS (*it) == max_pos && it->method != GET_FROM_BUFFER)
19984 SET_TEXT_POS (row->maxpos, max_pos, max_bpos);
19985 else
19986 {
19987 INC_BOTH (max_pos, max_bpos);
19988 SET_TEXT_POS (row->maxpos, max_pos, max_bpos);
19989 }
19990 }
19991 else if (row->truncated_on_right_p)
19992 /* display_line already called reseat_at_next_visible_line_start,
19993 which puts the iterator at the beginning of the next line, in
19994 the logical order. */
19995 row->maxpos = it->current.pos;
19996 else if (max_pos == min_pos && it->method != GET_FROM_BUFFER)
19997 /* A line that is entirely from a string/image/stretch... */
19998 row->maxpos = row->minpos;
19999 else
20000 emacs_abort ();
20001 }
20002 else
20003 row->maxpos = it->current.pos;
20004 }
20005
20006 /* Construct the glyph row IT->glyph_row in the desired matrix of
20007 IT->w from text at the current position of IT. See dispextern.h
20008 for an overview of struct it. Value is non-zero if
20009 IT->glyph_row displays text, as opposed to a line displaying ZV
20010 only. */
20011
20012 static int
20013 display_line (struct it *it)
20014 {
20015 struct glyph_row *row = it->glyph_row;
20016 Lisp_Object overlay_arrow_string;
20017 struct it wrap_it;
20018 void *wrap_data = NULL;
20019 int may_wrap = 0, wrap_x IF_LINT (= 0);
20020 int wrap_row_used = -1;
20021 int wrap_row_ascent IF_LINT (= 0), wrap_row_height IF_LINT (= 0);
20022 int wrap_row_phys_ascent IF_LINT (= 0), wrap_row_phys_height IF_LINT (= 0);
20023 int wrap_row_extra_line_spacing IF_LINT (= 0);
20024 ptrdiff_t wrap_row_min_pos IF_LINT (= 0), wrap_row_min_bpos IF_LINT (= 0);
20025 ptrdiff_t wrap_row_max_pos IF_LINT (= 0), wrap_row_max_bpos IF_LINT (= 0);
20026 int cvpos;
20027 ptrdiff_t min_pos = ZV + 1, max_pos = 0;
20028 ptrdiff_t min_bpos IF_LINT (= 0), max_bpos IF_LINT (= 0);
20029 bool pending_handle_line_prefix = false;
20030
20031 /* We always start displaying at hpos zero even if hscrolled. */
20032 eassert (it->hpos == 0 && it->current_x == 0);
20033
20034 if (MATRIX_ROW_VPOS (row, it->w->desired_matrix)
20035 >= it->w->desired_matrix->nrows)
20036 {
20037 it->w->nrows_scale_factor++;
20038 it->f->fonts_changed = 1;
20039 return 0;
20040 }
20041
20042 /* Clear the result glyph row and enable it. */
20043 prepare_desired_row (it->w, row, false);
20044
20045 row->y = it->current_y;
20046 row->start = it->start;
20047 row->continuation_lines_width = it->continuation_lines_width;
20048 row->displays_text_p = 1;
20049 row->starts_in_middle_of_char_p = it->starts_in_middle_of_char_p;
20050 it->starts_in_middle_of_char_p = 0;
20051
20052 /* Arrange the overlays nicely for our purposes. Usually, we call
20053 display_line on only one line at a time, in which case this
20054 can't really hurt too much, or we call it on lines which appear
20055 one after another in the buffer, in which case all calls to
20056 recenter_overlay_lists but the first will be pretty cheap. */
20057 recenter_overlay_lists (current_buffer, IT_CHARPOS (*it));
20058
20059 /* Move over display elements that are not visible because we are
20060 hscrolled. This may stop at an x-position < IT->first_visible_x
20061 if the first glyph is partially visible or if we hit a line end. */
20062 if (it->current_x < it->first_visible_x)
20063 {
20064 enum move_it_result move_result;
20065
20066 this_line_min_pos = row->start.pos;
20067 move_result = move_it_in_display_line_to (it, ZV, it->first_visible_x,
20068 MOVE_TO_POS | MOVE_TO_X);
20069 /* If we are under a large hscroll, move_it_in_display_line_to
20070 could hit the end of the line without reaching
20071 it->first_visible_x. Pretend that we did reach it. This is
20072 especially important on a TTY, where we will call
20073 extend_face_to_end_of_line, which needs to know how many
20074 blank glyphs to produce. */
20075 if (it->current_x < it->first_visible_x
20076 && (move_result == MOVE_NEWLINE_OR_CR
20077 || move_result == MOVE_POS_MATCH_OR_ZV))
20078 it->current_x = it->first_visible_x;
20079
20080 /* Record the smallest positions seen while we moved over
20081 display elements that are not visible. This is needed by
20082 redisplay_internal for optimizing the case where the cursor
20083 stays inside the same line. The rest of this function only
20084 considers positions that are actually displayed, so
20085 RECORD_MAX_MIN_POS will not otherwise record positions that
20086 are hscrolled to the left of the left edge of the window. */
20087 min_pos = CHARPOS (this_line_min_pos);
20088 min_bpos = BYTEPOS (this_line_min_pos);
20089 }
20090 else if (it->area == TEXT_AREA)
20091 {
20092 /* We only do this when not calling move_it_in_display_line_to
20093 above, because that function calls itself handle_line_prefix. */
20094 handle_line_prefix (it);
20095 }
20096 else
20097 {
20098 /* Line-prefix and wrap-prefix are always displayed in the text
20099 area. But if this is the first call to display_line after
20100 init_iterator, the iterator might have been set up to write
20101 into a marginal area, e.g. if the line begins with some
20102 display property that writes to the margins. So we need to
20103 wait with the call to handle_line_prefix until whatever
20104 writes to the margin has done its job. */
20105 pending_handle_line_prefix = true;
20106 }
20107
20108 /* Get the initial row height. This is either the height of the
20109 text hscrolled, if there is any, or zero. */
20110 row->ascent = it->max_ascent;
20111 row->height = it->max_ascent + it->max_descent;
20112 row->phys_ascent = it->max_phys_ascent;
20113 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
20114 row->extra_line_spacing = it->max_extra_line_spacing;
20115
20116 /* Utility macro to record max and min buffer positions seen until now. */
20117 #define RECORD_MAX_MIN_POS(IT) \
20118 do \
20119 { \
20120 int composition_p = !STRINGP ((IT)->string) \
20121 && ((IT)->what == IT_COMPOSITION); \
20122 ptrdiff_t current_pos = \
20123 composition_p ? (IT)->cmp_it.charpos \
20124 : IT_CHARPOS (*(IT)); \
20125 ptrdiff_t current_bpos = \
20126 composition_p ? CHAR_TO_BYTE (current_pos) \
20127 : IT_BYTEPOS (*(IT)); \
20128 if (current_pos < min_pos) \
20129 { \
20130 min_pos = current_pos; \
20131 min_bpos = current_bpos; \
20132 } \
20133 if (IT_CHARPOS (*it) > max_pos) \
20134 { \
20135 max_pos = IT_CHARPOS (*it); \
20136 max_bpos = IT_BYTEPOS (*it); \
20137 } \
20138 } \
20139 while (0)
20140
20141 /* Loop generating characters. The loop is left with IT on the next
20142 character to display. */
20143 while (1)
20144 {
20145 int n_glyphs_before, hpos_before, x_before;
20146 int x, nglyphs;
20147 int ascent = 0, descent = 0, phys_ascent = 0, phys_descent = 0;
20148
20149 /* Retrieve the next thing to display. Value is zero if end of
20150 buffer reached. */
20151 if (!get_next_display_element (it))
20152 {
20153 /* Maybe add a space at the end of this line that is used to
20154 display the cursor there under X. Set the charpos of the
20155 first glyph of blank lines not corresponding to any text
20156 to -1. */
20157 if (IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
20158 row->exact_window_width_line_p = 1;
20159 else if ((append_space_for_newline (it, 1) && row->used[TEXT_AREA] == 1)
20160 || row->used[TEXT_AREA] == 0)
20161 {
20162 row->glyphs[TEXT_AREA]->charpos = -1;
20163 row->displays_text_p = 0;
20164
20165 if (!NILP (BVAR (XBUFFER (it->w->contents), indicate_empty_lines))
20166 && (!MINI_WINDOW_P (it->w)
20167 || (minibuf_level && EQ (it->window, minibuf_window))))
20168 row->indicate_empty_line_p = 1;
20169 }
20170
20171 it->continuation_lines_width = 0;
20172 row->ends_at_zv_p = 1;
20173 /* A row that displays right-to-left text must always have
20174 its last face extended all the way to the end of line,
20175 even if this row ends in ZV, because we still write to
20176 the screen left to right. We also need to extend the
20177 last face if the default face is remapped to some
20178 different face, otherwise the functions that clear
20179 portions of the screen will clear with the default face's
20180 background color. */
20181 if (row->reversed_p
20182 || lookup_basic_face (it->f, DEFAULT_FACE_ID) != DEFAULT_FACE_ID)
20183 extend_face_to_end_of_line (it);
20184 break;
20185 }
20186
20187 /* Now, get the metrics of what we want to display. This also
20188 generates glyphs in `row' (which is IT->glyph_row). */
20189 n_glyphs_before = row->used[TEXT_AREA];
20190 x = it->current_x;
20191
20192 /* Remember the line height so far in case the next element doesn't
20193 fit on the line. */
20194 if (it->line_wrap != TRUNCATE)
20195 {
20196 ascent = it->max_ascent;
20197 descent = it->max_descent;
20198 phys_ascent = it->max_phys_ascent;
20199 phys_descent = it->max_phys_descent;
20200
20201 if (it->line_wrap == WORD_WRAP && it->area == TEXT_AREA)
20202 {
20203 if (IT_DISPLAYING_WHITESPACE (it))
20204 may_wrap = 1;
20205 else if (may_wrap)
20206 {
20207 SAVE_IT (wrap_it, *it, wrap_data);
20208 wrap_x = x;
20209 wrap_row_used = row->used[TEXT_AREA];
20210 wrap_row_ascent = row->ascent;
20211 wrap_row_height = row->height;
20212 wrap_row_phys_ascent = row->phys_ascent;
20213 wrap_row_phys_height = row->phys_height;
20214 wrap_row_extra_line_spacing = row->extra_line_spacing;
20215 wrap_row_min_pos = min_pos;
20216 wrap_row_min_bpos = min_bpos;
20217 wrap_row_max_pos = max_pos;
20218 wrap_row_max_bpos = max_bpos;
20219 may_wrap = 0;
20220 }
20221 }
20222 }
20223
20224 PRODUCE_GLYPHS (it);
20225
20226 /* If this display element was in marginal areas, continue with
20227 the next one. */
20228 if (it->area != TEXT_AREA)
20229 {
20230 row->ascent = max (row->ascent, it->max_ascent);
20231 row->height = max (row->height, it->max_ascent + it->max_descent);
20232 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
20233 row->phys_height = max (row->phys_height,
20234 it->max_phys_ascent + it->max_phys_descent);
20235 row->extra_line_spacing = max (row->extra_line_spacing,
20236 it->max_extra_line_spacing);
20237 set_iterator_to_next (it, 1);
20238 /* If we didn't handle the line/wrap prefix above, and the
20239 call to set_iterator_to_next just switched to TEXT_AREA,
20240 process the prefix now. */
20241 if (it->area == TEXT_AREA && pending_handle_line_prefix)
20242 {
20243 pending_handle_line_prefix = false;
20244 handle_line_prefix (it);
20245 }
20246 continue;
20247 }
20248
20249 /* Does the display element fit on the line? If we truncate
20250 lines, we should draw past the right edge of the window. If
20251 we don't truncate, we want to stop so that we can display the
20252 continuation glyph before the right margin. If lines are
20253 continued, there are two possible strategies for characters
20254 resulting in more than 1 glyph (e.g. tabs): Display as many
20255 glyphs as possible in this line and leave the rest for the
20256 continuation line, or display the whole element in the next
20257 line. Original redisplay did the former, so we do it also. */
20258 nglyphs = row->used[TEXT_AREA] - n_glyphs_before;
20259 hpos_before = it->hpos;
20260 x_before = x;
20261
20262 if (/* Not a newline. */
20263 nglyphs > 0
20264 /* Glyphs produced fit entirely in the line. */
20265 && it->current_x < it->last_visible_x)
20266 {
20267 it->hpos += nglyphs;
20268 row->ascent = max (row->ascent, it->max_ascent);
20269 row->height = max (row->height, it->max_ascent + it->max_descent);
20270 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
20271 row->phys_height = max (row->phys_height,
20272 it->max_phys_ascent + it->max_phys_descent);
20273 row->extra_line_spacing = max (row->extra_line_spacing,
20274 it->max_extra_line_spacing);
20275 if (it->current_x - it->pixel_width < it->first_visible_x
20276 /* In R2L rows, we arrange in extend_face_to_end_of_line
20277 to add a right offset to the line, by a suitable
20278 change to the stretch glyph that is the leftmost
20279 glyph of the line. */
20280 && !row->reversed_p)
20281 row->x = x - it->first_visible_x;
20282 /* Record the maximum and minimum buffer positions seen so
20283 far in glyphs that will be displayed by this row. */
20284 if (it->bidi_p)
20285 RECORD_MAX_MIN_POS (it);
20286 }
20287 else
20288 {
20289 int i, new_x;
20290 struct glyph *glyph;
20291
20292 for (i = 0; i < nglyphs; ++i, x = new_x)
20293 {
20294 /* Identify the glyphs added by the last call to
20295 PRODUCE_GLYPHS. In R2L rows, they are prepended to
20296 the previous glyphs. */
20297 if (!row->reversed_p)
20298 glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
20299 else
20300 glyph = row->glyphs[TEXT_AREA] + nglyphs - 1 - i;
20301 new_x = x + glyph->pixel_width;
20302
20303 if (/* Lines are continued. */
20304 it->line_wrap != TRUNCATE
20305 && (/* Glyph doesn't fit on the line. */
20306 new_x > it->last_visible_x
20307 /* Or it fits exactly on a window system frame. */
20308 || (new_x == it->last_visible_x
20309 && FRAME_WINDOW_P (it->f)
20310 && (row->reversed_p
20311 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20312 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)))))
20313 {
20314 /* End of a continued line. */
20315
20316 if (it->hpos == 0
20317 || (new_x == it->last_visible_x
20318 && FRAME_WINDOW_P (it->f)
20319 && (row->reversed_p
20320 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20321 : WINDOW_RIGHT_FRINGE_WIDTH (it->w))))
20322 {
20323 /* Current glyph is the only one on the line or
20324 fits exactly on the line. We must continue
20325 the line because we can't draw the cursor
20326 after the glyph. */
20327 row->continued_p = 1;
20328 it->current_x = new_x;
20329 it->continuation_lines_width += new_x;
20330 ++it->hpos;
20331 if (i == nglyphs - 1)
20332 {
20333 /* If line-wrap is on, check if a previous
20334 wrap point was found. */
20335 if (!IT_OVERFLOW_NEWLINE_INTO_FRINGE (it)
20336 && wrap_row_used > 0
20337 /* Even if there is a previous wrap
20338 point, continue the line here as
20339 usual, if (i) the previous character
20340 was a space or tab AND (ii) the
20341 current character is not. */
20342 && (!may_wrap
20343 || IT_DISPLAYING_WHITESPACE (it)))
20344 goto back_to_wrap;
20345
20346 /* Record the maximum and minimum buffer
20347 positions seen so far in glyphs that will be
20348 displayed by this row. */
20349 if (it->bidi_p)
20350 RECORD_MAX_MIN_POS (it);
20351 set_iterator_to_next (it, 1);
20352 if (IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
20353 {
20354 if (!get_next_display_element (it))
20355 {
20356 row->exact_window_width_line_p = 1;
20357 it->continuation_lines_width = 0;
20358 row->continued_p = 0;
20359 row->ends_at_zv_p = 1;
20360 }
20361 else if (ITERATOR_AT_END_OF_LINE_P (it))
20362 {
20363 row->continued_p = 0;
20364 row->exact_window_width_line_p = 1;
20365 }
20366 /* If line-wrap is on, check if a
20367 previous wrap point was found. */
20368 else if (wrap_row_used > 0
20369 /* Even if there is a previous wrap
20370 point, continue the line here as
20371 usual, if (i) the previous character
20372 was a space or tab AND (ii) the
20373 current character is not. */
20374 && (!may_wrap
20375 || IT_DISPLAYING_WHITESPACE (it)))
20376 goto back_to_wrap;
20377
20378 }
20379 }
20380 else if (it->bidi_p)
20381 RECORD_MAX_MIN_POS (it);
20382 if (WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
20383 || WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0)
20384 extend_face_to_end_of_line (it);
20385 }
20386 else if (CHAR_GLYPH_PADDING_P (*glyph)
20387 && !FRAME_WINDOW_P (it->f))
20388 {
20389 /* A padding glyph that doesn't fit on this line.
20390 This means the whole character doesn't fit
20391 on the line. */
20392 if (row->reversed_p)
20393 unproduce_glyphs (it, row->used[TEXT_AREA]
20394 - n_glyphs_before);
20395 row->used[TEXT_AREA] = n_glyphs_before;
20396
20397 /* Fill the rest of the row with continuation
20398 glyphs like in 20.x. */
20399 while (row->glyphs[TEXT_AREA] + row->used[TEXT_AREA]
20400 < row->glyphs[1 + TEXT_AREA])
20401 produce_special_glyphs (it, IT_CONTINUATION);
20402
20403 row->continued_p = 1;
20404 it->current_x = x_before;
20405 it->continuation_lines_width += x_before;
20406
20407 /* Restore the height to what it was before the
20408 element not fitting on the line. */
20409 it->max_ascent = ascent;
20410 it->max_descent = descent;
20411 it->max_phys_ascent = phys_ascent;
20412 it->max_phys_descent = phys_descent;
20413 if (WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
20414 || WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0)
20415 extend_face_to_end_of_line (it);
20416 }
20417 else if (wrap_row_used > 0)
20418 {
20419 back_to_wrap:
20420 if (row->reversed_p)
20421 unproduce_glyphs (it,
20422 row->used[TEXT_AREA] - wrap_row_used);
20423 RESTORE_IT (it, &wrap_it, wrap_data);
20424 it->continuation_lines_width += wrap_x;
20425 row->used[TEXT_AREA] = wrap_row_used;
20426 row->ascent = wrap_row_ascent;
20427 row->height = wrap_row_height;
20428 row->phys_ascent = wrap_row_phys_ascent;
20429 row->phys_height = wrap_row_phys_height;
20430 row->extra_line_spacing = wrap_row_extra_line_spacing;
20431 min_pos = wrap_row_min_pos;
20432 min_bpos = wrap_row_min_bpos;
20433 max_pos = wrap_row_max_pos;
20434 max_bpos = wrap_row_max_bpos;
20435 row->continued_p = 1;
20436 row->ends_at_zv_p = 0;
20437 row->exact_window_width_line_p = 0;
20438 it->continuation_lines_width += x;
20439
20440 /* Make sure that a non-default face is extended
20441 up to the right margin of the window. */
20442 extend_face_to_end_of_line (it);
20443 }
20444 else if (it->c == '\t' && FRAME_WINDOW_P (it->f))
20445 {
20446 /* A TAB that extends past the right edge of the
20447 window. This produces a single glyph on
20448 window system frames. We leave the glyph in
20449 this row and let it fill the row, but don't
20450 consume the TAB. */
20451 if ((row->reversed_p
20452 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20453 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)) == 0)
20454 produce_special_glyphs (it, IT_CONTINUATION);
20455 it->continuation_lines_width += it->last_visible_x;
20456 row->ends_in_middle_of_char_p = 1;
20457 row->continued_p = 1;
20458 glyph->pixel_width = it->last_visible_x - x;
20459 it->starts_in_middle_of_char_p = 1;
20460 if (WINDOW_LEFT_MARGIN_WIDTH (it->w) > 0
20461 || WINDOW_RIGHT_MARGIN_WIDTH (it->w) > 0)
20462 extend_face_to_end_of_line (it);
20463 }
20464 else
20465 {
20466 /* Something other than a TAB that draws past
20467 the right edge of the window. Restore
20468 positions to values before the element. */
20469 if (row->reversed_p)
20470 unproduce_glyphs (it, row->used[TEXT_AREA]
20471 - (n_glyphs_before + i));
20472 row->used[TEXT_AREA] = n_glyphs_before + i;
20473
20474 /* Display continuation glyphs. */
20475 it->current_x = x_before;
20476 it->continuation_lines_width += x;
20477 if (!FRAME_WINDOW_P (it->f)
20478 || (row->reversed_p
20479 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20480 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)) == 0)
20481 produce_special_glyphs (it, IT_CONTINUATION);
20482 row->continued_p = 1;
20483
20484 extend_face_to_end_of_line (it);
20485
20486 if (nglyphs > 1 && i > 0)
20487 {
20488 row->ends_in_middle_of_char_p = 1;
20489 it->starts_in_middle_of_char_p = 1;
20490 }
20491
20492 /* Restore the height to what it was before the
20493 element not fitting on the line. */
20494 it->max_ascent = ascent;
20495 it->max_descent = descent;
20496 it->max_phys_ascent = phys_ascent;
20497 it->max_phys_descent = phys_descent;
20498 }
20499
20500 break;
20501 }
20502 else if (new_x > it->first_visible_x)
20503 {
20504 /* Increment number of glyphs actually displayed. */
20505 ++it->hpos;
20506
20507 /* Record the maximum and minimum buffer positions
20508 seen so far in glyphs that will be displayed by
20509 this row. */
20510 if (it->bidi_p)
20511 RECORD_MAX_MIN_POS (it);
20512
20513 if (x < it->first_visible_x && !row->reversed_p)
20514 /* Glyph is partially visible, i.e. row starts at
20515 negative X position. Don't do that in R2L
20516 rows, where we arrange to add a right offset to
20517 the line in extend_face_to_end_of_line, by a
20518 suitable change to the stretch glyph that is
20519 the leftmost glyph of the line. */
20520 row->x = x - it->first_visible_x;
20521 /* When the last glyph of an R2L row only fits
20522 partially on the line, we need to set row->x to a
20523 negative offset, so that the leftmost glyph is
20524 the one that is partially visible. But if we are
20525 going to produce the truncation glyph, this will
20526 be taken care of in produce_special_glyphs. */
20527 if (row->reversed_p
20528 && new_x > it->last_visible_x
20529 && !(it->line_wrap == TRUNCATE
20530 && WINDOW_LEFT_FRINGE_WIDTH (it->w) == 0))
20531 {
20532 eassert (FRAME_WINDOW_P (it->f));
20533 row->x = it->last_visible_x - new_x;
20534 }
20535 }
20536 else
20537 {
20538 /* Glyph is completely off the left margin of the
20539 window. This should not happen because of the
20540 move_it_in_display_line at the start of this
20541 function, unless the text display area of the
20542 window is empty. */
20543 eassert (it->first_visible_x <= it->last_visible_x);
20544 }
20545 }
20546 /* Even if this display element produced no glyphs at all,
20547 we want to record its position. */
20548 if (it->bidi_p && nglyphs == 0)
20549 RECORD_MAX_MIN_POS (it);
20550
20551 row->ascent = max (row->ascent, it->max_ascent);
20552 row->height = max (row->height, it->max_ascent + it->max_descent);
20553 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
20554 row->phys_height = max (row->phys_height,
20555 it->max_phys_ascent + it->max_phys_descent);
20556 row->extra_line_spacing = max (row->extra_line_spacing,
20557 it->max_extra_line_spacing);
20558
20559 /* End of this display line if row is continued. */
20560 if (row->continued_p || row->ends_at_zv_p)
20561 break;
20562 }
20563
20564 at_end_of_line:
20565 /* Is this a line end? If yes, we're also done, after making
20566 sure that a non-default face is extended up to the right
20567 margin of the window. */
20568 if (ITERATOR_AT_END_OF_LINE_P (it))
20569 {
20570 int used_before = row->used[TEXT_AREA];
20571
20572 row->ends_in_newline_from_string_p = STRINGP (it->object);
20573
20574 /* Add a space at the end of the line that is used to
20575 display the cursor there. */
20576 if (!IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
20577 append_space_for_newline (it, 0);
20578
20579 /* Extend the face to the end of the line. */
20580 extend_face_to_end_of_line (it);
20581
20582 /* Make sure we have the position. */
20583 if (used_before == 0)
20584 row->glyphs[TEXT_AREA]->charpos = CHARPOS (it->position);
20585
20586 /* Record the position of the newline, for use in
20587 find_row_edges. */
20588 it->eol_pos = it->current.pos;
20589
20590 /* Consume the line end. This skips over invisible lines. */
20591 set_iterator_to_next (it, 1);
20592 it->continuation_lines_width = 0;
20593 break;
20594 }
20595
20596 /* Proceed with next display element. Note that this skips
20597 over lines invisible because of selective display. */
20598 set_iterator_to_next (it, 1);
20599
20600 /* If we truncate lines, we are done when the last displayed
20601 glyphs reach past the right margin of the window. */
20602 if (it->line_wrap == TRUNCATE
20603 && ((FRAME_WINDOW_P (it->f)
20604 /* Images are preprocessed in produce_image_glyph such
20605 that they are cropped at the right edge of the
20606 window, so an image glyph will always end exactly at
20607 last_visible_x, even if there's no right fringe. */
20608 && ((row->reversed_p
20609 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20610 : WINDOW_RIGHT_FRINGE_WIDTH (it->w))
20611 || it->what == IT_IMAGE))
20612 ? (it->current_x >= it->last_visible_x)
20613 : (it->current_x > it->last_visible_x)))
20614 {
20615 /* Maybe add truncation glyphs. */
20616 if (!FRAME_WINDOW_P (it->f)
20617 || (row->reversed_p
20618 ? WINDOW_LEFT_FRINGE_WIDTH (it->w)
20619 : WINDOW_RIGHT_FRINGE_WIDTH (it->w)) == 0)
20620 {
20621 int i, n;
20622
20623 if (!row->reversed_p)
20624 {
20625 for (i = row->used[TEXT_AREA] - 1; i > 0; --i)
20626 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][i]))
20627 break;
20628 }
20629 else
20630 {
20631 for (i = 0; i < row->used[TEXT_AREA]; i++)
20632 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][i]))
20633 break;
20634 /* Remove any padding glyphs at the front of ROW, to
20635 make room for the truncation glyphs we will be
20636 adding below. The loop below always inserts at
20637 least one truncation glyph, so also remove the
20638 last glyph added to ROW. */
20639 unproduce_glyphs (it, i + 1);
20640 /* Adjust i for the loop below. */
20641 i = row->used[TEXT_AREA] - (i + 1);
20642 }
20643
20644 /* produce_special_glyphs overwrites the last glyph, so
20645 we don't want that if we want to keep that last
20646 glyph, which means it's an image. */
20647 if (it->current_x > it->last_visible_x)
20648 {
20649 it->current_x = x_before;
20650 if (!FRAME_WINDOW_P (it->f))
20651 {
20652 for (n = row->used[TEXT_AREA]; i < n; ++i)
20653 {
20654 row->used[TEXT_AREA] = i;
20655 produce_special_glyphs (it, IT_TRUNCATION);
20656 }
20657 }
20658 else
20659 {
20660 row->used[TEXT_AREA] = i;
20661 produce_special_glyphs (it, IT_TRUNCATION);
20662 }
20663 it->hpos = hpos_before;
20664 }
20665 }
20666 else if (IT_OVERFLOW_NEWLINE_INTO_FRINGE (it))
20667 {
20668 /* Don't truncate if we can overflow newline into fringe. */
20669 if (!get_next_display_element (it))
20670 {
20671 it->continuation_lines_width = 0;
20672 row->ends_at_zv_p = 1;
20673 row->exact_window_width_line_p = 1;
20674 break;
20675 }
20676 if (ITERATOR_AT_END_OF_LINE_P (it))
20677 {
20678 row->exact_window_width_line_p = 1;
20679 goto at_end_of_line;
20680 }
20681 it->current_x = x_before;
20682 it->hpos = hpos_before;
20683 }
20684
20685 row->truncated_on_right_p = 1;
20686 it->continuation_lines_width = 0;
20687 reseat_at_next_visible_line_start (it, 0);
20688 /* We insist below that IT's position be at ZV because in
20689 bidi-reordered lines the character at visible line start
20690 might not be the character that follows the newline in
20691 the logical order. */
20692 if (IT_BYTEPOS (*it) > BEG_BYTE)
20693 row->ends_at_zv_p =
20694 IT_BYTEPOS (*it) >= ZV_BYTE && FETCH_BYTE (ZV_BYTE - 1) != '\n';
20695 else
20696 row->ends_at_zv_p = false;
20697 break;
20698 }
20699 }
20700
20701 if (wrap_data)
20702 bidi_unshelve_cache (wrap_data, 1);
20703
20704 /* If line is not empty and hscrolled, maybe insert truncation glyphs
20705 at the left window margin. */
20706 if (it->first_visible_x
20707 && IT_CHARPOS (*it) != CHARPOS (row->start.pos))
20708 {
20709 if (!FRAME_WINDOW_P (it->f)
20710 || (((row->reversed_p
20711 ? WINDOW_RIGHT_FRINGE_WIDTH (it->w)
20712 : WINDOW_LEFT_FRINGE_WIDTH (it->w)) == 0)
20713 /* Don't let insert_left_trunc_glyphs overwrite the
20714 first glyph of the row if it is an image. */
20715 && row->glyphs[TEXT_AREA]->type != IMAGE_GLYPH))
20716 insert_left_trunc_glyphs (it);
20717 row->truncated_on_left_p = 1;
20718 }
20719
20720 /* Remember the position at which this line ends.
20721
20722 BIDI Note: any code that needs MATRIX_ROW_START/END_CHARPOS
20723 cannot be before the call to find_row_edges below, since that is
20724 where these positions are determined. */
20725 row->end = it->current;
20726 if (!it->bidi_p)
20727 {
20728 row->minpos = row->start.pos;
20729 row->maxpos = row->end.pos;
20730 }
20731 else
20732 {
20733 /* ROW->minpos and ROW->maxpos must be the smallest and
20734 `1 + the largest' buffer positions in ROW. But if ROW was
20735 bidi-reordered, these two positions can be anywhere in the
20736 row, so we must determine them now. */
20737 find_row_edges (it, row, min_pos, min_bpos, max_pos, max_bpos);
20738 }
20739
20740 /* If the start of this line is the overlay arrow-position, then
20741 mark this glyph row as the one containing the overlay arrow.
20742 This is clearly a mess with variable size fonts. It would be
20743 better to let it be displayed like cursors under X. */
20744 if ((MATRIX_ROW_DISPLAYS_TEXT_P (row) || !overlay_arrow_seen)
20745 && (overlay_arrow_string = overlay_arrow_at_row (it, row),
20746 !NILP (overlay_arrow_string)))
20747 {
20748 /* Overlay arrow in window redisplay is a fringe bitmap. */
20749 if (STRINGP (overlay_arrow_string))
20750 {
20751 struct glyph_row *arrow_row
20752 = get_overlay_arrow_glyph_row (it->w, overlay_arrow_string);
20753 struct glyph *glyph = arrow_row->glyphs[TEXT_AREA];
20754 struct glyph *arrow_end = glyph + arrow_row->used[TEXT_AREA];
20755 struct glyph *p = row->glyphs[TEXT_AREA];
20756 struct glyph *p2, *end;
20757
20758 /* Copy the arrow glyphs. */
20759 while (glyph < arrow_end)
20760 *p++ = *glyph++;
20761
20762 /* Throw away padding glyphs. */
20763 p2 = p;
20764 end = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA];
20765 while (p2 < end && CHAR_GLYPH_PADDING_P (*p2))
20766 ++p2;
20767 if (p2 > p)
20768 {
20769 while (p2 < end)
20770 *p++ = *p2++;
20771 row->used[TEXT_AREA] = p2 - row->glyphs[TEXT_AREA];
20772 }
20773 }
20774 else
20775 {
20776 eassert (INTEGERP (overlay_arrow_string));
20777 row->overlay_arrow_bitmap = XINT (overlay_arrow_string);
20778 }
20779 overlay_arrow_seen = 1;
20780 }
20781
20782 /* Highlight trailing whitespace. */
20783 if (!NILP (Vshow_trailing_whitespace))
20784 highlight_trailing_whitespace (it->f, it->glyph_row);
20785
20786 /* Compute pixel dimensions of this line. */
20787 compute_line_metrics (it);
20788
20789 /* Implementation note: No changes in the glyphs of ROW or in their
20790 faces can be done past this point, because compute_line_metrics
20791 computes ROW's hash value and stores it within the glyph_row
20792 structure. */
20793
20794 /* Record whether this row ends inside an ellipsis. */
20795 row->ends_in_ellipsis_p
20796 = (it->method == GET_FROM_DISPLAY_VECTOR
20797 && it->ellipsis_p);
20798
20799 /* Save fringe bitmaps in this row. */
20800 row->left_user_fringe_bitmap = it->left_user_fringe_bitmap;
20801 row->left_user_fringe_face_id = it->left_user_fringe_face_id;
20802 row->right_user_fringe_bitmap = it->right_user_fringe_bitmap;
20803 row->right_user_fringe_face_id = it->right_user_fringe_face_id;
20804
20805 it->left_user_fringe_bitmap = 0;
20806 it->left_user_fringe_face_id = 0;
20807 it->right_user_fringe_bitmap = 0;
20808 it->right_user_fringe_face_id = 0;
20809
20810 /* Maybe set the cursor. */
20811 cvpos = it->w->cursor.vpos;
20812 if ((cvpos < 0
20813 /* In bidi-reordered rows, keep checking for proper cursor
20814 position even if one has been found already, because buffer
20815 positions in such rows change non-linearly with ROW->VPOS,
20816 when a line is continued. One exception: when we are at ZV,
20817 display cursor on the first suitable glyph row, since all
20818 the empty rows after that also have their position set to ZV. */
20819 /* FIXME: Revisit this when glyph ``spilling'' in continuation
20820 lines' rows is implemented for bidi-reordered rows. */
20821 || (it->bidi_p
20822 && !MATRIX_ROW (it->w->desired_matrix, cvpos)->ends_at_zv_p))
20823 && PT >= MATRIX_ROW_START_CHARPOS (row)
20824 && PT <= MATRIX_ROW_END_CHARPOS (row)
20825 && cursor_row_p (row))
20826 set_cursor_from_row (it->w, row, it->w->desired_matrix, 0, 0, 0, 0);
20827
20828 /* Prepare for the next line. This line starts horizontally at (X
20829 HPOS) = (0 0). Vertical positions are incremented. As a
20830 convenience for the caller, IT->glyph_row is set to the next
20831 row to be used. */
20832 it->current_x = it->hpos = 0;
20833 it->current_y += row->height;
20834 SET_TEXT_POS (it->eol_pos, 0, 0);
20835 ++it->vpos;
20836 ++it->glyph_row;
20837 /* The next row should by default use the same value of the
20838 reversed_p flag as this one. set_iterator_to_next decides when
20839 it's a new paragraph, and PRODUCE_GLYPHS recomputes the value of
20840 the flag accordingly. */
20841 if (it->glyph_row < MATRIX_BOTTOM_TEXT_ROW (it->w->desired_matrix, it->w))
20842 it->glyph_row->reversed_p = row->reversed_p;
20843 it->start = row->end;
20844 return MATRIX_ROW_DISPLAYS_TEXT_P (row);
20845
20846 #undef RECORD_MAX_MIN_POS
20847 }
20848
20849 DEFUN ("current-bidi-paragraph-direction", Fcurrent_bidi_paragraph_direction,
20850 Scurrent_bidi_paragraph_direction, 0, 1, 0,
20851 doc: /* Return paragraph direction at point in BUFFER.
20852 Value is either `left-to-right' or `right-to-left'.
20853 If BUFFER is omitted or nil, it defaults to the current buffer.
20854
20855 Paragraph direction determines how the text in the paragraph is displayed.
20856 In left-to-right paragraphs, text begins at the left margin of the window
20857 and the reading direction is generally left to right. In right-to-left
20858 paragraphs, text begins at the right margin and is read from right to left.
20859
20860 See also `bidi-paragraph-direction'. */)
20861 (Lisp_Object buffer)
20862 {
20863 struct buffer *buf = current_buffer;
20864 struct buffer *old = buf;
20865
20866 if (! NILP (buffer))
20867 {
20868 CHECK_BUFFER (buffer);
20869 buf = XBUFFER (buffer);
20870 }
20871
20872 if (NILP (BVAR (buf, bidi_display_reordering))
20873 || NILP (BVAR (buf, enable_multibyte_characters))
20874 /* When we are loading loadup.el, the character property tables
20875 needed for bidi iteration are not yet available. */
20876 || !NILP (Vpurify_flag))
20877 return Qleft_to_right;
20878 else if (!NILP (BVAR (buf, bidi_paragraph_direction)))
20879 return BVAR (buf, bidi_paragraph_direction);
20880 else
20881 {
20882 /* Determine the direction from buffer text. We could try to
20883 use current_matrix if it is up to date, but this seems fast
20884 enough as it is. */
20885 struct bidi_it itb;
20886 ptrdiff_t pos = BUF_PT (buf);
20887 ptrdiff_t bytepos = BUF_PT_BYTE (buf);
20888 int c;
20889 void *itb_data = bidi_shelve_cache ();
20890
20891 set_buffer_temp (buf);
20892 /* bidi_paragraph_init finds the base direction of the paragraph
20893 by searching forward from paragraph start. We need the base
20894 direction of the current or _previous_ paragraph, so we need
20895 to make sure we are within that paragraph. To that end, find
20896 the previous non-empty line. */
20897 if (pos >= ZV && pos > BEGV)
20898 DEC_BOTH (pos, bytepos);
20899 AUTO_STRING (trailing_white_space, "[\f\t ]*\n");
20900 if (fast_looking_at (trailing_white_space,
20901 pos, bytepos, ZV, ZV_BYTE, Qnil) > 0)
20902 {
20903 while ((c = FETCH_BYTE (bytepos)) == '\n'
20904 || c == ' ' || c == '\t' || c == '\f')
20905 {
20906 if (bytepos <= BEGV_BYTE)
20907 break;
20908 bytepos--;
20909 pos--;
20910 }
20911 while (!CHAR_HEAD_P (FETCH_BYTE (bytepos)))
20912 bytepos--;
20913 }
20914 bidi_init_it (pos, bytepos, FRAME_WINDOW_P (SELECTED_FRAME ()), &itb);
20915 itb.paragraph_dir = NEUTRAL_DIR;
20916 itb.string.s = NULL;
20917 itb.string.lstring = Qnil;
20918 itb.string.bufpos = 0;
20919 itb.string.from_disp_str = 0;
20920 itb.string.unibyte = 0;
20921 /* We have no window to use here for ignoring window-specific
20922 overlays. Using NULL for window pointer will cause
20923 compute_display_string_pos to use the current buffer. */
20924 itb.w = NULL;
20925 bidi_paragraph_init (NEUTRAL_DIR, &itb, 1);
20926 bidi_unshelve_cache (itb_data, 0);
20927 set_buffer_temp (old);
20928 switch (itb.paragraph_dir)
20929 {
20930 case L2R:
20931 return Qleft_to_right;
20932 break;
20933 case R2L:
20934 return Qright_to_left;
20935 break;
20936 default:
20937 emacs_abort ();
20938 }
20939 }
20940 }
20941
20942 DEFUN ("bidi-find-overridden-directionality",
20943 Fbidi_find_overridden_directionality,
20944 Sbidi_find_overridden_directionality, 2, 3, 0,
20945 doc: /* Return position between FROM and TO where directionality was overridden.
20946
20947 This function returns the first character position in the specified
20948 region of OBJECT where there is a character whose `bidi-class' property
20949 is `L', but which was forced to display as `R' by a directional
20950 override, and likewise with characters whose `bidi-class' is `R'
20951 or `AL' that were forced to display as `L'.
20952
20953 If no such character is found, the function returns nil.
20954
20955 OBJECT is a Lisp string or buffer to search for overridden
20956 directionality, and defaults to the current buffer if nil or omitted.
20957 OBJECT can also be a window, in which case the function will search
20958 the buffer displayed in that window. Passing the window instead of
20959 a buffer is preferable when the buffer is displayed in some window,
20960 because this function will then be able to correctly account for
20961 window-specific overlays, which can affect the results.
20962
20963 Strong directional characters `L', `R', and `AL' can have their
20964 intrinsic directionality overridden by directional override
20965 control characters RLO \(u+202e) and LRO \(u+202d). See the
20966 function `get-char-code-property' for a way to inquire about
20967 the `bidi-class' property of a character. */)
20968 (Lisp_Object from, Lisp_Object to, Lisp_Object object)
20969 {
20970 struct buffer *buf = current_buffer;
20971 struct buffer *old = buf;
20972 struct window *w = NULL;
20973 bool frame_window_p = FRAME_WINDOW_P (SELECTED_FRAME ());
20974 struct bidi_it itb;
20975 ptrdiff_t from_pos, to_pos, from_bpos;
20976 void *itb_data;
20977
20978 if (!NILP (object))
20979 {
20980 if (BUFFERP (object))
20981 buf = XBUFFER (object);
20982 else if (WINDOWP (object))
20983 {
20984 w = decode_live_window (object);
20985 buf = XBUFFER (w->contents);
20986 frame_window_p = FRAME_WINDOW_P (XFRAME (w->frame));
20987 }
20988 else
20989 CHECK_STRING (object);
20990 }
20991
20992 if (STRINGP (object))
20993 {
20994 /* Characters in unibyte strings are always treated by bidi.c as
20995 strong LTR. */
20996 if (!STRING_MULTIBYTE (object)
20997 /* When we are loading loadup.el, the character property
20998 tables needed for bidi iteration are not yet
20999 available. */
21000 || !NILP (Vpurify_flag))
21001 return Qnil;
21002
21003 validate_subarray (object, from, to, SCHARS (object), &from_pos, &to_pos);
21004 if (from_pos >= SCHARS (object))
21005 return Qnil;
21006
21007 /* Set up the bidi iterator. */
21008 itb_data = bidi_shelve_cache ();
21009 itb.paragraph_dir = NEUTRAL_DIR;
21010 itb.string.lstring = object;
21011 itb.string.s = NULL;
21012 itb.string.schars = SCHARS (object);
21013 itb.string.bufpos = 0;
21014 itb.string.from_disp_str = 0;
21015 itb.string.unibyte = 0;
21016 itb.w = w;
21017 bidi_init_it (0, 0, frame_window_p, &itb);
21018 }
21019 else
21020 {
21021 /* Nothing this fancy can happen in unibyte buffers, or in a
21022 buffer that disabled reordering, or if FROM is at EOB. */
21023 if (NILP (BVAR (buf, bidi_display_reordering))
21024 || NILP (BVAR (buf, enable_multibyte_characters))
21025 /* When we are loading loadup.el, the character property
21026 tables needed for bidi iteration are not yet
21027 available. */
21028 || !NILP (Vpurify_flag))
21029 return Qnil;
21030
21031 set_buffer_temp (buf);
21032 validate_region (&from, &to);
21033 from_pos = XINT (from);
21034 to_pos = XINT (to);
21035 if (from_pos >= ZV)
21036 return Qnil;
21037
21038 /* Set up the bidi iterator. */
21039 itb_data = bidi_shelve_cache ();
21040 from_bpos = CHAR_TO_BYTE (from_pos);
21041 if (from_pos == BEGV)
21042 {
21043 itb.charpos = BEGV;
21044 itb.bytepos = BEGV_BYTE;
21045 }
21046 else if (FETCH_CHAR (from_bpos - 1) == '\n')
21047 {
21048 itb.charpos = from_pos;
21049 itb.bytepos = from_bpos;
21050 }
21051 else
21052 itb.charpos = find_newline_no_quit (from_pos, CHAR_TO_BYTE (from_pos),
21053 -1, &itb.bytepos);
21054 itb.paragraph_dir = NEUTRAL_DIR;
21055 itb.string.s = NULL;
21056 itb.string.lstring = Qnil;
21057 itb.string.bufpos = 0;
21058 itb.string.from_disp_str = 0;
21059 itb.string.unibyte = 0;
21060 itb.w = w;
21061 bidi_init_it (itb.charpos, itb.bytepos, frame_window_p, &itb);
21062 }
21063
21064 ptrdiff_t found;
21065 do {
21066 /* For the purposes of this function, the actual base direction of
21067 the paragraph doesn't matter, so just set it to L2R. */
21068 bidi_paragraph_init (L2R, &itb, 0);
21069 while ((found = bidi_find_first_overridden (&itb)) < from_pos)
21070 ;
21071 } while (found == ZV && itb.ch == '\n' && itb.charpos < to_pos);
21072
21073 bidi_unshelve_cache (itb_data, 0);
21074 set_buffer_temp (old);
21075
21076 return (from_pos <= found && found < to_pos) ? make_number (found) : Qnil;
21077 }
21078
21079 DEFUN ("move-point-visually", Fmove_point_visually,
21080 Smove_point_visually, 1, 1, 0,
21081 doc: /* Move point in the visual order in the specified DIRECTION.
21082 DIRECTION can be 1, meaning move to the right, or -1, which moves to the
21083 left.
21084
21085 Value is the new character position of point. */)
21086 (Lisp_Object direction)
21087 {
21088 struct window *w = XWINDOW (selected_window);
21089 struct buffer *b = XBUFFER (w->contents);
21090 struct glyph_row *row;
21091 int dir;
21092 Lisp_Object paragraph_dir;
21093
21094 #define ROW_GLYPH_NEWLINE_P(ROW,GLYPH) \
21095 (!(ROW)->continued_p \
21096 && NILP ((GLYPH)->object) \
21097 && (GLYPH)->type == CHAR_GLYPH \
21098 && (GLYPH)->u.ch == ' ' \
21099 && (GLYPH)->charpos >= 0 \
21100 && !(GLYPH)->avoid_cursor_p)
21101
21102 CHECK_NUMBER (direction);
21103 dir = XINT (direction);
21104 if (dir > 0)
21105 dir = 1;
21106 else
21107 dir = -1;
21108
21109 /* If current matrix is up-to-date, we can use the information
21110 recorded in the glyphs, at least as long as the goal is on the
21111 screen. */
21112 if (w->window_end_valid
21113 && !windows_or_buffers_changed
21114 && b
21115 && !b->clip_changed
21116 && !b->prevent_redisplay_optimizations_p
21117 && !window_outdated (w)
21118 /* We rely below on the cursor coordinates to be up to date, but
21119 we cannot trust them if some command moved point since the
21120 last complete redisplay. */
21121 && w->last_point == BUF_PT (b)
21122 && w->cursor.vpos >= 0
21123 && w->cursor.vpos < w->current_matrix->nrows
21124 && (row = MATRIX_ROW (w->current_matrix, w->cursor.vpos))->enabled_p)
21125 {
21126 struct glyph *g = row->glyphs[TEXT_AREA];
21127 struct glyph *e = dir > 0 ? g + row->used[TEXT_AREA] : g - 1;
21128 struct glyph *gpt = g + w->cursor.hpos;
21129
21130 for (g = gpt + dir; (dir > 0 ? g < e : g > e); g += dir)
21131 {
21132 if (BUFFERP (g->object) && g->charpos != PT)
21133 {
21134 SET_PT (g->charpos);
21135 w->cursor.vpos = -1;
21136 return make_number (PT);
21137 }
21138 else if (!NILP (g->object) && !EQ (g->object, gpt->object))
21139 {
21140 ptrdiff_t new_pos;
21141
21142 if (BUFFERP (gpt->object))
21143 {
21144 new_pos = PT;
21145 if ((gpt->resolved_level - row->reversed_p) % 2 == 0)
21146 new_pos += (row->reversed_p ? -dir : dir);
21147 else
21148 new_pos -= (row->reversed_p ? -dir : dir);
21149 }
21150 else if (BUFFERP (g->object))
21151 new_pos = g->charpos;
21152 else
21153 break;
21154 SET_PT (new_pos);
21155 w->cursor.vpos = -1;
21156 return make_number (PT);
21157 }
21158 else if (ROW_GLYPH_NEWLINE_P (row, g))
21159 {
21160 /* Glyphs inserted at the end of a non-empty line for
21161 positioning the cursor have zero charpos, so we must
21162 deduce the value of point by other means. */
21163 if (g->charpos > 0)
21164 SET_PT (g->charpos);
21165 else if (row->ends_at_zv_p && PT != ZV)
21166 SET_PT (ZV);
21167 else if (PT != MATRIX_ROW_END_CHARPOS (row) - 1)
21168 SET_PT (MATRIX_ROW_END_CHARPOS (row) - 1);
21169 else
21170 break;
21171 w->cursor.vpos = -1;
21172 return make_number (PT);
21173 }
21174 }
21175 if (g == e || NILP (g->object))
21176 {
21177 if (row->truncated_on_left_p || row->truncated_on_right_p)
21178 goto simulate_display;
21179 if (!row->reversed_p)
21180 row += dir;
21181 else
21182 row -= dir;
21183 if (row < MATRIX_FIRST_TEXT_ROW (w->current_matrix)
21184 || row > MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w))
21185 goto simulate_display;
21186
21187 if (dir > 0)
21188 {
21189 if (row->reversed_p && !row->continued_p)
21190 {
21191 SET_PT (MATRIX_ROW_END_CHARPOS (row) - 1);
21192 w->cursor.vpos = -1;
21193 return make_number (PT);
21194 }
21195 g = row->glyphs[TEXT_AREA];
21196 e = g + row->used[TEXT_AREA];
21197 for ( ; g < e; g++)
21198 {
21199 if (BUFFERP (g->object)
21200 /* Empty lines have only one glyph, which stands
21201 for the newline, and whose charpos is the
21202 buffer position of the newline. */
21203 || ROW_GLYPH_NEWLINE_P (row, g)
21204 /* When the buffer ends in a newline, the line at
21205 EOB also has one glyph, but its charpos is -1. */
21206 || (row->ends_at_zv_p
21207 && !row->reversed_p
21208 && NILP (g->object)
21209 && g->type == CHAR_GLYPH
21210 && g->u.ch == ' '))
21211 {
21212 if (g->charpos > 0)
21213 SET_PT (g->charpos);
21214 else if (!row->reversed_p
21215 && row->ends_at_zv_p
21216 && PT != ZV)
21217 SET_PT (ZV);
21218 else
21219 continue;
21220 w->cursor.vpos = -1;
21221 return make_number (PT);
21222 }
21223 }
21224 }
21225 else
21226 {
21227 if (!row->reversed_p && !row->continued_p)
21228 {
21229 SET_PT (MATRIX_ROW_END_CHARPOS (row) - 1);
21230 w->cursor.vpos = -1;
21231 return make_number (PT);
21232 }
21233 e = row->glyphs[TEXT_AREA];
21234 g = e + row->used[TEXT_AREA] - 1;
21235 for ( ; g >= e; g--)
21236 {
21237 if (BUFFERP (g->object)
21238 || (ROW_GLYPH_NEWLINE_P (row, g)
21239 && g->charpos > 0)
21240 /* Empty R2L lines on GUI frames have the buffer
21241 position of the newline stored in the stretch
21242 glyph. */
21243 || g->type == STRETCH_GLYPH
21244 || (row->ends_at_zv_p
21245 && row->reversed_p
21246 && NILP (g->object)
21247 && g->type == CHAR_GLYPH
21248 && g->u.ch == ' '))
21249 {
21250 if (g->charpos > 0)
21251 SET_PT (g->charpos);
21252 else if (row->reversed_p
21253 && row->ends_at_zv_p
21254 && PT != ZV)
21255 SET_PT (ZV);
21256 else
21257 continue;
21258 w->cursor.vpos = -1;
21259 return make_number (PT);
21260 }
21261 }
21262 }
21263 }
21264 }
21265
21266 simulate_display:
21267
21268 /* If we wind up here, we failed to move by using the glyphs, so we
21269 need to simulate display instead. */
21270
21271 if (b)
21272 paragraph_dir = Fcurrent_bidi_paragraph_direction (w->contents);
21273 else
21274 paragraph_dir = Qleft_to_right;
21275 if (EQ (paragraph_dir, Qright_to_left))
21276 dir = -dir;
21277 if (PT <= BEGV && dir < 0)
21278 xsignal0 (Qbeginning_of_buffer);
21279 else if (PT >= ZV && dir > 0)
21280 xsignal0 (Qend_of_buffer);
21281 else
21282 {
21283 struct text_pos pt;
21284 struct it it;
21285 int pt_x, target_x, pixel_width, pt_vpos;
21286 bool at_eol_p;
21287 bool overshoot_expected = false;
21288 bool target_is_eol_p = false;
21289
21290 /* Setup the arena. */
21291 SET_TEXT_POS (pt, PT, PT_BYTE);
21292 start_display (&it, w, pt);
21293
21294 if (it.cmp_it.id < 0
21295 && it.method == GET_FROM_STRING
21296 && it.area == TEXT_AREA
21297 && it.string_from_display_prop_p
21298 && (it.sp > 0 && it.stack[it.sp - 1].method == GET_FROM_BUFFER))
21299 overshoot_expected = true;
21300
21301 /* Find the X coordinate of point. We start from the beginning
21302 of this or previous line to make sure we are before point in
21303 the logical order (since the move_it_* functions can only
21304 move forward). */
21305 reseat:
21306 reseat_at_previous_visible_line_start (&it);
21307 it.current_x = it.hpos = it.current_y = it.vpos = 0;
21308 if (IT_CHARPOS (it) != PT)
21309 {
21310 move_it_to (&it, overshoot_expected ? PT - 1 : PT,
21311 -1, -1, -1, MOVE_TO_POS);
21312 /* If we missed point because the character there is
21313 displayed out of a display vector that has more than one
21314 glyph, retry expecting overshoot. */
21315 if (it.method == GET_FROM_DISPLAY_VECTOR
21316 && it.current.dpvec_index > 0
21317 && !overshoot_expected)
21318 {
21319 overshoot_expected = true;
21320 goto reseat;
21321 }
21322 else if (IT_CHARPOS (it) != PT && !overshoot_expected)
21323 move_it_in_display_line (&it, PT, -1, MOVE_TO_POS);
21324 }
21325 pt_x = it.current_x;
21326 pt_vpos = it.vpos;
21327 if (dir > 0 || overshoot_expected)
21328 {
21329 struct glyph_row *row = it.glyph_row;
21330
21331 /* When point is at beginning of line, we don't have
21332 information about the glyph there loaded into struct
21333 it. Calling get_next_display_element fixes that. */
21334 if (pt_x == 0)
21335 get_next_display_element (&it);
21336 at_eol_p = ITERATOR_AT_END_OF_LINE_P (&it);
21337 it.glyph_row = NULL;
21338 PRODUCE_GLYPHS (&it); /* compute it.pixel_width */
21339 it.glyph_row = row;
21340 /* PRODUCE_GLYPHS advances it.current_x, so we must restore
21341 it, lest it will become out of sync with it's buffer
21342 position. */
21343 it.current_x = pt_x;
21344 }
21345 else
21346 at_eol_p = ITERATOR_AT_END_OF_LINE_P (&it);
21347 pixel_width = it.pixel_width;
21348 if (overshoot_expected && at_eol_p)
21349 pixel_width = 0;
21350 else if (pixel_width <= 0)
21351 pixel_width = 1;
21352
21353 /* If there's a display string (or something similar) at point,
21354 we are actually at the glyph to the left of point, so we need
21355 to correct the X coordinate. */
21356 if (overshoot_expected)
21357 {
21358 if (it.bidi_p)
21359 pt_x += pixel_width * it.bidi_it.scan_dir;
21360 else
21361 pt_x += pixel_width;
21362 }
21363
21364 /* Compute target X coordinate, either to the left or to the
21365 right of point. On TTY frames, all characters have the same
21366 pixel width of 1, so we can use that. On GUI frames we don't
21367 have an easy way of getting at the pixel width of the
21368 character to the left of point, so we use a different method
21369 of getting to that place. */
21370 if (dir > 0)
21371 target_x = pt_x + pixel_width;
21372 else
21373 target_x = pt_x - (!FRAME_WINDOW_P (it.f)) * pixel_width;
21374
21375 /* Target X coordinate could be one line above or below the line
21376 of point, in which case we need to adjust the target X
21377 coordinate. Also, if moving to the left, we need to begin at
21378 the left edge of the point's screen line. */
21379 if (dir < 0)
21380 {
21381 if (pt_x > 0)
21382 {
21383 start_display (&it, w, pt);
21384 reseat_at_previous_visible_line_start (&it);
21385 it.current_x = it.current_y = it.hpos = 0;
21386 if (pt_vpos != 0)
21387 move_it_by_lines (&it, pt_vpos);
21388 }
21389 else
21390 {
21391 move_it_by_lines (&it, -1);
21392 target_x = it.last_visible_x - !FRAME_WINDOW_P (it.f);
21393 target_is_eol_p = true;
21394 /* Under word-wrap, we don't know the x coordinate of
21395 the last character displayed on the previous line,
21396 which immediately precedes the wrap point. To find
21397 out its x coordinate, we try moving to the right
21398 margin of the window, which will stop at the wrap
21399 point, and then reset target_x to point at the
21400 character that precedes the wrap point. This is not
21401 needed on GUI frames, because (see below) there we
21402 move from the left margin one grapheme cluster at a
21403 time, and stop when we hit the wrap point. */
21404 if (!FRAME_WINDOW_P (it.f) && it.line_wrap == WORD_WRAP)
21405 {
21406 void *it_data = NULL;
21407 struct it it2;
21408
21409 SAVE_IT (it2, it, it_data);
21410 move_it_in_display_line_to (&it, ZV, target_x,
21411 MOVE_TO_POS | MOVE_TO_X);
21412 /* If we arrived at target_x, that _is_ the last
21413 character on the previous line. */
21414 if (it.current_x != target_x)
21415 target_x = it.current_x - 1;
21416 RESTORE_IT (&it, &it2, it_data);
21417 }
21418 }
21419 }
21420 else
21421 {
21422 if (at_eol_p
21423 || (target_x >= it.last_visible_x
21424 && it.line_wrap != TRUNCATE))
21425 {
21426 if (pt_x > 0)
21427 move_it_by_lines (&it, 0);
21428 move_it_by_lines (&it, 1);
21429 target_x = 0;
21430 }
21431 }
21432
21433 /* Move to the target X coordinate. */
21434 #ifdef HAVE_WINDOW_SYSTEM
21435 /* On GUI frames, as we don't know the X coordinate of the
21436 character to the left of point, moving point to the left
21437 requires walking, one grapheme cluster at a time, until we
21438 find ourself at a place immediately to the left of the
21439 character at point. */
21440 if (FRAME_WINDOW_P (it.f) && dir < 0)
21441 {
21442 struct text_pos new_pos;
21443 enum move_it_result rc = MOVE_X_REACHED;
21444
21445 if (it.current_x == 0)
21446 get_next_display_element (&it);
21447 if (it.what == IT_COMPOSITION)
21448 {
21449 new_pos.charpos = it.cmp_it.charpos;
21450 new_pos.bytepos = -1;
21451 }
21452 else
21453 new_pos = it.current.pos;
21454
21455 while (it.current_x + it.pixel_width <= target_x
21456 && (rc == MOVE_X_REACHED
21457 /* Under word-wrap, move_it_in_display_line_to
21458 stops at correct coordinates, but sometimes
21459 returns MOVE_POS_MATCH_OR_ZV. */
21460 || (it.line_wrap == WORD_WRAP
21461 && rc == MOVE_POS_MATCH_OR_ZV)))
21462 {
21463 int new_x = it.current_x + it.pixel_width;
21464
21465 /* For composed characters, we want the position of the
21466 first character in the grapheme cluster (usually, the
21467 composition's base character), whereas it.current
21468 might give us the position of the _last_ one, e.g. if
21469 the composition is rendered in reverse due to bidi
21470 reordering. */
21471 if (it.what == IT_COMPOSITION)
21472 {
21473 new_pos.charpos = it.cmp_it.charpos;
21474 new_pos.bytepos = -1;
21475 }
21476 else
21477 new_pos = it.current.pos;
21478 if (new_x == it.current_x)
21479 new_x++;
21480 rc = move_it_in_display_line_to (&it, ZV, new_x,
21481 MOVE_TO_POS | MOVE_TO_X);
21482 if (ITERATOR_AT_END_OF_LINE_P (&it) && !target_is_eol_p)
21483 break;
21484 }
21485 /* The previous position we saw in the loop is the one we
21486 want. */
21487 if (new_pos.bytepos == -1)
21488 new_pos.bytepos = CHAR_TO_BYTE (new_pos.charpos);
21489 it.current.pos = new_pos;
21490 }
21491 else
21492 #endif
21493 if (it.current_x != target_x)
21494 move_it_in_display_line_to (&it, ZV, target_x, MOVE_TO_POS | MOVE_TO_X);
21495
21496 /* When lines are truncated, the above loop will stop at the
21497 window edge. But we want to get to the end of line, even if
21498 it is beyond the window edge; automatic hscroll will then
21499 scroll the window to show point as appropriate. */
21500 if (target_is_eol_p && it.line_wrap == TRUNCATE
21501 && get_next_display_element (&it))
21502 {
21503 struct text_pos new_pos = it.current.pos;
21504
21505 while (!ITERATOR_AT_END_OF_LINE_P (&it))
21506 {
21507 set_iterator_to_next (&it, 0);
21508 if (it.method == GET_FROM_BUFFER)
21509 new_pos = it.current.pos;
21510 if (!get_next_display_element (&it))
21511 break;
21512 }
21513
21514 it.current.pos = new_pos;
21515 }
21516
21517 /* If we ended up in a display string that covers point, move to
21518 buffer position to the right in the visual order. */
21519 if (dir > 0)
21520 {
21521 while (IT_CHARPOS (it) == PT)
21522 {
21523 set_iterator_to_next (&it, 0);
21524 if (!get_next_display_element (&it))
21525 break;
21526 }
21527 }
21528
21529 /* Move point to that position. */
21530 SET_PT_BOTH (IT_CHARPOS (it), IT_BYTEPOS (it));
21531 }
21532
21533 return make_number (PT);
21534
21535 #undef ROW_GLYPH_NEWLINE_P
21536 }
21537
21538 DEFUN ("bidi-resolved-levels", Fbidi_resolved_levels,
21539 Sbidi_resolved_levels, 0, 1, 0,
21540 doc: /* Return the resolved bidirectional levels of characters at VPOS.
21541
21542 The resolved levels are produced by the Emacs bidi reordering engine
21543 that implements the UBA, the Unicode Bidirectional Algorithm. Please
21544 read the Unicode Standard Annex 9 (UAX#9) for background information
21545 about these levels.
21546
21547 VPOS is the zero-based number of the current window's screen line
21548 for which to produce the resolved levels. If VPOS is nil or omitted,
21549 it defaults to the screen line of point. If the window displays a
21550 header line, VPOS of zero will report on the header line, and first
21551 line of text in the window will have VPOS of 1.
21552
21553 Value is an array of resolved levels, indexed by glyph number.
21554 Glyphs are numbered from zero starting from the beginning of the
21555 screen line, i.e. the left edge of the window for left-to-right lines
21556 and from the right edge for right-to-left lines. The resolved levels
21557 are produced only for the window's text area; text in display margins
21558 is not included.
21559
21560 If the selected window's display is not up-to-date, or if the specified
21561 screen line does not display text, this function returns nil. It is
21562 highly recommended to bind this function to some simple key, like F8,
21563 in order to avoid these problems.
21564
21565 This function exists mainly for testing the correctness of the
21566 Emacs UBA implementation, in particular with the test suite. */)
21567 (Lisp_Object vpos)
21568 {
21569 struct window *w = XWINDOW (selected_window);
21570 struct buffer *b = XBUFFER (w->contents);
21571 int nrow;
21572 struct glyph_row *row;
21573
21574 if (NILP (vpos))
21575 {
21576 int d1, d2, d3, d4, d5;
21577
21578 pos_visible_p (w, PT, &d1, &d2, &d3, &d4, &d5, &nrow);
21579 }
21580 else
21581 {
21582 CHECK_NUMBER_COERCE_MARKER (vpos);
21583 nrow = XINT (vpos);
21584 }
21585
21586 /* We require up-to-date glyph matrix for this window. */
21587 if (w->window_end_valid
21588 && !windows_or_buffers_changed
21589 && b
21590 && !b->clip_changed
21591 && !b->prevent_redisplay_optimizations_p
21592 && !window_outdated (w)
21593 && nrow >= 0
21594 && nrow < w->current_matrix->nrows
21595 && (row = MATRIX_ROW (w->current_matrix, nrow))->enabled_p
21596 && MATRIX_ROW_DISPLAYS_TEXT_P (row))
21597 {
21598 struct glyph *g, *e, *g1;
21599 int nglyphs, i;
21600 Lisp_Object levels;
21601
21602 if (!row->reversed_p) /* Left-to-right glyph row. */
21603 {
21604 g = g1 = row->glyphs[TEXT_AREA];
21605 e = g + row->used[TEXT_AREA];
21606
21607 /* Skip over glyphs at the start of the row that was
21608 generated by redisplay for its own needs. */
21609 while (g < e
21610 && NILP (g->object)
21611 && g->charpos < 0)
21612 g++;
21613 g1 = g;
21614
21615 /* Count the "interesting" glyphs in this row. */
21616 for (nglyphs = 0; g < e && !NILP (g->object); g++)
21617 nglyphs++;
21618
21619 /* Create and fill the array. */
21620 levels = make_uninit_vector (nglyphs);
21621 for (i = 0; g1 < g; i++, g1++)
21622 ASET (levels, i, make_number (g1->resolved_level));
21623 }
21624 else /* Right-to-left glyph row. */
21625 {
21626 g = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1;
21627 e = row->glyphs[TEXT_AREA] - 1;
21628 while (g > e
21629 && NILP (g->object)
21630 && g->charpos < 0)
21631 g--;
21632 g1 = g;
21633 for (nglyphs = 0; g > e && !NILP (g->object); g--)
21634 nglyphs++;
21635 levels = make_uninit_vector (nglyphs);
21636 for (i = 0; g1 > g; i++, g1--)
21637 ASET (levels, i, make_number (g1->resolved_level));
21638 }
21639 return levels;
21640 }
21641 else
21642 return Qnil;
21643 }
21644
21645
21646 \f
21647 /***********************************************************************
21648 Menu Bar
21649 ***********************************************************************/
21650
21651 /* Redisplay the menu bar in the frame for window W.
21652
21653 The menu bar of X frames that don't have X toolkit support is
21654 displayed in a special window W->frame->menu_bar_window.
21655
21656 The menu bar of terminal frames is treated specially as far as
21657 glyph matrices are concerned. Menu bar lines are not part of
21658 windows, so the update is done directly on the frame matrix rows
21659 for the menu bar. */
21660
21661 static void
21662 display_menu_bar (struct window *w)
21663 {
21664 struct frame *f = XFRAME (WINDOW_FRAME (w));
21665 struct it it;
21666 Lisp_Object items;
21667 int i;
21668
21669 /* Don't do all this for graphical frames. */
21670 #ifdef HAVE_NTGUI
21671 if (FRAME_W32_P (f))
21672 return;
21673 #endif
21674 #if defined (USE_X_TOOLKIT) || defined (USE_GTK)
21675 if (FRAME_X_P (f))
21676 return;
21677 #endif
21678
21679 #ifdef HAVE_NS
21680 if (FRAME_NS_P (f))
21681 return;
21682 #endif /* HAVE_NS */
21683
21684 #if defined (USE_X_TOOLKIT) || defined (USE_GTK)
21685 eassert (!FRAME_WINDOW_P (f));
21686 init_iterator (&it, w, -1, -1, f->desired_matrix->rows, MENU_FACE_ID);
21687 it.first_visible_x = 0;
21688 it.last_visible_x = FRAME_PIXEL_WIDTH (f);
21689 #elif defined (HAVE_X_WINDOWS) /* X without toolkit. */
21690 if (FRAME_WINDOW_P (f))
21691 {
21692 /* Menu bar lines are displayed in the desired matrix of the
21693 dummy window menu_bar_window. */
21694 struct window *menu_w;
21695 menu_w = XWINDOW (f->menu_bar_window);
21696 init_iterator (&it, menu_w, -1, -1, menu_w->desired_matrix->rows,
21697 MENU_FACE_ID);
21698 it.first_visible_x = 0;
21699 it.last_visible_x = FRAME_PIXEL_WIDTH (f);
21700 }
21701 else
21702 #endif /* not USE_X_TOOLKIT and not USE_GTK */
21703 {
21704 /* This is a TTY frame, i.e. character hpos/vpos are used as
21705 pixel x/y. */
21706 init_iterator (&it, w, -1, -1, f->desired_matrix->rows,
21707 MENU_FACE_ID);
21708 it.first_visible_x = 0;
21709 it.last_visible_x = FRAME_COLS (f);
21710 }
21711
21712 /* FIXME: This should be controlled by a user option. See the
21713 comments in redisplay_tool_bar and display_mode_line about
21714 this. */
21715 it.paragraph_embedding = L2R;
21716
21717 /* Clear all rows of the menu bar. */
21718 for (i = 0; i < FRAME_MENU_BAR_LINES (f); ++i)
21719 {
21720 struct glyph_row *row = it.glyph_row + i;
21721 clear_glyph_row (row);
21722 row->enabled_p = true;
21723 row->full_width_p = 1;
21724 row->reversed_p = false;
21725 }
21726
21727 /* Display all items of the menu bar. */
21728 items = FRAME_MENU_BAR_ITEMS (it.f);
21729 for (i = 0; i < ASIZE (items); i += 4)
21730 {
21731 Lisp_Object string;
21732
21733 /* Stop at nil string. */
21734 string = AREF (items, i + 1);
21735 if (NILP (string))
21736 break;
21737
21738 /* Remember where item was displayed. */
21739 ASET (items, i + 3, make_number (it.hpos));
21740
21741 /* Display the item, pad with one space. */
21742 if (it.current_x < it.last_visible_x)
21743 display_string (NULL, string, Qnil, 0, 0, &it,
21744 SCHARS (string) + 1, 0, 0, -1);
21745 }
21746
21747 /* Fill out the line with spaces. */
21748 if (it.current_x < it.last_visible_x)
21749 display_string ("", Qnil, Qnil, 0, 0, &it, -1, 0, 0, -1);
21750
21751 /* Compute the total height of the lines. */
21752 compute_line_metrics (&it);
21753 }
21754
21755 /* Deep copy of a glyph row, including the glyphs. */
21756 static void
21757 deep_copy_glyph_row (struct glyph_row *to, struct glyph_row *from)
21758 {
21759 struct glyph *pointers[1 + LAST_AREA];
21760 int to_used = to->used[TEXT_AREA];
21761
21762 /* Save glyph pointers of TO. */
21763 memcpy (pointers, to->glyphs, sizeof to->glyphs);
21764
21765 /* Do a structure assignment. */
21766 *to = *from;
21767
21768 /* Restore original glyph pointers of TO. */
21769 memcpy (to->glyphs, pointers, sizeof to->glyphs);
21770
21771 /* Copy the glyphs. */
21772 memcpy (to->glyphs[TEXT_AREA], from->glyphs[TEXT_AREA],
21773 min (from->used[TEXT_AREA], to_used) * sizeof (struct glyph));
21774
21775 /* If we filled only part of the TO row, fill the rest with
21776 space_glyph (which will display as empty space). */
21777 if (to_used > from->used[TEXT_AREA])
21778 fill_up_frame_row_with_spaces (to, to_used);
21779 }
21780
21781 /* Display one menu item on a TTY, by overwriting the glyphs in the
21782 frame F's desired glyph matrix with glyphs produced from the menu
21783 item text. Called from term.c to display TTY drop-down menus one
21784 item at a time.
21785
21786 ITEM_TEXT is the menu item text as a C string.
21787
21788 FACE_ID is the face ID to be used for this menu item. FACE_ID
21789 could specify one of 3 faces: a face for an enabled item, a face
21790 for a disabled item, or a face for a selected item.
21791
21792 X and Y are coordinates of the first glyph in the frame's desired
21793 matrix to be overwritten by the menu item. Since this is a TTY, Y
21794 is the zero-based number of the glyph row and X is the zero-based
21795 glyph number in the row, starting from left, where to start
21796 displaying the item.
21797
21798 SUBMENU non-zero means this menu item drops down a submenu, which
21799 should be indicated by displaying a proper visual cue after the
21800 item text. */
21801
21802 void
21803 display_tty_menu_item (const char *item_text, int width, int face_id,
21804 int x, int y, int submenu)
21805 {
21806 struct it it;
21807 struct frame *f = SELECTED_FRAME ();
21808 struct window *w = XWINDOW (f->selected_window);
21809 int saved_used, saved_truncated, saved_width, saved_reversed;
21810 struct glyph_row *row;
21811 size_t item_len = strlen (item_text);
21812
21813 eassert (FRAME_TERMCAP_P (f));
21814
21815 /* Don't write beyond the matrix's last row. This can happen for
21816 TTY screens that are not high enough to show the entire menu.
21817 (This is actually a bit of defensive programming, as
21818 tty_menu_display already limits the number of menu items to one
21819 less than the number of screen lines.) */
21820 if (y >= f->desired_matrix->nrows)
21821 return;
21822
21823 init_iterator (&it, w, -1, -1, f->desired_matrix->rows + y, MENU_FACE_ID);
21824 it.first_visible_x = 0;
21825 it.last_visible_x = FRAME_COLS (f) - 1;
21826 row = it.glyph_row;
21827 /* Start with the row contents from the current matrix. */
21828 deep_copy_glyph_row (row, f->current_matrix->rows + y);
21829 saved_width = row->full_width_p;
21830 row->full_width_p = 1;
21831 saved_reversed = row->reversed_p;
21832 row->reversed_p = 0;
21833 row->enabled_p = true;
21834
21835 /* Arrange for the menu item glyphs to start at (X,Y) and have the
21836 desired face. */
21837 eassert (x < f->desired_matrix->matrix_w);
21838 it.current_x = it.hpos = x;
21839 it.current_y = it.vpos = y;
21840 saved_used = row->used[TEXT_AREA];
21841 saved_truncated = row->truncated_on_right_p;
21842 row->used[TEXT_AREA] = x;
21843 it.face_id = face_id;
21844 it.line_wrap = TRUNCATE;
21845
21846 /* FIXME: This should be controlled by a user option. See the
21847 comments in redisplay_tool_bar and display_mode_line about this.
21848 Also, if paragraph_embedding could ever be R2L, changes will be
21849 needed to avoid shifting to the right the row characters in
21850 term.c:append_glyph. */
21851 it.paragraph_embedding = L2R;
21852
21853 /* Pad with a space on the left. */
21854 display_string (" ", Qnil, Qnil, 0, 0, &it, 1, 0, FRAME_COLS (f) - 1, -1);
21855 width--;
21856 /* Display the menu item, pad with spaces to WIDTH. */
21857 if (submenu)
21858 {
21859 display_string (item_text, Qnil, Qnil, 0, 0, &it,
21860 item_len, 0, FRAME_COLS (f) - 1, -1);
21861 width -= item_len;
21862 /* Indicate with " >" that there's a submenu. */
21863 display_string (" >", Qnil, Qnil, 0, 0, &it, width, 0,
21864 FRAME_COLS (f) - 1, -1);
21865 }
21866 else
21867 display_string (item_text, Qnil, Qnil, 0, 0, &it,
21868 width, 0, FRAME_COLS (f) - 1, -1);
21869
21870 row->used[TEXT_AREA] = max (saved_used, row->used[TEXT_AREA]);
21871 row->truncated_on_right_p = saved_truncated;
21872 row->hash = row_hash (row);
21873 row->full_width_p = saved_width;
21874 row->reversed_p = saved_reversed;
21875 }
21876 \f
21877 /***********************************************************************
21878 Mode Line
21879 ***********************************************************************/
21880
21881 /* Redisplay mode lines in the window tree whose root is WINDOW. If
21882 FORCE is non-zero, redisplay mode lines unconditionally.
21883 Otherwise, redisplay only mode lines that are garbaged. Value is
21884 the number of windows whose mode lines were redisplayed. */
21885
21886 static int
21887 redisplay_mode_lines (Lisp_Object window, bool force)
21888 {
21889 int nwindows = 0;
21890
21891 while (!NILP (window))
21892 {
21893 struct window *w = XWINDOW (window);
21894
21895 if (WINDOWP (w->contents))
21896 nwindows += redisplay_mode_lines (w->contents, force);
21897 else if (force
21898 || FRAME_GARBAGED_P (XFRAME (w->frame))
21899 || !MATRIX_MODE_LINE_ROW (w->current_matrix)->enabled_p)
21900 {
21901 struct text_pos lpoint;
21902 struct buffer *old = current_buffer;
21903
21904 /* Set the window's buffer for the mode line display. */
21905 SET_TEXT_POS (lpoint, PT, PT_BYTE);
21906 set_buffer_internal_1 (XBUFFER (w->contents));
21907
21908 /* Point refers normally to the selected window. For any
21909 other window, set up appropriate value. */
21910 if (!EQ (window, selected_window))
21911 {
21912 struct text_pos pt;
21913
21914 CLIP_TEXT_POS_FROM_MARKER (pt, w->pointm);
21915 TEMP_SET_PT_BOTH (CHARPOS (pt), BYTEPOS (pt));
21916 }
21917
21918 /* Display mode lines. */
21919 clear_glyph_matrix (w->desired_matrix);
21920 if (display_mode_lines (w))
21921 ++nwindows;
21922
21923 /* Restore old settings. */
21924 set_buffer_internal_1 (old);
21925 TEMP_SET_PT_BOTH (CHARPOS (lpoint), BYTEPOS (lpoint));
21926 }
21927
21928 window = w->next;
21929 }
21930
21931 return nwindows;
21932 }
21933
21934
21935 /* Display the mode and/or header line of window W. Value is the
21936 sum number of mode lines and header lines displayed. */
21937
21938 static int
21939 display_mode_lines (struct window *w)
21940 {
21941 Lisp_Object old_selected_window = selected_window;
21942 Lisp_Object old_selected_frame = selected_frame;
21943 Lisp_Object new_frame = w->frame;
21944 Lisp_Object old_frame_selected_window = XFRAME (new_frame)->selected_window;
21945 int n = 0;
21946
21947 selected_frame = new_frame;
21948 /* FIXME: If we were to allow the mode-line's computation changing the buffer
21949 or window's point, then we'd need select_window_1 here as well. */
21950 XSETWINDOW (selected_window, w);
21951 XFRAME (new_frame)->selected_window = selected_window;
21952
21953 /* These will be set while the mode line specs are processed. */
21954 line_number_displayed = 0;
21955 w->column_number_displayed = -1;
21956
21957 if (WINDOW_WANTS_MODELINE_P (w))
21958 {
21959 struct window *sel_w = XWINDOW (old_selected_window);
21960
21961 /* Select mode line face based on the real selected window. */
21962 display_mode_line (w, CURRENT_MODE_LINE_FACE_ID_3 (sel_w, sel_w, w),
21963 BVAR (current_buffer, mode_line_format));
21964 ++n;
21965 }
21966
21967 if (WINDOW_WANTS_HEADER_LINE_P (w))
21968 {
21969 display_mode_line (w, HEADER_LINE_FACE_ID,
21970 BVAR (current_buffer, header_line_format));
21971 ++n;
21972 }
21973
21974 XFRAME (new_frame)->selected_window = old_frame_selected_window;
21975 selected_frame = old_selected_frame;
21976 selected_window = old_selected_window;
21977 if (n > 0)
21978 w->must_be_updated_p = true;
21979 return n;
21980 }
21981
21982
21983 /* Display mode or header line of window W. FACE_ID specifies which
21984 line to display; it is either MODE_LINE_FACE_ID or
21985 HEADER_LINE_FACE_ID. FORMAT is the mode/header line format to
21986 display. Value is the pixel height of the mode/header line
21987 displayed. */
21988
21989 static int
21990 display_mode_line (struct window *w, enum face_id face_id, Lisp_Object format)
21991 {
21992 struct it it;
21993 struct face *face;
21994 ptrdiff_t count = SPECPDL_INDEX ();
21995
21996 init_iterator (&it, w, -1, -1, NULL, face_id);
21997 /* Don't extend on a previously drawn mode-line.
21998 This may happen if called from pos_visible_p. */
21999 it.glyph_row->enabled_p = false;
22000 prepare_desired_row (w, it.glyph_row, true);
22001
22002 it.glyph_row->mode_line_p = 1;
22003
22004 /* FIXME: This should be controlled by a user option. But
22005 supporting such an option is not trivial, since the mode line is
22006 made up of many separate strings. */
22007 it.paragraph_embedding = L2R;
22008
22009 record_unwind_protect (unwind_format_mode_line,
22010 format_mode_line_unwind_data (NULL, NULL, Qnil, 0));
22011
22012 mode_line_target = MODE_LINE_DISPLAY;
22013
22014 /* Temporarily make frame's keyboard the current kboard so that
22015 kboard-local variables in the mode_line_format will get the right
22016 values. */
22017 push_kboard (FRAME_KBOARD (it.f));
22018 record_unwind_save_match_data ();
22019 display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
22020 pop_kboard ();
22021
22022 unbind_to (count, Qnil);
22023
22024 /* Fill up with spaces. */
22025 display_string (" ", Qnil, Qnil, 0, 0, &it, 10000, -1, -1, 0);
22026
22027 compute_line_metrics (&it);
22028 it.glyph_row->full_width_p = 1;
22029 it.glyph_row->continued_p = 0;
22030 it.glyph_row->truncated_on_left_p = 0;
22031 it.glyph_row->truncated_on_right_p = 0;
22032
22033 /* Make a 3D mode-line have a shadow at its right end. */
22034 face = FACE_FROM_ID (it.f, face_id);
22035 extend_face_to_end_of_line (&it);
22036 if (face->box != FACE_NO_BOX)
22037 {
22038 struct glyph *last = (it.glyph_row->glyphs[TEXT_AREA]
22039 + it.glyph_row->used[TEXT_AREA] - 1);
22040 last->right_box_line_p = 1;
22041 }
22042
22043 return it.glyph_row->height;
22044 }
22045
22046 /* Move element ELT in LIST to the front of LIST.
22047 Return the updated list. */
22048
22049 static Lisp_Object
22050 move_elt_to_front (Lisp_Object elt, Lisp_Object list)
22051 {
22052 register Lisp_Object tail, prev;
22053 register Lisp_Object tem;
22054
22055 tail = list;
22056 prev = Qnil;
22057 while (CONSP (tail))
22058 {
22059 tem = XCAR (tail);
22060
22061 if (EQ (elt, tem))
22062 {
22063 /* Splice out the link TAIL. */
22064 if (NILP (prev))
22065 list = XCDR (tail);
22066 else
22067 Fsetcdr (prev, XCDR (tail));
22068
22069 /* Now make it the first. */
22070 Fsetcdr (tail, list);
22071 return tail;
22072 }
22073 else
22074 prev = tail;
22075 tail = XCDR (tail);
22076 QUIT;
22077 }
22078
22079 /* Not found--return unchanged LIST. */
22080 return list;
22081 }
22082
22083 /* Contribute ELT to the mode line for window IT->w. How it
22084 translates into text depends on its data type.
22085
22086 IT describes the display environment in which we display, as usual.
22087
22088 DEPTH is the depth in recursion. It is used to prevent
22089 infinite recursion here.
22090
22091 FIELD_WIDTH is the number of characters the display of ELT should
22092 occupy in the mode line, and PRECISION is the maximum number of
22093 characters to display from ELT's representation. See
22094 display_string for details.
22095
22096 Returns the hpos of the end of the text generated by ELT.
22097
22098 PROPS is a property list to add to any string we encounter.
22099
22100 If RISKY is nonzero, remove (disregard) any properties in any string
22101 we encounter, and ignore :eval and :propertize.
22102
22103 The global variable `mode_line_target' determines whether the
22104 output is passed to `store_mode_line_noprop',
22105 `store_mode_line_string', or `display_string'. */
22106
22107 static int
22108 display_mode_element (struct it *it, int depth, int field_width, int precision,
22109 Lisp_Object elt, Lisp_Object props, int risky)
22110 {
22111 int n = 0, field, prec;
22112 int literal = 0;
22113
22114 tail_recurse:
22115 if (depth > 100)
22116 elt = build_string ("*too-deep*");
22117
22118 depth++;
22119
22120 switch (XTYPE (elt))
22121 {
22122 case Lisp_String:
22123 {
22124 /* A string: output it and check for %-constructs within it. */
22125 unsigned char c;
22126 ptrdiff_t offset = 0;
22127
22128 if (SCHARS (elt) > 0
22129 && (!NILP (props) || risky))
22130 {
22131 Lisp_Object oprops, aelt;
22132 oprops = Ftext_properties_at (make_number (0), elt);
22133
22134 /* If the starting string's properties are not what
22135 we want, translate the string. Also, if the string
22136 is risky, do that anyway. */
22137
22138 if (NILP (Fequal (props, oprops)) || risky)
22139 {
22140 /* If the starting string has properties,
22141 merge the specified ones onto the existing ones. */
22142 if (! NILP (oprops) && !risky)
22143 {
22144 Lisp_Object tem;
22145
22146 oprops = Fcopy_sequence (oprops);
22147 tem = props;
22148 while (CONSP (tem))
22149 {
22150 oprops = Fplist_put (oprops, XCAR (tem),
22151 XCAR (XCDR (tem)));
22152 tem = XCDR (XCDR (tem));
22153 }
22154 props = oprops;
22155 }
22156
22157 aelt = Fassoc (elt, mode_line_proptrans_alist);
22158 if (! NILP (aelt) && !NILP (Fequal (props, XCDR (aelt))))
22159 {
22160 /* AELT is what we want. Move it to the front
22161 without consing. */
22162 elt = XCAR (aelt);
22163 mode_line_proptrans_alist
22164 = move_elt_to_front (aelt, mode_line_proptrans_alist);
22165 }
22166 else
22167 {
22168 Lisp_Object tem;
22169
22170 /* If AELT has the wrong props, it is useless.
22171 so get rid of it. */
22172 if (! NILP (aelt))
22173 mode_line_proptrans_alist
22174 = Fdelq (aelt, mode_line_proptrans_alist);
22175
22176 elt = Fcopy_sequence (elt);
22177 Fset_text_properties (make_number (0), Flength (elt),
22178 props, elt);
22179 /* Add this item to mode_line_proptrans_alist. */
22180 mode_line_proptrans_alist
22181 = Fcons (Fcons (elt, props),
22182 mode_line_proptrans_alist);
22183 /* Truncate mode_line_proptrans_alist
22184 to at most 50 elements. */
22185 tem = Fnthcdr (make_number (50),
22186 mode_line_proptrans_alist);
22187 if (! NILP (tem))
22188 XSETCDR (tem, Qnil);
22189 }
22190 }
22191 }
22192
22193 offset = 0;
22194
22195 if (literal)
22196 {
22197 prec = precision - n;
22198 switch (mode_line_target)
22199 {
22200 case MODE_LINE_NOPROP:
22201 case MODE_LINE_TITLE:
22202 n += store_mode_line_noprop (SSDATA (elt), -1, prec);
22203 break;
22204 case MODE_LINE_STRING:
22205 n += store_mode_line_string (NULL, elt, 1, 0, prec, Qnil);
22206 break;
22207 case MODE_LINE_DISPLAY:
22208 n += display_string (NULL, elt, Qnil, 0, 0, it,
22209 0, prec, 0, STRING_MULTIBYTE (elt));
22210 break;
22211 }
22212
22213 break;
22214 }
22215
22216 /* Handle the non-literal case. */
22217
22218 while ((precision <= 0 || n < precision)
22219 && SREF (elt, offset) != 0
22220 && (mode_line_target != MODE_LINE_DISPLAY
22221 || it->current_x < it->last_visible_x))
22222 {
22223 ptrdiff_t last_offset = offset;
22224
22225 /* Advance to end of string or next format specifier. */
22226 while ((c = SREF (elt, offset++)) != '\0' && c != '%')
22227 ;
22228
22229 if (offset - 1 != last_offset)
22230 {
22231 ptrdiff_t nchars, nbytes;
22232
22233 /* Output to end of string or up to '%'. Field width
22234 is length of string. Don't output more than
22235 PRECISION allows us. */
22236 offset--;
22237
22238 prec = c_string_width (SDATA (elt) + last_offset,
22239 offset - last_offset, precision - n,
22240 &nchars, &nbytes);
22241
22242 switch (mode_line_target)
22243 {
22244 case MODE_LINE_NOPROP:
22245 case MODE_LINE_TITLE:
22246 n += store_mode_line_noprop (SSDATA (elt) + last_offset, 0, prec);
22247 break;
22248 case MODE_LINE_STRING:
22249 {
22250 ptrdiff_t bytepos = last_offset;
22251 ptrdiff_t charpos = string_byte_to_char (elt, bytepos);
22252 ptrdiff_t endpos = (precision <= 0
22253 ? string_byte_to_char (elt, offset)
22254 : charpos + nchars);
22255
22256 n += store_mode_line_string (NULL,
22257 Fsubstring (elt, make_number (charpos),
22258 make_number (endpos)),
22259 0, 0, 0, Qnil);
22260 }
22261 break;
22262 case MODE_LINE_DISPLAY:
22263 {
22264 ptrdiff_t bytepos = last_offset;
22265 ptrdiff_t charpos = string_byte_to_char (elt, bytepos);
22266
22267 if (precision <= 0)
22268 nchars = string_byte_to_char (elt, offset) - charpos;
22269 n += display_string (NULL, elt, Qnil, 0, charpos,
22270 it, 0, nchars, 0,
22271 STRING_MULTIBYTE (elt));
22272 }
22273 break;
22274 }
22275 }
22276 else /* c == '%' */
22277 {
22278 ptrdiff_t percent_position = offset;
22279
22280 /* Get the specified minimum width. Zero means
22281 don't pad. */
22282 field = 0;
22283 while ((c = SREF (elt, offset++)) >= '0' && c <= '9')
22284 field = field * 10 + c - '0';
22285
22286 /* Don't pad beyond the total padding allowed. */
22287 if (field_width - n > 0 && field > field_width - n)
22288 field = field_width - n;
22289
22290 /* Note that either PRECISION <= 0 or N < PRECISION. */
22291 prec = precision - n;
22292
22293 if (c == 'M')
22294 n += display_mode_element (it, depth, field, prec,
22295 Vglobal_mode_string, props,
22296 risky);
22297 else if (c != 0)
22298 {
22299 bool multibyte;
22300 ptrdiff_t bytepos, charpos;
22301 const char *spec;
22302 Lisp_Object string;
22303
22304 bytepos = percent_position;
22305 charpos = (STRING_MULTIBYTE (elt)
22306 ? string_byte_to_char (elt, bytepos)
22307 : bytepos);
22308 spec = decode_mode_spec (it->w, c, field, &string);
22309 multibyte = STRINGP (string) && STRING_MULTIBYTE (string);
22310
22311 switch (mode_line_target)
22312 {
22313 case MODE_LINE_NOPROP:
22314 case MODE_LINE_TITLE:
22315 n += store_mode_line_noprop (spec, field, prec);
22316 break;
22317 case MODE_LINE_STRING:
22318 {
22319 Lisp_Object tem = build_string (spec);
22320 props = Ftext_properties_at (make_number (charpos), elt);
22321 /* Should only keep face property in props */
22322 n += store_mode_line_string (NULL, tem, 0, field, prec, props);
22323 }
22324 break;
22325 case MODE_LINE_DISPLAY:
22326 {
22327 int nglyphs_before, nwritten;
22328
22329 nglyphs_before = it->glyph_row->used[TEXT_AREA];
22330 nwritten = display_string (spec, string, elt,
22331 charpos, 0, it,
22332 field, prec, 0,
22333 multibyte);
22334
22335 /* Assign to the glyphs written above the
22336 string where the `%x' came from, position
22337 of the `%'. */
22338 if (nwritten > 0)
22339 {
22340 struct glyph *glyph
22341 = (it->glyph_row->glyphs[TEXT_AREA]
22342 + nglyphs_before);
22343 int i;
22344
22345 for (i = 0; i < nwritten; ++i)
22346 {
22347 glyph[i].object = elt;
22348 glyph[i].charpos = charpos;
22349 }
22350
22351 n += nwritten;
22352 }
22353 }
22354 break;
22355 }
22356 }
22357 else /* c == 0 */
22358 break;
22359 }
22360 }
22361 }
22362 break;
22363
22364 case Lisp_Symbol:
22365 /* A symbol: process the value of the symbol recursively
22366 as if it appeared here directly. Avoid error if symbol void.
22367 Special case: if value of symbol is a string, output the string
22368 literally. */
22369 {
22370 register Lisp_Object tem;
22371
22372 /* If the variable is not marked as risky to set
22373 then its contents are risky to use. */
22374 if (NILP (Fget (elt, Qrisky_local_variable)))
22375 risky = 1;
22376
22377 tem = Fboundp (elt);
22378 if (!NILP (tem))
22379 {
22380 tem = Fsymbol_value (elt);
22381 /* If value is a string, output that string literally:
22382 don't check for % within it. */
22383 if (STRINGP (tem))
22384 literal = 1;
22385
22386 if (!EQ (tem, elt))
22387 {
22388 /* Give up right away for nil or t. */
22389 elt = tem;
22390 goto tail_recurse;
22391 }
22392 }
22393 }
22394 break;
22395
22396 case Lisp_Cons:
22397 {
22398 register Lisp_Object car, tem;
22399
22400 /* A cons cell: five distinct cases.
22401 If first element is :eval or :propertize, do something special.
22402 If first element is a string or a cons, process all the elements
22403 and effectively concatenate them.
22404 If first element is a negative number, truncate displaying cdr to
22405 at most that many characters. If positive, pad (with spaces)
22406 to at least that many characters.
22407 If first element is a symbol, process the cadr or caddr recursively
22408 according to whether the symbol's value is non-nil or nil. */
22409 car = XCAR (elt);
22410 if (EQ (car, QCeval))
22411 {
22412 /* An element of the form (:eval FORM) means evaluate FORM
22413 and use the result as mode line elements. */
22414
22415 if (risky)
22416 break;
22417
22418 if (CONSP (XCDR (elt)))
22419 {
22420 Lisp_Object spec;
22421 spec = safe__eval (true, XCAR (XCDR (elt)));
22422 n += display_mode_element (it, depth, field_width - n,
22423 precision - n, spec, props,
22424 risky);
22425 }
22426 }
22427 else if (EQ (car, QCpropertize))
22428 {
22429 /* An element of the form (:propertize ELT PROPS...)
22430 means display ELT but applying properties PROPS. */
22431
22432 if (risky)
22433 break;
22434
22435 if (CONSP (XCDR (elt)))
22436 n += display_mode_element (it, depth, field_width - n,
22437 precision - n, XCAR (XCDR (elt)),
22438 XCDR (XCDR (elt)), risky);
22439 }
22440 else if (SYMBOLP (car))
22441 {
22442 tem = Fboundp (car);
22443 elt = XCDR (elt);
22444 if (!CONSP (elt))
22445 goto invalid;
22446 /* elt is now the cdr, and we know it is a cons cell.
22447 Use its car if CAR has a non-nil value. */
22448 if (!NILP (tem))
22449 {
22450 tem = Fsymbol_value (car);
22451 if (!NILP (tem))
22452 {
22453 elt = XCAR (elt);
22454 goto tail_recurse;
22455 }
22456 }
22457 /* Symbol's value is nil (or symbol is unbound)
22458 Get the cddr of the original list
22459 and if possible find the caddr and use that. */
22460 elt = XCDR (elt);
22461 if (NILP (elt))
22462 break;
22463 else if (!CONSP (elt))
22464 goto invalid;
22465 elt = XCAR (elt);
22466 goto tail_recurse;
22467 }
22468 else if (INTEGERP (car))
22469 {
22470 register int lim = XINT (car);
22471 elt = XCDR (elt);
22472 if (lim < 0)
22473 {
22474 /* Negative int means reduce maximum width. */
22475 if (precision <= 0)
22476 precision = -lim;
22477 else
22478 precision = min (precision, -lim);
22479 }
22480 else if (lim > 0)
22481 {
22482 /* Padding specified. Don't let it be more than
22483 current maximum. */
22484 if (precision > 0)
22485 lim = min (precision, lim);
22486
22487 /* If that's more padding than already wanted, queue it.
22488 But don't reduce padding already specified even if
22489 that is beyond the current truncation point. */
22490 field_width = max (lim, field_width);
22491 }
22492 goto tail_recurse;
22493 }
22494 else if (STRINGP (car) || CONSP (car))
22495 {
22496 Lisp_Object halftail = elt;
22497 int len = 0;
22498
22499 while (CONSP (elt)
22500 && (precision <= 0 || n < precision))
22501 {
22502 n += display_mode_element (it, depth,
22503 /* Do padding only after the last
22504 element in the list. */
22505 (! CONSP (XCDR (elt))
22506 ? field_width - n
22507 : 0),
22508 precision - n, XCAR (elt),
22509 props, risky);
22510 elt = XCDR (elt);
22511 len++;
22512 if ((len & 1) == 0)
22513 halftail = XCDR (halftail);
22514 /* Check for cycle. */
22515 if (EQ (halftail, elt))
22516 break;
22517 }
22518 }
22519 }
22520 break;
22521
22522 default:
22523 invalid:
22524 elt = build_string ("*invalid*");
22525 goto tail_recurse;
22526 }
22527
22528 /* Pad to FIELD_WIDTH. */
22529 if (field_width > 0 && n < field_width)
22530 {
22531 switch (mode_line_target)
22532 {
22533 case MODE_LINE_NOPROP:
22534 case MODE_LINE_TITLE:
22535 n += store_mode_line_noprop ("", field_width - n, 0);
22536 break;
22537 case MODE_LINE_STRING:
22538 n += store_mode_line_string ("", Qnil, 0, field_width - n, 0, Qnil);
22539 break;
22540 case MODE_LINE_DISPLAY:
22541 n += display_string ("", Qnil, Qnil, 0, 0, it, field_width - n,
22542 0, 0, 0);
22543 break;
22544 }
22545 }
22546
22547 return n;
22548 }
22549
22550 /* Store a mode-line string element in mode_line_string_list.
22551
22552 If STRING is non-null, display that C string. Otherwise, the Lisp
22553 string LISP_STRING is displayed.
22554
22555 FIELD_WIDTH is the minimum number of output glyphs to produce.
22556 If STRING has fewer characters than FIELD_WIDTH, pad to the right
22557 with spaces. FIELD_WIDTH <= 0 means don't pad.
22558
22559 PRECISION is the maximum number of characters to output from
22560 STRING. PRECISION <= 0 means don't truncate the string.
22561
22562 If COPY_STRING is non-zero, make a copy of LISP_STRING before adding
22563 properties to the string.
22564
22565 PROPS are the properties to add to the string.
22566 The mode_line_string_face face property is always added to the string.
22567 */
22568
22569 static int
22570 store_mode_line_string (const char *string, Lisp_Object lisp_string, int copy_string,
22571 int field_width, int precision, Lisp_Object props)
22572 {
22573 ptrdiff_t len;
22574 int n = 0;
22575
22576 if (string != NULL)
22577 {
22578 len = strlen (string);
22579 if (precision > 0 && len > precision)
22580 len = precision;
22581 lisp_string = make_string (string, len);
22582 if (NILP (props))
22583 props = mode_line_string_face_prop;
22584 else if (!NILP (mode_line_string_face))
22585 {
22586 Lisp_Object face = Fplist_get (props, Qface);
22587 props = Fcopy_sequence (props);
22588 if (NILP (face))
22589 face = mode_line_string_face;
22590 else
22591 face = list2 (face, mode_line_string_face);
22592 props = Fplist_put (props, Qface, face);
22593 }
22594 Fadd_text_properties (make_number (0), make_number (len),
22595 props, lisp_string);
22596 }
22597 else
22598 {
22599 len = XFASTINT (Flength (lisp_string));
22600 if (precision > 0 && len > precision)
22601 {
22602 len = precision;
22603 lisp_string = Fsubstring (lisp_string, make_number (0), make_number (len));
22604 precision = -1;
22605 }
22606 if (!NILP (mode_line_string_face))
22607 {
22608 Lisp_Object face;
22609 if (NILP (props))
22610 props = Ftext_properties_at (make_number (0), lisp_string);
22611 face = Fplist_get (props, Qface);
22612 if (NILP (face))
22613 face = mode_line_string_face;
22614 else
22615 face = list2 (face, mode_line_string_face);
22616 props = list2 (Qface, face);
22617 if (copy_string)
22618 lisp_string = Fcopy_sequence (lisp_string);
22619 }
22620 if (!NILP (props))
22621 Fadd_text_properties (make_number (0), make_number (len),
22622 props, lisp_string);
22623 }
22624
22625 if (len > 0)
22626 {
22627 mode_line_string_list = Fcons (lisp_string, mode_line_string_list);
22628 n += len;
22629 }
22630
22631 if (field_width > len)
22632 {
22633 field_width -= len;
22634 lisp_string = Fmake_string (make_number (field_width), make_number (' '));
22635 if (!NILP (props))
22636 Fadd_text_properties (make_number (0), make_number (field_width),
22637 props, lisp_string);
22638 mode_line_string_list = Fcons (lisp_string, mode_line_string_list);
22639 n += field_width;
22640 }
22641
22642 return n;
22643 }
22644
22645
22646 DEFUN ("format-mode-line", Fformat_mode_line, Sformat_mode_line,
22647 1, 4, 0,
22648 doc: /* Format a string out of a mode line format specification.
22649 First arg FORMAT specifies the mode line format (see `mode-line-format'
22650 for details) to use.
22651
22652 By default, the format is evaluated for the currently selected window.
22653
22654 Optional second arg FACE specifies the face property to put on all
22655 characters for which no face is specified. The value nil means the
22656 default face. The value t means whatever face the window's mode line
22657 currently uses (either `mode-line' or `mode-line-inactive',
22658 depending on whether the window is the selected window or not).
22659 An integer value means the value string has no text
22660 properties.
22661
22662 Optional third and fourth args WINDOW and BUFFER specify the window
22663 and buffer to use as the context for the formatting (defaults
22664 are the selected window and the WINDOW's buffer). */)
22665 (Lisp_Object format, Lisp_Object face,
22666 Lisp_Object window, Lisp_Object buffer)
22667 {
22668 struct it it;
22669 int len;
22670 struct window *w;
22671 struct buffer *old_buffer = NULL;
22672 int face_id;
22673 int no_props = INTEGERP (face);
22674 ptrdiff_t count = SPECPDL_INDEX ();
22675 Lisp_Object str;
22676 int string_start = 0;
22677
22678 w = decode_any_window (window);
22679 XSETWINDOW (window, w);
22680
22681 if (NILP (buffer))
22682 buffer = w->contents;
22683 CHECK_BUFFER (buffer);
22684
22685 /* Make formatting the modeline a non-op when noninteractive, otherwise
22686 there will be problems later caused by a partially initialized frame. */
22687 if (NILP (format) || noninteractive)
22688 return empty_unibyte_string;
22689
22690 if (no_props)
22691 face = Qnil;
22692
22693 face_id = (NILP (face) || EQ (face, Qdefault)) ? DEFAULT_FACE_ID
22694 : EQ (face, Qt) ? (EQ (window, selected_window)
22695 ? MODE_LINE_FACE_ID : MODE_LINE_INACTIVE_FACE_ID)
22696 : EQ (face, Qmode_line) ? MODE_LINE_FACE_ID
22697 : EQ (face, Qmode_line_inactive) ? MODE_LINE_INACTIVE_FACE_ID
22698 : EQ (face, Qheader_line) ? HEADER_LINE_FACE_ID
22699 : EQ (face, Qtool_bar) ? TOOL_BAR_FACE_ID
22700 : DEFAULT_FACE_ID;
22701
22702 old_buffer = current_buffer;
22703
22704 /* Save things including mode_line_proptrans_alist,
22705 and set that to nil so that we don't alter the outer value. */
22706 record_unwind_protect (unwind_format_mode_line,
22707 format_mode_line_unwind_data
22708 (XFRAME (WINDOW_FRAME (w)),
22709 old_buffer, selected_window, 1));
22710 mode_line_proptrans_alist = Qnil;
22711
22712 Fselect_window (window, Qt);
22713 set_buffer_internal_1 (XBUFFER (buffer));
22714
22715 init_iterator (&it, w, -1, -1, NULL, face_id);
22716
22717 if (no_props)
22718 {
22719 mode_line_target = MODE_LINE_NOPROP;
22720 mode_line_string_face_prop = Qnil;
22721 mode_line_string_list = Qnil;
22722 string_start = MODE_LINE_NOPROP_LEN (0);
22723 }
22724 else
22725 {
22726 mode_line_target = MODE_LINE_STRING;
22727 mode_line_string_list = Qnil;
22728 mode_line_string_face = face;
22729 mode_line_string_face_prop
22730 = NILP (face) ? Qnil : list2 (Qface, face);
22731 }
22732
22733 push_kboard (FRAME_KBOARD (it.f));
22734 display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
22735 pop_kboard ();
22736
22737 if (no_props)
22738 {
22739 len = MODE_LINE_NOPROP_LEN (string_start);
22740 str = make_string (mode_line_noprop_buf + string_start, len);
22741 }
22742 else
22743 {
22744 mode_line_string_list = Fnreverse (mode_line_string_list);
22745 str = Fmapconcat (intern ("identity"), mode_line_string_list,
22746 empty_unibyte_string);
22747 }
22748
22749 unbind_to (count, Qnil);
22750 return str;
22751 }
22752
22753 /* Write a null-terminated, right justified decimal representation of
22754 the positive integer D to BUF using a minimal field width WIDTH. */
22755
22756 static void
22757 pint2str (register char *buf, register int width, register ptrdiff_t d)
22758 {
22759 register char *p = buf;
22760
22761 if (d <= 0)
22762 *p++ = '0';
22763 else
22764 {
22765 while (d > 0)
22766 {
22767 *p++ = d % 10 + '0';
22768 d /= 10;
22769 }
22770 }
22771
22772 for (width -= (int) (p - buf); width > 0; --width)
22773 *p++ = ' ';
22774 *p-- = '\0';
22775 while (p > buf)
22776 {
22777 d = *buf;
22778 *buf++ = *p;
22779 *p-- = d;
22780 }
22781 }
22782
22783 /* Write a null-terminated, right justified decimal and "human
22784 readable" representation of the nonnegative integer D to BUF using
22785 a minimal field width WIDTH. D should be smaller than 999.5e24. */
22786
22787 static const char power_letter[] =
22788 {
22789 0, /* no letter */
22790 'k', /* kilo */
22791 'M', /* mega */
22792 'G', /* giga */
22793 'T', /* tera */
22794 'P', /* peta */
22795 'E', /* exa */
22796 'Z', /* zetta */
22797 'Y' /* yotta */
22798 };
22799
22800 static void
22801 pint2hrstr (char *buf, int width, ptrdiff_t d)
22802 {
22803 /* We aim to represent the nonnegative integer D as
22804 QUOTIENT.TENTHS * 10 ^ (3 * EXPONENT). */
22805 ptrdiff_t quotient = d;
22806 int remainder = 0;
22807 /* -1 means: do not use TENTHS. */
22808 int tenths = -1;
22809 int exponent = 0;
22810
22811 /* Length of QUOTIENT.TENTHS as a string. */
22812 int length;
22813
22814 char * psuffix;
22815 char * p;
22816
22817 if (quotient >= 1000)
22818 {
22819 /* Scale to the appropriate EXPONENT. */
22820 do
22821 {
22822 remainder = quotient % 1000;
22823 quotient /= 1000;
22824 exponent++;
22825 }
22826 while (quotient >= 1000);
22827
22828 /* Round to nearest and decide whether to use TENTHS or not. */
22829 if (quotient <= 9)
22830 {
22831 tenths = remainder / 100;
22832 if (remainder % 100 >= 50)
22833 {
22834 if (tenths < 9)
22835 tenths++;
22836 else
22837 {
22838 quotient++;
22839 if (quotient == 10)
22840 tenths = -1;
22841 else
22842 tenths = 0;
22843 }
22844 }
22845 }
22846 else
22847 if (remainder >= 500)
22848 {
22849 if (quotient < 999)
22850 quotient++;
22851 else
22852 {
22853 quotient = 1;
22854 exponent++;
22855 tenths = 0;
22856 }
22857 }
22858 }
22859
22860 /* Calculate the LENGTH of QUOTIENT.TENTHS as a string. */
22861 if (tenths == -1 && quotient <= 99)
22862 if (quotient <= 9)
22863 length = 1;
22864 else
22865 length = 2;
22866 else
22867 length = 3;
22868 p = psuffix = buf + max (width, length);
22869
22870 /* Print EXPONENT. */
22871 *psuffix++ = power_letter[exponent];
22872 *psuffix = '\0';
22873
22874 /* Print TENTHS. */
22875 if (tenths >= 0)
22876 {
22877 *--p = '0' + tenths;
22878 *--p = '.';
22879 }
22880
22881 /* Print QUOTIENT. */
22882 do
22883 {
22884 int digit = quotient % 10;
22885 *--p = '0' + digit;
22886 }
22887 while ((quotient /= 10) != 0);
22888
22889 /* Print leading spaces. */
22890 while (buf < p)
22891 *--p = ' ';
22892 }
22893
22894 /* Set a mnemonic character for coding_system (Lisp symbol) in BUF.
22895 If EOL_FLAG is 1, set also a mnemonic character for end-of-line
22896 type of CODING_SYSTEM. Return updated pointer into BUF. */
22897
22898 static unsigned char invalid_eol_type[] = "(*invalid*)";
22899
22900 static char *
22901 decode_mode_spec_coding (Lisp_Object coding_system, register char *buf, int eol_flag)
22902 {
22903 Lisp_Object val;
22904 bool multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters));
22905 const unsigned char *eol_str;
22906 int eol_str_len;
22907 /* The EOL conversion we are using. */
22908 Lisp_Object eoltype;
22909
22910 val = CODING_SYSTEM_SPEC (coding_system);
22911 eoltype = Qnil;
22912
22913 if (!VECTORP (val)) /* Not yet decided. */
22914 {
22915 *buf++ = multibyte ? '-' : ' ';
22916 if (eol_flag)
22917 eoltype = eol_mnemonic_undecided;
22918 /* Don't mention EOL conversion if it isn't decided. */
22919 }
22920 else
22921 {
22922 Lisp_Object attrs;
22923 Lisp_Object eolvalue;
22924
22925 attrs = AREF (val, 0);
22926 eolvalue = AREF (val, 2);
22927
22928 *buf++ = multibyte
22929 ? XFASTINT (CODING_ATTR_MNEMONIC (attrs))
22930 : ' ';
22931
22932 if (eol_flag)
22933 {
22934 /* The EOL conversion that is normal on this system. */
22935
22936 if (NILP (eolvalue)) /* Not yet decided. */
22937 eoltype = eol_mnemonic_undecided;
22938 else if (VECTORP (eolvalue)) /* Not yet decided. */
22939 eoltype = eol_mnemonic_undecided;
22940 else /* eolvalue is Qunix, Qdos, or Qmac. */
22941 eoltype = (EQ (eolvalue, Qunix)
22942 ? eol_mnemonic_unix
22943 : (EQ (eolvalue, Qdos) == 1
22944 ? eol_mnemonic_dos : eol_mnemonic_mac));
22945 }
22946 }
22947
22948 if (eol_flag)
22949 {
22950 /* Mention the EOL conversion if it is not the usual one. */
22951 if (STRINGP (eoltype))
22952 {
22953 eol_str = SDATA (eoltype);
22954 eol_str_len = SBYTES (eoltype);
22955 }
22956 else if (CHARACTERP (eoltype))
22957 {
22958 int c = XFASTINT (eoltype);
22959 return buf + CHAR_STRING (c, (unsigned char *) buf);
22960 }
22961 else
22962 {
22963 eol_str = invalid_eol_type;
22964 eol_str_len = sizeof (invalid_eol_type) - 1;
22965 }
22966 memcpy (buf, eol_str, eol_str_len);
22967 buf += eol_str_len;
22968 }
22969
22970 return buf;
22971 }
22972
22973 /* Return a string for the output of a mode line %-spec for window W,
22974 generated by character C. FIELD_WIDTH > 0 means pad the string
22975 returned with spaces to that value. Return a Lisp string in
22976 *STRING if the resulting string is taken from that Lisp string.
22977
22978 Note we operate on the current buffer for most purposes. */
22979
22980 static char lots_of_dashes[] = "--------------------------------------------------------------------------------------------------------------------------------------------";
22981
22982 static const char *
22983 decode_mode_spec (struct window *w, register int c, int field_width,
22984 Lisp_Object *string)
22985 {
22986 Lisp_Object obj;
22987 struct frame *f = XFRAME (WINDOW_FRAME (w));
22988 char *decode_mode_spec_buf = f->decode_mode_spec_buffer;
22989 /* We are going to use f->decode_mode_spec_buffer as the buffer to
22990 produce strings from numerical values, so limit preposterously
22991 large values of FIELD_WIDTH to avoid overrunning the buffer's
22992 end. The size of the buffer is enough for FRAME_MESSAGE_BUF_SIZE
22993 bytes plus the terminating null. */
22994 int width = min (field_width, FRAME_MESSAGE_BUF_SIZE (f));
22995 struct buffer *b = current_buffer;
22996
22997 obj = Qnil;
22998 *string = Qnil;
22999
23000 switch (c)
23001 {
23002 case '*':
23003 if (!NILP (BVAR (b, read_only)))
23004 return "%";
23005 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
23006 return "*";
23007 return "-";
23008
23009 case '+':
23010 /* This differs from %* only for a modified read-only buffer. */
23011 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
23012 return "*";
23013 if (!NILP (BVAR (b, read_only)))
23014 return "%";
23015 return "-";
23016
23017 case '&':
23018 /* This differs from %* in ignoring read-only-ness. */
23019 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
23020 return "*";
23021 return "-";
23022
23023 case '%':
23024 return "%";
23025
23026 case '[':
23027 {
23028 int i;
23029 char *p;
23030
23031 if (command_loop_level > 5)
23032 return "[[[... ";
23033 p = decode_mode_spec_buf;
23034 for (i = 0; i < command_loop_level; i++)
23035 *p++ = '[';
23036 *p = 0;
23037 return decode_mode_spec_buf;
23038 }
23039
23040 case ']':
23041 {
23042 int i;
23043 char *p;
23044
23045 if (command_loop_level > 5)
23046 return " ...]]]";
23047 p = decode_mode_spec_buf;
23048 for (i = 0; i < command_loop_level; i++)
23049 *p++ = ']';
23050 *p = 0;
23051 return decode_mode_spec_buf;
23052 }
23053
23054 case '-':
23055 {
23056 register int i;
23057
23058 /* Let lots_of_dashes be a string of infinite length. */
23059 if (mode_line_target == MODE_LINE_NOPROP
23060 || mode_line_target == MODE_LINE_STRING)
23061 return "--";
23062 if (field_width <= 0
23063 || field_width > sizeof (lots_of_dashes))
23064 {
23065 for (i = 0; i < FRAME_MESSAGE_BUF_SIZE (f) - 1; ++i)
23066 decode_mode_spec_buf[i] = '-';
23067 decode_mode_spec_buf[i] = '\0';
23068 return decode_mode_spec_buf;
23069 }
23070 else
23071 return lots_of_dashes;
23072 }
23073
23074 case 'b':
23075 obj = BVAR (b, name);
23076 break;
23077
23078 case 'c':
23079 /* %c and %l are ignored in `frame-title-format'.
23080 (In redisplay_internal, the frame title is drawn _before_ the
23081 windows are updated, so the stuff which depends on actual
23082 window contents (such as %l) may fail to render properly, or
23083 even crash emacs.) */
23084 if (mode_line_target == MODE_LINE_TITLE)
23085 return "";
23086 else
23087 {
23088 ptrdiff_t col = current_column ();
23089 w->column_number_displayed = col;
23090 pint2str (decode_mode_spec_buf, width, col);
23091 return decode_mode_spec_buf;
23092 }
23093
23094 case 'e':
23095 #if !defined SYSTEM_MALLOC && !defined HYBRID_MALLOC
23096 {
23097 if (NILP (Vmemory_full))
23098 return "";
23099 else
23100 return "!MEM FULL! ";
23101 }
23102 #else
23103 return "";
23104 #endif
23105
23106 case 'F':
23107 /* %F displays the frame name. */
23108 if (!NILP (f->title))
23109 return SSDATA (f->title);
23110 if (f->explicit_name || ! FRAME_WINDOW_P (f))
23111 return SSDATA (f->name);
23112 return "Emacs";
23113
23114 case 'f':
23115 obj = BVAR (b, filename);
23116 break;
23117
23118 case 'i':
23119 {
23120 ptrdiff_t size = ZV - BEGV;
23121 pint2str (decode_mode_spec_buf, width, size);
23122 return decode_mode_spec_buf;
23123 }
23124
23125 case 'I':
23126 {
23127 ptrdiff_t size = ZV - BEGV;
23128 pint2hrstr (decode_mode_spec_buf, width, size);
23129 return decode_mode_spec_buf;
23130 }
23131
23132 case 'l':
23133 {
23134 ptrdiff_t startpos, startpos_byte, line, linepos, linepos_byte;
23135 ptrdiff_t topline, nlines, height;
23136 ptrdiff_t junk;
23137
23138 /* %c and %l are ignored in `frame-title-format'. */
23139 if (mode_line_target == MODE_LINE_TITLE)
23140 return "";
23141
23142 startpos = marker_position (w->start);
23143 startpos_byte = marker_byte_position (w->start);
23144 height = WINDOW_TOTAL_LINES (w);
23145
23146 /* If we decided that this buffer isn't suitable for line numbers,
23147 don't forget that too fast. */
23148 if (w->base_line_pos == -1)
23149 goto no_value;
23150
23151 /* If the buffer is very big, don't waste time. */
23152 if (INTEGERP (Vline_number_display_limit)
23153 && BUF_ZV (b) - BUF_BEGV (b) > XINT (Vline_number_display_limit))
23154 {
23155 w->base_line_pos = 0;
23156 w->base_line_number = 0;
23157 goto no_value;
23158 }
23159
23160 if (w->base_line_number > 0
23161 && w->base_line_pos > 0
23162 && w->base_line_pos <= startpos)
23163 {
23164 line = w->base_line_number;
23165 linepos = w->base_line_pos;
23166 linepos_byte = buf_charpos_to_bytepos (b, linepos);
23167 }
23168 else
23169 {
23170 line = 1;
23171 linepos = BUF_BEGV (b);
23172 linepos_byte = BUF_BEGV_BYTE (b);
23173 }
23174
23175 /* Count lines from base line to window start position. */
23176 nlines = display_count_lines (linepos_byte,
23177 startpos_byte,
23178 startpos, &junk);
23179
23180 topline = nlines + line;
23181
23182 /* Determine a new base line, if the old one is too close
23183 or too far away, or if we did not have one.
23184 "Too close" means it's plausible a scroll-down would
23185 go back past it. */
23186 if (startpos == BUF_BEGV (b))
23187 {
23188 w->base_line_number = topline;
23189 w->base_line_pos = BUF_BEGV (b);
23190 }
23191 else if (nlines < height + 25 || nlines > height * 3 + 50
23192 || linepos == BUF_BEGV (b))
23193 {
23194 ptrdiff_t limit = BUF_BEGV (b);
23195 ptrdiff_t limit_byte = BUF_BEGV_BYTE (b);
23196 ptrdiff_t position;
23197 ptrdiff_t distance =
23198 (height * 2 + 30) * line_number_display_limit_width;
23199
23200 if (startpos - distance > limit)
23201 {
23202 limit = startpos - distance;
23203 limit_byte = CHAR_TO_BYTE (limit);
23204 }
23205
23206 nlines = display_count_lines (startpos_byte,
23207 limit_byte,
23208 - (height * 2 + 30),
23209 &position);
23210 /* If we couldn't find the lines we wanted within
23211 line_number_display_limit_width chars per line,
23212 give up on line numbers for this window. */
23213 if (position == limit_byte && limit == startpos - distance)
23214 {
23215 w->base_line_pos = -1;
23216 w->base_line_number = 0;
23217 goto no_value;
23218 }
23219
23220 w->base_line_number = topline - nlines;
23221 w->base_line_pos = BYTE_TO_CHAR (position);
23222 }
23223
23224 /* Now count lines from the start pos to point. */
23225 nlines = display_count_lines (startpos_byte,
23226 PT_BYTE, PT, &junk);
23227
23228 /* Record that we did display the line number. */
23229 line_number_displayed = 1;
23230
23231 /* Make the string to show. */
23232 pint2str (decode_mode_spec_buf, width, topline + nlines);
23233 return decode_mode_spec_buf;
23234 no_value:
23235 {
23236 char *p = decode_mode_spec_buf;
23237 int pad = width - 2;
23238 while (pad-- > 0)
23239 *p++ = ' ';
23240 *p++ = '?';
23241 *p++ = '?';
23242 *p = '\0';
23243 return decode_mode_spec_buf;
23244 }
23245 }
23246 break;
23247
23248 case 'm':
23249 obj = BVAR (b, mode_name);
23250 break;
23251
23252 case 'n':
23253 if (BUF_BEGV (b) > BUF_BEG (b) || BUF_ZV (b) < BUF_Z (b))
23254 return " Narrow";
23255 break;
23256
23257 case 'p':
23258 {
23259 ptrdiff_t pos = marker_position (w->start);
23260 ptrdiff_t total = BUF_ZV (b) - BUF_BEGV (b);
23261
23262 if (w->window_end_pos <= BUF_Z (b) - BUF_ZV (b))
23263 {
23264 if (pos <= BUF_BEGV (b))
23265 return "All";
23266 else
23267 return "Bottom";
23268 }
23269 else if (pos <= BUF_BEGV (b))
23270 return "Top";
23271 else
23272 {
23273 if (total > 1000000)
23274 /* Do it differently for a large value, to avoid overflow. */
23275 total = ((pos - BUF_BEGV (b)) + (total / 100) - 1) / (total / 100);
23276 else
23277 total = ((pos - BUF_BEGV (b)) * 100 + total - 1) / total;
23278 /* We can't normally display a 3-digit number,
23279 so get us a 2-digit number that is close. */
23280 if (total == 100)
23281 total = 99;
23282 sprintf (decode_mode_spec_buf, "%2"pD"d%%", total);
23283 return decode_mode_spec_buf;
23284 }
23285 }
23286
23287 /* Display percentage of size above the bottom of the screen. */
23288 case 'P':
23289 {
23290 ptrdiff_t toppos = marker_position (w->start);
23291 ptrdiff_t botpos = BUF_Z (b) - w->window_end_pos;
23292 ptrdiff_t total = BUF_ZV (b) - BUF_BEGV (b);
23293
23294 if (botpos >= BUF_ZV (b))
23295 {
23296 if (toppos <= BUF_BEGV (b))
23297 return "All";
23298 else
23299 return "Bottom";
23300 }
23301 else
23302 {
23303 if (total > 1000000)
23304 /* Do it differently for a large value, to avoid overflow. */
23305 total = ((botpos - BUF_BEGV (b)) + (total / 100) - 1) / (total / 100);
23306 else
23307 total = ((botpos - BUF_BEGV (b)) * 100 + total - 1) / total;
23308 /* We can't normally display a 3-digit number,
23309 so get us a 2-digit number that is close. */
23310 if (total == 100)
23311 total = 99;
23312 if (toppos <= BUF_BEGV (b))
23313 sprintf (decode_mode_spec_buf, "Top%2"pD"d%%", total);
23314 else
23315 sprintf (decode_mode_spec_buf, "%2"pD"d%%", total);
23316 return decode_mode_spec_buf;
23317 }
23318 }
23319
23320 case 's':
23321 /* status of process */
23322 obj = Fget_buffer_process (Fcurrent_buffer ());
23323 if (NILP (obj))
23324 return "no process";
23325 #ifndef MSDOS
23326 obj = Fsymbol_name (Fprocess_status (obj));
23327 #endif
23328 break;
23329
23330 case '@':
23331 {
23332 ptrdiff_t count = inhibit_garbage_collection ();
23333 Lisp_Object curdir = BVAR (current_buffer, directory);
23334 Lisp_Object val = Qnil;
23335
23336 if (STRINGP (curdir))
23337 val = call1 (intern ("file-remote-p"), curdir);
23338
23339 unbind_to (count, Qnil);
23340
23341 if (NILP (val))
23342 return "-";
23343 else
23344 return "@";
23345 }
23346
23347 case 'z':
23348 /* coding-system (not including end-of-line format) */
23349 case 'Z':
23350 /* coding-system (including end-of-line type) */
23351 {
23352 int eol_flag = (c == 'Z');
23353 char *p = decode_mode_spec_buf;
23354
23355 if (! FRAME_WINDOW_P (f))
23356 {
23357 /* No need to mention EOL here--the terminal never needs
23358 to do EOL conversion. */
23359 p = decode_mode_spec_coding (CODING_ID_NAME
23360 (FRAME_KEYBOARD_CODING (f)->id),
23361 p, 0);
23362 p = decode_mode_spec_coding (CODING_ID_NAME
23363 (FRAME_TERMINAL_CODING (f)->id),
23364 p, 0);
23365 }
23366 p = decode_mode_spec_coding (BVAR (b, buffer_file_coding_system),
23367 p, eol_flag);
23368
23369 #if 0 /* This proves to be annoying; I think we can do without. -- rms. */
23370 #ifdef subprocesses
23371 obj = Fget_buffer_process (Fcurrent_buffer ());
23372 if (PROCESSP (obj))
23373 {
23374 p = decode_mode_spec_coding
23375 (XPROCESS (obj)->decode_coding_system, p, eol_flag);
23376 p = decode_mode_spec_coding
23377 (XPROCESS (obj)->encode_coding_system, p, eol_flag);
23378 }
23379 #endif /* subprocesses */
23380 #endif /* 0 */
23381 *p = 0;
23382 return decode_mode_spec_buf;
23383 }
23384 }
23385
23386 if (STRINGP (obj))
23387 {
23388 *string = obj;
23389 return SSDATA (obj);
23390 }
23391 else
23392 return "";
23393 }
23394
23395
23396 /* Count up to COUNT lines starting from START_BYTE. COUNT negative
23397 means count lines back from START_BYTE. But don't go beyond
23398 LIMIT_BYTE. Return the number of lines thus found (always
23399 nonnegative).
23400
23401 Set *BYTE_POS_PTR to the byte position where we stopped. This is
23402 either the position COUNT lines after/before START_BYTE, if we
23403 found COUNT lines, or LIMIT_BYTE if we hit the limit before finding
23404 COUNT lines. */
23405
23406 static ptrdiff_t
23407 display_count_lines (ptrdiff_t start_byte,
23408 ptrdiff_t limit_byte, ptrdiff_t count,
23409 ptrdiff_t *byte_pos_ptr)
23410 {
23411 register unsigned char *cursor;
23412 unsigned char *base;
23413
23414 register ptrdiff_t ceiling;
23415 register unsigned char *ceiling_addr;
23416 ptrdiff_t orig_count = count;
23417
23418 /* If we are not in selective display mode,
23419 check only for newlines. */
23420 int selective_display = (!NILP (BVAR (current_buffer, selective_display))
23421 && !INTEGERP (BVAR (current_buffer, selective_display)));
23422
23423 if (count > 0)
23424 {
23425 while (start_byte < limit_byte)
23426 {
23427 ceiling = BUFFER_CEILING_OF (start_byte);
23428 ceiling = min (limit_byte - 1, ceiling);
23429 ceiling_addr = BYTE_POS_ADDR (ceiling) + 1;
23430 base = (cursor = BYTE_POS_ADDR (start_byte));
23431
23432 do
23433 {
23434 if (selective_display)
23435 {
23436 while (*cursor != '\n' && *cursor != 015
23437 && ++cursor != ceiling_addr)
23438 continue;
23439 if (cursor == ceiling_addr)
23440 break;
23441 }
23442 else
23443 {
23444 cursor = memchr (cursor, '\n', ceiling_addr - cursor);
23445 if (! cursor)
23446 break;
23447 }
23448
23449 cursor++;
23450
23451 if (--count == 0)
23452 {
23453 start_byte += cursor - base;
23454 *byte_pos_ptr = start_byte;
23455 return orig_count;
23456 }
23457 }
23458 while (cursor < ceiling_addr);
23459
23460 start_byte += ceiling_addr - base;
23461 }
23462 }
23463 else
23464 {
23465 while (start_byte > limit_byte)
23466 {
23467 ceiling = BUFFER_FLOOR_OF (start_byte - 1);
23468 ceiling = max (limit_byte, ceiling);
23469 ceiling_addr = BYTE_POS_ADDR (ceiling);
23470 base = (cursor = BYTE_POS_ADDR (start_byte - 1) + 1);
23471 while (1)
23472 {
23473 if (selective_display)
23474 {
23475 while (--cursor >= ceiling_addr
23476 && *cursor != '\n' && *cursor != 015)
23477 continue;
23478 if (cursor < ceiling_addr)
23479 break;
23480 }
23481 else
23482 {
23483 cursor = memrchr (ceiling_addr, '\n', cursor - ceiling_addr);
23484 if (! cursor)
23485 break;
23486 }
23487
23488 if (++count == 0)
23489 {
23490 start_byte += cursor - base + 1;
23491 *byte_pos_ptr = start_byte;
23492 /* When scanning backwards, we should
23493 not count the newline posterior to which we stop. */
23494 return - orig_count - 1;
23495 }
23496 }
23497 start_byte += ceiling_addr - base;
23498 }
23499 }
23500
23501 *byte_pos_ptr = limit_byte;
23502
23503 if (count < 0)
23504 return - orig_count + count;
23505 return orig_count - count;
23506
23507 }
23508
23509
23510 \f
23511 /***********************************************************************
23512 Displaying strings
23513 ***********************************************************************/
23514
23515 /* Display a NUL-terminated string, starting with index START.
23516
23517 If STRING is non-null, display that C string. Otherwise, the Lisp
23518 string LISP_STRING is displayed. There's a case that STRING is
23519 non-null and LISP_STRING is not nil. It means STRING is a string
23520 data of LISP_STRING. In that case, we display LISP_STRING while
23521 ignoring its text properties.
23522
23523 If FACE_STRING is not nil, FACE_STRING_POS is a position in
23524 FACE_STRING. Display STRING or LISP_STRING with the face at
23525 FACE_STRING_POS in FACE_STRING:
23526
23527 Display the string in the environment given by IT, but use the
23528 standard display table, temporarily.
23529
23530 FIELD_WIDTH is the minimum number of output glyphs to produce.
23531 If STRING has fewer characters than FIELD_WIDTH, pad to the right
23532 with spaces. If STRING has more characters, more than FIELD_WIDTH
23533 glyphs will be produced. FIELD_WIDTH <= 0 means don't pad.
23534
23535 PRECISION is the maximum number of characters to output from
23536 STRING. PRECISION < 0 means don't truncate the string.
23537
23538 This is roughly equivalent to printf format specifiers:
23539
23540 FIELD_WIDTH PRECISION PRINTF
23541 ----------------------------------------
23542 -1 -1 %s
23543 -1 10 %.10s
23544 10 -1 %10s
23545 20 10 %20.10s
23546
23547 MULTIBYTE zero means do not display multibyte chars, > 0 means do
23548 display them, and < 0 means obey the current buffer's value of
23549 enable_multibyte_characters.
23550
23551 Value is the number of columns displayed. */
23552
23553 static int
23554 display_string (const char *string, Lisp_Object lisp_string, Lisp_Object face_string,
23555 ptrdiff_t face_string_pos, ptrdiff_t start, struct it *it,
23556 int field_width, int precision, int max_x, int multibyte)
23557 {
23558 int hpos_at_start = it->hpos;
23559 int saved_face_id = it->face_id;
23560 struct glyph_row *row = it->glyph_row;
23561 ptrdiff_t it_charpos;
23562
23563 /* Initialize the iterator IT for iteration over STRING beginning
23564 with index START. */
23565 reseat_to_string (it, NILP (lisp_string) ? string : NULL, lisp_string, start,
23566 precision, field_width, multibyte);
23567 if (string && STRINGP (lisp_string))
23568 /* LISP_STRING is the one returned by decode_mode_spec. We should
23569 ignore its text properties. */
23570 it->stop_charpos = it->end_charpos;
23571
23572 /* If displaying STRING, set up the face of the iterator from
23573 FACE_STRING, if that's given. */
23574 if (STRINGP (face_string))
23575 {
23576 ptrdiff_t endptr;
23577 struct face *face;
23578
23579 it->face_id
23580 = face_at_string_position (it->w, face_string, face_string_pos,
23581 0, &endptr, it->base_face_id, false);
23582 face = FACE_FROM_ID (it->f, it->face_id);
23583 it->face_box_p = face->box != FACE_NO_BOX;
23584 }
23585
23586 /* Set max_x to the maximum allowed X position. Don't let it go
23587 beyond the right edge of the window. */
23588 if (max_x <= 0)
23589 max_x = it->last_visible_x;
23590 else
23591 max_x = min (max_x, it->last_visible_x);
23592
23593 /* Skip over display elements that are not visible. because IT->w is
23594 hscrolled. */
23595 if (it->current_x < it->first_visible_x)
23596 move_it_in_display_line_to (it, 100000, it->first_visible_x,
23597 MOVE_TO_POS | MOVE_TO_X);
23598
23599 row->ascent = it->max_ascent;
23600 row->height = it->max_ascent + it->max_descent;
23601 row->phys_ascent = it->max_phys_ascent;
23602 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
23603 row->extra_line_spacing = it->max_extra_line_spacing;
23604
23605 if (STRINGP (it->string))
23606 it_charpos = IT_STRING_CHARPOS (*it);
23607 else
23608 it_charpos = IT_CHARPOS (*it);
23609
23610 /* This condition is for the case that we are called with current_x
23611 past last_visible_x. */
23612 while (it->current_x < max_x)
23613 {
23614 int x_before, x, n_glyphs_before, i, nglyphs;
23615
23616 /* Get the next display element. */
23617 if (!get_next_display_element (it))
23618 break;
23619
23620 /* Produce glyphs. */
23621 x_before = it->current_x;
23622 n_glyphs_before = row->used[TEXT_AREA];
23623 PRODUCE_GLYPHS (it);
23624
23625 nglyphs = row->used[TEXT_AREA] - n_glyphs_before;
23626 i = 0;
23627 x = x_before;
23628 while (i < nglyphs)
23629 {
23630 struct glyph *glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
23631
23632 if (it->line_wrap != TRUNCATE
23633 && x + glyph->pixel_width > max_x)
23634 {
23635 /* End of continued line or max_x reached. */
23636 if (CHAR_GLYPH_PADDING_P (*glyph))
23637 {
23638 /* A wide character is unbreakable. */
23639 if (row->reversed_p)
23640 unproduce_glyphs (it, row->used[TEXT_AREA]
23641 - n_glyphs_before);
23642 row->used[TEXT_AREA] = n_glyphs_before;
23643 it->current_x = x_before;
23644 }
23645 else
23646 {
23647 if (row->reversed_p)
23648 unproduce_glyphs (it, row->used[TEXT_AREA]
23649 - (n_glyphs_before + i));
23650 row->used[TEXT_AREA] = n_glyphs_before + i;
23651 it->current_x = x;
23652 }
23653 break;
23654 }
23655 else if (x + glyph->pixel_width >= it->first_visible_x)
23656 {
23657 /* Glyph is at least partially visible. */
23658 ++it->hpos;
23659 if (x < it->first_visible_x)
23660 row->x = x - it->first_visible_x;
23661 }
23662 else
23663 {
23664 /* Glyph is off the left margin of the display area.
23665 Should not happen. */
23666 emacs_abort ();
23667 }
23668
23669 row->ascent = max (row->ascent, it->max_ascent);
23670 row->height = max (row->height, it->max_ascent + it->max_descent);
23671 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
23672 row->phys_height = max (row->phys_height,
23673 it->max_phys_ascent + it->max_phys_descent);
23674 row->extra_line_spacing = max (row->extra_line_spacing,
23675 it->max_extra_line_spacing);
23676 x += glyph->pixel_width;
23677 ++i;
23678 }
23679
23680 /* Stop if max_x reached. */
23681 if (i < nglyphs)
23682 break;
23683
23684 /* Stop at line ends. */
23685 if (ITERATOR_AT_END_OF_LINE_P (it))
23686 {
23687 it->continuation_lines_width = 0;
23688 break;
23689 }
23690
23691 set_iterator_to_next (it, 1);
23692 if (STRINGP (it->string))
23693 it_charpos = IT_STRING_CHARPOS (*it);
23694 else
23695 it_charpos = IT_CHARPOS (*it);
23696
23697 /* Stop if truncating at the right edge. */
23698 if (it->line_wrap == TRUNCATE
23699 && it->current_x >= it->last_visible_x)
23700 {
23701 /* Add truncation mark, but don't do it if the line is
23702 truncated at a padding space. */
23703 if (it_charpos < it->string_nchars)
23704 {
23705 if (!FRAME_WINDOW_P (it->f))
23706 {
23707 int ii, n;
23708
23709 if (it->current_x > it->last_visible_x)
23710 {
23711 if (!row->reversed_p)
23712 {
23713 for (ii = row->used[TEXT_AREA] - 1; ii > 0; --ii)
23714 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][ii]))
23715 break;
23716 }
23717 else
23718 {
23719 for (ii = 0; ii < row->used[TEXT_AREA]; ii++)
23720 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][ii]))
23721 break;
23722 unproduce_glyphs (it, ii + 1);
23723 ii = row->used[TEXT_AREA] - (ii + 1);
23724 }
23725 for (n = row->used[TEXT_AREA]; ii < n; ++ii)
23726 {
23727 row->used[TEXT_AREA] = ii;
23728 produce_special_glyphs (it, IT_TRUNCATION);
23729 }
23730 }
23731 produce_special_glyphs (it, IT_TRUNCATION);
23732 }
23733 row->truncated_on_right_p = 1;
23734 }
23735 break;
23736 }
23737 }
23738
23739 /* Maybe insert a truncation at the left. */
23740 if (it->first_visible_x
23741 && it_charpos > 0)
23742 {
23743 if (!FRAME_WINDOW_P (it->f)
23744 || (row->reversed_p
23745 ? WINDOW_RIGHT_FRINGE_WIDTH (it->w)
23746 : WINDOW_LEFT_FRINGE_WIDTH (it->w)) == 0)
23747 insert_left_trunc_glyphs (it);
23748 row->truncated_on_left_p = 1;
23749 }
23750
23751 it->face_id = saved_face_id;
23752
23753 /* Value is number of columns displayed. */
23754 return it->hpos - hpos_at_start;
23755 }
23756
23757
23758 \f
23759 /* This is like a combination of memq and assq. Return 1/2 if PROPVAL
23760 appears as an element of LIST or as the car of an element of LIST.
23761 If PROPVAL is a list, compare each element against LIST in that
23762 way, and return 1/2 if any element of PROPVAL is found in LIST.
23763 Otherwise return 0. This function cannot quit.
23764 The return value is 2 if the text is invisible but with an ellipsis
23765 and 1 if it's invisible and without an ellipsis. */
23766
23767 int
23768 invisible_p (register Lisp_Object propval, Lisp_Object list)
23769 {
23770 register Lisp_Object tail, proptail;
23771
23772 for (tail = list; CONSP (tail); tail = XCDR (tail))
23773 {
23774 register Lisp_Object tem;
23775 tem = XCAR (tail);
23776 if (EQ (propval, tem))
23777 return 1;
23778 if (CONSP (tem) && EQ (propval, XCAR (tem)))
23779 return NILP (XCDR (tem)) ? 1 : 2;
23780 }
23781
23782 if (CONSP (propval))
23783 {
23784 for (proptail = propval; CONSP (proptail); proptail = XCDR (proptail))
23785 {
23786 Lisp_Object propelt;
23787 propelt = XCAR (proptail);
23788 for (tail = list; CONSP (tail); tail = XCDR (tail))
23789 {
23790 register Lisp_Object tem;
23791 tem = XCAR (tail);
23792 if (EQ (propelt, tem))
23793 return 1;
23794 if (CONSP (tem) && EQ (propelt, XCAR (tem)))
23795 return NILP (XCDR (tem)) ? 1 : 2;
23796 }
23797 }
23798 }
23799
23800 return 0;
23801 }
23802
23803 DEFUN ("invisible-p", Finvisible_p, Sinvisible_p, 1, 1, 0,
23804 doc: /* Non-nil if the property makes the text invisible.
23805 POS-OR-PROP can be a marker or number, in which case it is taken to be
23806 a position in the current buffer and the value of the `invisible' property
23807 is checked; or it can be some other value, which is then presumed to be the
23808 value of the `invisible' property of the text of interest.
23809 The non-nil value returned can be t for truly invisible text or something
23810 else if the text is replaced by an ellipsis. */)
23811 (Lisp_Object pos_or_prop)
23812 {
23813 Lisp_Object prop
23814 = (NATNUMP (pos_or_prop) || MARKERP (pos_or_prop)
23815 ? Fget_char_property (pos_or_prop, Qinvisible, Qnil)
23816 : pos_or_prop);
23817 int invis = TEXT_PROP_MEANS_INVISIBLE (prop);
23818 return (invis == 0 ? Qnil
23819 : invis == 1 ? Qt
23820 : make_number (invis));
23821 }
23822
23823 /* Calculate a width or height in pixels from a specification using
23824 the following elements:
23825
23826 SPEC ::=
23827 NUM - a (fractional) multiple of the default font width/height
23828 (NUM) - specifies exactly NUM pixels
23829 UNIT - a fixed number of pixels, see below.
23830 ELEMENT - size of a display element in pixels, see below.
23831 (NUM . SPEC) - equals NUM * SPEC
23832 (+ SPEC SPEC ...) - add pixel values
23833 (- SPEC SPEC ...) - subtract pixel values
23834 (- SPEC) - negate pixel value
23835
23836 NUM ::=
23837 INT or FLOAT - a number constant
23838 SYMBOL - use symbol's (buffer local) variable binding.
23839
23840 UNIT ::=
23841 in - pixels per inch *)
23842 mm - pixels per 1/1000 meter *)
23843 cm - pixels per 1/100 meter *)
23844 width - width of current font in pixels.
23845 height - height of current font in pixels.
23846
23847 *) using the ratio(s) defined in display-pixels-per-inch.
23848
23849 ELEMENT ::=
23850
23851 left-fringe - left fringe width in pixels
23852 right-fringe - right fringe width in pixels
23853
23854 left-margin - left margin width in pixels
23855 right-margin - right margin width in pixels
23856
23857 scroll-bar - scroll-bar area width in pixels
23858
23859 Examples:
23860
23861 Pixels corresponding to 5 inches:
23862 (5 . in)
23863
23864 Total width of non-text areas on left side of window (if scroll-bar is on left):
23865 '(space :width (+ left-fringe left-margin scroll-bar))
23866
23867 Align to first text column (in header line):
23868 '(space :align-to 0)
23869
23870 Align to middle of text area minus half the width of variable `my-image'
23871 containing a loaded image:
23872 '(space :align-to (0.5 . (- text my-image)))
23873
23874 Width of left margin minus width of 1 character in the default font:
23875 '(space :width (- left-margin 1))
23876
23877 Width of left margin minus width of 2 characters in the current font:
23878 '(space :width (- left-margin (2 . width)))
23879
23880 Center 1 character over left-margin (in header line):
23881 '(space :align-to (+ left-margin (0.5 . left-margin) -0.5))
23882
23883 Different ways to express width of left fringe plus left margin minus one pixel:
23884 '(space :width (- (+ left-fringe left-margin) (1)))
23885 '(space :width (+ left-fringe left-margin (- (1))))
23886 '(space :width (+ left-fringe left-margin (-1)))
23887
23888 */
23889
23890 static int
23891 calc_pixel_width_or_height (double *res, struct it *it, Lisp_Object prop,
23892 struct font *font, int width_p, int *align_to)
23893 {
23894 double pixels;
23895
23896 #define OK_PIXELS(val) ((*res = (double)(val)), 1)
23897 #define OK_ALIGN_TO(val) ((*align_to = (int)(val)), 1)
23898
23899 if (NILP (prop))
23900 return OK_PIXELS (0);
23901
23902 eassert (FRAME_LIVE_P (it->f));
23903
23904 if (SYMBOLP (prop))
23905 {
23906 if (SCHARS (SYMBOL_NAME (prop)) == 2)
23907 {
23908 char *unit = SSDATA (SYMBOL_NAME (prop));
23909
23910 if (unit[0] == 'i' && unit[1] == 'n')
23911 pixels = 1.0;
23912 else if (unit[0] == 'm' && unit[1] == 'm')
23913 pixels = 25.4;
23914 else if (unit[0] == 'c' && unit[1] == 'm')
23915 pixels = 2.54;
23916 else
23917 pixels = 0;
23918 if (pixels > 0)
23919 {
23920 double ppi = (width_p ? FRAME_RES_X (it->f)
23921 : FRAME_RES_Y (it->f));
23922
23923 if (ppi > 0)
23924 return OK_PIXELS (ppi / pixels);
23925 return 0;
23926 }
23927 }
23928
23929 #ifdef HAVE_WINDOW_SYSTEM
23930 if (EQ (prop, Qheight))
23931 return OK_PIXELS (font ? FONT_HEIGHT (font) : FRAME_LINE_HEIGHT (it->f));
23932 if (EQ (prop, Qwidth))
23933 return OK_PIXELS (font ? FONT_WIDTH (font) : FRAME_COLUMN_WIDTH (it->f));
23934 #else
23935 if (EQ (prop, Qheight) || EQ (prop, Qwidth))
23936 return OK_PIXELS (1);
23937 #endif
23938
23939 if (EQ (prop, Qtext))
23940 return OK_PIXELS (width_p
23941 ? window_box_width (it->w, TEXT_AREA)
23942 : WINDOW_BOX_HEIGHT_NO_MODE_LINE (it->w));
23943
23944 if (align_to && *align_to < 0)
23945 {
23946 *res = 0;
23947 if (EQ (prop, Qleft))
23948 return OK_ALIGN_TO (window_box_left_offset (it->w, TEXT_AREA));
23949 if (EQ (prop, Qright))
23950 return OK_ALIGN_TO (window_box_right_offset (it->w, TEXT_AREA));
23951 if (EQ (prop, Qcenter))
23952 return OK_ALIGN_TO (window_box_left_offset (it->w, TEXT_AREA)
23953 + window_box_width (it->w, TEXT_AREA) / 2);
23954 if (EQ (prop, Qleft_fringe))
23955 return OK_ALIGN_TO (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (it->w)
23956 ? WINDOW_LEFT_SCROLL_BAR_AREA_WIDTH (it->w)
23957 : window_box_right_offset (it->w, LEFT_MARGIN_AREA));
23958 if (EQ (prop, Qright_fringe))
23959 return OK_ALIGN_TO (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (it->w)
23960 ? window_box_right_offset (it->w, RIGHT_MARGIN_AREA)
23961 : window_box_right_offset (it->w, TEXT_AREA));
23962 if (EQ (prop, Qleft_margin))
23963 return OK_ALIGN_TO (window_box_left_offset (it->w, LEFT_MARGIN_AREA));
23964 if (EQ (prop, Qright_margin))
23965 return OK_ALIGN_TO (window_box_left_offset (it->w, RIGHT_MARGIN_AREA));
23966 if (EQ (prop, Qscroll_bar))
23967 return OK_ALIGN_TO (WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_LEFT (it->w)
23968 ? 0
23969 : (window_box_right_offset (it->w, RIGHT_MARGIN_AREA)
23970 + (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (it->w)
23971 ? WINDOW_RIGHT_FRINGE_WIDTH (it->w)
23972 : 0)));
23973 }
23974 else
23975 {
23976 if (EQ (prop, Qleft_fringe))
23977 return OK_PIXELS (WINDOW_LEFT_FRINGE_WIDTH (it->w));
23978 if (EQ (prop, Qright_fringe))
23979 return OK_PIXELS (WINDOW_RIGHT_FRINGE_WIDTH (it->w));
23980 if (EQ (prop, Qleft_margin))
23981 return OK_PIXELS (WINDOW_LEFT_MARGIN_WIDTH (it->w));
23982 if (EQ (prop, Qright_margin))
23983 return OK_PIXELS (WINDOW_RIGHT_MARGIN_WIDTH (it->w));
23984 if (EQ (prop, Qscroll_bar))
23985 return OK_PIXELS (WINDOW_SCROLL_BAR_AREA_WIDTH (it->w));
23986 }
23987
23988 prop = buffer_local_value (prop, it->w->contents);
23989 if (EQ (prop, Qunbound))
23990 prop = Qnil;
23991 }
23992
23993 if (INTEGERP (prop) || FLOATP (prop))
23994 {
23995 int base_unit = (width_p
23996 ? FRAME_COLUMN_WIDTH (it->f)
23997 : FRAME_LINE_HEIGHT (it->f));
23998 return OK_PIXELS (XFLOATINT (prop) * base_unit);
23999 }
24000
24001 if (CONSP (prop))
24002 {
24003 Lisp_Object car = XCAR (prop);
24004 Lisp_Object cdr = XCDR (prop);
24005
24006 if (SYMBOLP (car))
24007 {
24008 #ifdef HAVE_WINDOW_SYSTEM
24009 if (FRAME_WINDOW_P (it->f)
24010 && valid_image_p (prop))
24011 {
24012 ptrdiff_t id = lookup_image (it->f, prop);
24013 struct image *img = IMAGE_FROM_ID (it->f, id);
24014
24015 return OK_PIXELS (width_p ? img->width : img->height);
24016 }
24017 #endif
24018 if (EQ (car, Qplus) || EQ (car, Qminus))
24019 {
24020 int first = 1;
24021 double px;
24022
24023 pixels = 0;
24024 while (CONSP (cdr))
24025 {
24026 if (!calc_pixel_width_or_height (&px, it, XCAR (cdr),
24027 font, width_p, align_to))
24028 return 0;
24029 if (first)
24030 pixels = (EQ (car, Qplus) ? px : -px), first = 0;
24031 else
24032 pixels += px;
24033 cdr = XCDR (cdr);
24034 }
24035 if (EQ (car, Qminus))
24036 pixels = -pixels;
24037 return OK_PIXELS (pixels);
24038 }
24039
24040 car = buffer_local_value (car, it->w->contents);
24041 if (EQ (car, Qunbound))
24042 car = Qnil;
24043 }
24044
24045 if (INTEGERP (car) || FLOATP (car))
24046 {
24047 double fact;
24048 pixels = XFLOATINT (car);
24049 if (NILP (cdr))
24050 return OK_PIXELS (pixels);
24051 if (calc_pixel_width_or_height (&fact, it, cdr,
24052 font, width_p, align_to))
24053 return OK_PIXELS (pixels * fact);
24054 return 0;
24055 }
24056
24057 return 0;
24058 }
24059
24060 return 0;
24061 }
24062
24063 \f
24064 /***********************************************************************
24065 Glyph Display
24066 ***********************************************************************/
24067
24068 #ifdef HAVE_WINDOW_SYSTEM
24069
24070 #ifdef GLYPH_DEBUG
24071
24072 void
24073 dump_glyph_string (struct glyph_string *s)
24074 {
24075 fprintf (stderr, "glyph string\n");
24076 fprintf (stderr, " x, y, w, h = %d, %d, %d, %d\n",
24077 s->x, s->y, s->width, s->height);
24078 fprintf (stderr, " ybase = %d\n", s->ybase);
24079 fprintf (stderr, " hl = %d\n", s->hl);
24080 fprintf (stderr, " left overhang = %d, right = %d\n",
24081 s->left_overhang, s->right_overhang);
24082 fprintf (stderr, " nchars = %d\n", s->nchars);
24083 fprintf (stderr, " extends to end of line = %d\n",
24084 s->extends_to_end_of_line_p);
24085 fprintf (stderr, " font height = %d\n", FONT_HEIGHT (s->font));
24086 fprintf (stderr, " bg width = %d\n", s->background_width);
24087 }
24088
24089 #endif /* GLYPH_DEBUG */
24090
24091 /* Initialize glyph string S. CHAR2B is a suitably allocated vector
24092 of XChar2b structures for S; it can't be allocated in
24093 init_glyph_string because it must be allocated via `alloca'. W
24094 is the window on which S is drawn. ROW and AREA are the glyph row
24095 and area within the row from which S is constructed. START is the
24096 index of the first glyph structure covered by S. HL is a
24097 face-override for drawing S. */
24098
24099 #ifdef HAVE_NTGUI
24100 #define OPTIONAL_HDC(hdc) HDC hdc,
24101 #define DECLARE_HDC(hdc) HDC hdc;
24102 #define ALLOCATE_HDC(hdc, f) hdc = get_frame_dc ((f))
24103 #define RELEASE_HDC(hdc, f) release_frame_dc ((f), (hdc))
24104 #endif
24105
24106 #ifndef OPTIONAL_HDC
24107 #define OPTIONAL_HDC(hdc)
24108 #define DECLARE_HDC(hdc)
24109 #define ALLOCATE_HDC(hdc, f)
24110 #define RELEASE_HDC(hdc, f)
24111 #endif
24112
24113 static void
24114 init_glyph_string (struct glyph_string *s,
24115 OPTIONAL_HDC (hdc)
24116 XChar2b *char2b, struct window *w, struct glyph_row *row,
24117 enum glyph_row_area area, int start, enum draw_glyphs_face hl)
24118 {
24119 memset (s, 0, sizeof *s);
24120 s->w = w;
24121 s->f = XFRAME (w->frame);
24122 #ifdef HAVE_NTGUI
24123 s->hdc = hdc;
24124 #endif
24125 s->display = FRAME_X_DISPLAY (s->f);
24126 s->window = FRAME_X_WINDOW (s->f);
24127 s->char2b = char2b;
24128 s->hl = hl;
24129 s->row = row;
24130 s->area = area;
24131 s->first_glyph = row->glyphs[area] + start;
24132 s->height = row->height;
24133 s->y = WINDOW_TO_FRAME_PIXEL_Y (w, row->y);
24134 s->ybase = s->y + row->ascent;
24135 }
24136
24137
24138 /* Append the list of glyph strings with head H and tail T to the list
24139 with head *HEAD and tail *TAIL. Set *HEAD and *TAIL to the result. */
24140
24141 static void
24142 append_glyph_string_lists (struct glyph_string **head, struct glyph_string **tail,
24143 struct glyph_string *h, struct glyph_string *t)
24144 {
24145 if (h)
24146 {
24147 if (*head)
24148 (*tail)->next = h;
24149 else
24150 *head = h;
24151 h->prev = *tail;
24152 *tail = t;
24153 }
24154 }
24155
24156
24157 /* Prepend the list of glyph strings with head H and tail T to the
24158 list with head *HEAD and tail *TAIL. Set *HEAD and *TAIL to the
24159 result. */
24160
24161 static void
24162 prepend_glyph_string_lists (struct glyph_string **head, struct glyph_string **tail,
24163 struct glyph_string *h, struct glyph_string *t)
24164 {
24165 if (h)
24166 {
24167 if (*head)
24168 (*head)->prev = t;
24169 else
24170 *tail = t;
24171 t->next = *head;
24172 *head = h;
24173 }
24174 }
24175
24176
24177 /* Append glyph string S to the list with head *HEAD and tail *TAIL.
24178 Set *HEAD and *TAIL to the resulting list. */
24179
24180 static void
24181 append_glyph_string (struct glyph_string **head, struct glyph_string **tail,
24182 struct glyph_string *s)
24183 {
24184 s->next = s->prev = NULL;
24185 append_glyph_string_lists (head, tail, s, s);
24186 }
24187
24188
24189 /* Get face and two-byte form of character C in face FACE_ID on frame F.
24190 The encoding of C is returned in *CHAR2B. DISPLAY_P non-zero means
24191 make sure that X resources for the face returned are allocated.
24192 Value is a pointer to a realized face that is ready for display if
24193 DISPLAY_P is non-zero. */
24194
24195 static struct face *
24196 get_char_face_and_encoding (struct frame *f, int c, int face_id,
24197 XChar2b *char2b, int display_p)
24198 {
24199 struct face *face = FACE_FROM_ID (f, face_id);
24200 unsigned code = 0;
24201
24202 if (face->font)
24203 {
24204 code = face->font->driver->encode_char (face->font, c);
24205
24206 if (code == FONT_INVALID_CODE)
24207 code = 0;
24208 }
24209 STORE_XCHAR2B (char2b, (code >> 8), (code & 0xFF));
24210
24211 /* Make sure X resources of the face are allocated. */
24212 #ifdef HAVE_X_WINDOWS
24213 if (display_p)
24214 #endif
24215 {
24216 eassert (face != NULL);
24217 prepare_face_for_display (f, face);
24218 }
24219
24220 return face;
24221 }
24222
24223
24224 /* Get face and two-byte form of character glyph GLYPH on frame F.
24225 The encoding of GLYPH->u.ch is returned in *CHAR2B. Value is
24226 a pointer to a realized face that is ready for display. */
24227
24228 static struct face *
24229 get_glyph_face_and_encoding (struct frame *f, struct glyph *glyph,
24230 XChar2b *char2b, int *two_byte_p)
24231 {
24232 struct face *face;
24233 unsigned code = 0;
24234
24235 eassert (glyph->type == CHAR_GLYPH);
24236 face = FACE_FROM_ID (f, glyph->face_id);
24237
24238 /* Make sure X resources of the face are allocated. */
24239 eassert (face != NULL);
24240 prepare_face_for_display (f, face);
24241
24242 if (two_byte_p)
24243 *two_byte_p = 0;
24244
24245 if (face->font)
24246 {
24247 if (CHAR_BYTE8_P (glyph->u.ch))
24248 code = CHAR_TO_BYTE8 (glyph->u.ch);
24249 else
24250 code = face->font->driver->encode_char (face->font, glyph->u.ch);
24251
24252 if (code == FONT_INVALID_CODE)
24253 code = 0;
24254 }
24255
24256 STORE_XCHAR2B (char2b, (code >> 8), (code & 0xFF));
24257 return face;
24258 }
24259
24260
24261 /* Get glyph code of character C in FONT in the two-byte form CHAR2B.
24262 Return 1 if FONT has a glyph for C, otherwise return 0. */
24263
24264 static int
24265 get_char_glyph_code (int c, struct font *font, XChar2b *char2b)
24266 {
24267 unsigned code;
24268
24269 if (CHAR_BYTE8_P (c))
24270 code = CHAR_TO_BYTE8 (c);
24271 else
24272 code = font->driver->encode_char (font, c);
24273
24274 if (code == FONT_INVALID_CODE)
24275 return 0;
24276 STORE_XCHAR2B (char2b, (code >> 8), (code & 0xFF));
24277 return 1;
24278 }
24279
24280
24281 /* Fill glyph string S with composition components specified by S->cmp.
24282
24283 BASE_FACE is the base face of the composition.
24284 S->cmp_from is the index of the first component for S.
24285
24286 OVERLAPS non-zero means S should draw the foreground only, and use
24287 its physical height for clipping. See also draw_glyphs.
24288
24289 Value is the index of a component not in S. */
24290
24291 static int
24292 fill_composite_glyph_string (struct glyph_string *s, struct face *base_face,
24293 int overlaps)
24294 {
24295 int i;
24296 /* For all glyphs of this composition, starting at the offset
24297 S->cmp_from, until we reach the end of the definition or encounter a
24298 glyph that requires the different face, add it to S. */
24299 struct face *face;
24300
24301 eassert (s);
24302
24303 s->for_overlaps = overlaps;
24304 s->face = NULL;
24305 s->font = NULL;
24306 for (i = s->cmp_from; i < s->cmp->glyph_len; i++)
24307 {
24308 int c = COMPOSITION_GLYPH (s->cmp, i);
24309
24310 /* TAB in a composition means display glyphs with padding space
24311 on the left or right. */
24312 if (c != '\t')
24313 {
24314 int face_id = FACE_FOR_CHAR (s->f, base_face->ascii_face, c,
24315 -1, Qnil);
24316
24317 face = get_char_face_and_encoding (s->f, c, face_id,
24318 s->char2b + i, 1);
24319 if (face)
24320 {
24321 if (! s->face)
24322 {
24323 s->face = face;
24324 s->font = s->face->font;
24325 }
24326 else if (s->face != face)
24327 break;
24328 }
24329 }
24330 ++s->nchars;
24331 }
24332 s->cmp_to = i;
24333
24334 if (s->face == NULL)
24335 {
24336 s->face = base_face->ascii_face;
24337 s->font = s->face->font;
24338 }
24339
24340 /* All glyph strings for the same composition has the same width,
24341 i.e. the width set for the first component of the composition. */
24342 s->width = s->first_glyph->pixel_width;
24343
24344 /* If the specified font could not be loaded, use the frame's
24345 default font, but record the fact that we couldn't load it in
24346 the glyph string so that we can draw rectangles for the
24347 characters of the glyph string. */
24348 if (s->font == NULL)
24349 {
24350 s->font_not_found_p = 1;
24351 s->font = FRAME_FONT (s->f);
24352 }
24353
24354 /* Adjust base line for subscript/superscript text. */
24355 s->ybase += s->first_glyph->voffset;
24356
24357 /* This glyph string must always be drawn with 16-bit functions. */
24358 s->two_byte_p = 1;
24359
24360 return s->cmp_to;
24361 }
24362
24363 static int
24364 fill_gstring_glyph_string (struct glyph_string *s, int face_id,
24365 int start, int end, int overlaps)
24366 {
24367 struct glyph *glyph, *last;
24368 Lisp_Object lgstring;
24369 int i;
24370
24371 s->for_overlaps = overlaps;
24372 glyph = s->row->glyphs[s->area] + start;
24373 last = s->row->glyphs[s->area] + end;
24374 s->cmp_id = glyph->u.cmp.id;
24375 s->cmp_from = glyph->slice.cmp.from;
24376 s->cmp_to = glyph->slice.cmp.to + 1;
24377 s->face = FACE_FROM_ID (s->f, face_id);
24378 lgstring = composition_gstring_from_id (s->cmp_id);
24379 s->font = XFONT_OBJECT (LGSTRING_FONT (lgstring));
24380 glyph++;
24381 while (glyph < last
24382 && glyph->u.cmp.automatic
24383 && glyph->u.cmp.id == s->cmp_id
24384 && s->cmp_to == glyph->slice.cmp.from)
24385 s->cmp_to = (glyph++)->slice.cmp.to + 1;
24386
24387 for (i = s->cmp_from; i < s->cmp_to; i++)
24388 {
24389 Lisp_Object lglyph = LGSTRING_GLYPH (lgstring, i);
24390 unsigned code = LGLYPH_CODE (lglyph);
24391
24392 STORE_XCHAR2B ((s->char2b + i), code >> 8, code & 0xFF);
24393 }
24394 s->width = composition_gstring_width (lgstring, s->cmp_from, s->cmp_to, NULL);
24395 return glyph - s->row->glyphs[s->area];
24396 }
24397
24398
24399 /* Fill glyph string S from a sequence glyphs for glyphless characters.
24400 See the comment of fill_glyph_string for arguments.
24401 Value is the index of the first glyph not in S. */
24402
24403
24404 static int
24405 fill_glyphless_glyph_string (struct glyph_string *s, int face_id,
24406 int start, int end, int overlaps)
24407 {
24408 struct glyph *glyph, *last;
24409 int voffset;
24410
24411 eassert (s->first_glyph->type == GLYPHLESS_GLYPH);
24412 s->for_overlaps = overlaps;
24413 glyph = s->row->glyphs[s->area] + start;
24414 last = s->row->glyphs[s->area] + end;
24415 voffset = glyph->voffset;
24416 s->face = FACE_FROM_ID (s->f, face_id);
24417 s->font = s->face->font ? s->face->font : FRAME_FONT (s->f);
24418 s->nchars = 1;
24419 s->width = glyph->pixel_width;
24420 glyph++;
24421 while (glyph < last
24422 && glyph->type == GLYPHLESS_GLYPH
24423 && glyph->voffset == voffset
24424 && glyph->face_id == face_id)
24425 {
24426 s->nchars++;
24427 s->width += glyph->pixel_width;
24428 glyph++;
24429 }
24430 s->ybase += voffset;
24431 return glyph - s->row->glyphs[s->area];
24432 }
24433
24434
24435 /* Fill glyph string S from a sequence of character glyphs.
24436
24437 FACE_ID is the face id of the string. START is the index of the
24438 first glyph to consider, END is the index of the last + 1.
24439 OVERLAPS non-zero means S should draw the foreground only, and use
24440 its physical height for clipping. See also draw_glyphs.
24441
24442 Value is the index of the first glyph not in S. */
24443
24444 static int
24445 fill_glyph_string (struct glyph_string *s, int face_id,
24446 int start, int end, int overlaps)
24447 {
24448 struct glyph *glyph, *last;
24449 int voffset;
24450 int glyph_not_available_p;
24451
24452 eassert (s->f == XFRAME (s->w->frame));
24453 eassert (s->nchars == 0);
24454 eassert (start >= 0 && end > start);
24455
24456 s->for_overlaps = overlaps;
24457 glyph = s->row->glyphs[s->area] + start;
24458 last = s->row->glyphs[s->area] + end;
24459 voffset = glyph->voffset;
24460 s->padding_p = glyph->padding_p;
24461 glyph_not_available_p = glyph->glyph_not_available_p;
24462
24463 while (glyph < last
24464 && glyph->type == CHAR_GLYPH
24465 && glyph->voffset == voffset
24466 /* Same face id implies same font, nowadays. */
24467 && glyph->face_id == face_id
24468 && glyph->glyph_not_available_p == glyph_not_available_p)
24469 {
24470 int two_byte_p;
24471
24472 s->face = get_glyph_face_and_encoding (s->f, glyph,
24473 s->char2b + s->nchars,
24474 &two_byte_p);
24475 s->two_byte_p = two_byte_p;
24476 ++s->nchars;
24477 eassert (s->nchars <= end - start);
24478 s->width += glyph->pixel_width;
24479 if (glyph++->padding_p != s->padding_p)
24480 break;
24481 }
24482
24483 s->font = s->face->font;
24484
24485 /* If the specified font could not be loaded, use the frame's font,
24486 but record the fact that we couldn't load it in
24487 S->font_not_found_p so that we can draw rectangles for the
24488 characters of the glyph string. */
24489 if (s->font == NULL || glyph_not_available_p)
24490 {
24491 s->font_not_found_p = 1;
24492 s->font = FRAME_FONT (s->f);
24493 }
24494
24495 /* Adjust base line for subscript/superscript text. */
24496 s->ybase += voffset;
24497
24498 eassert (s->face && s->face->gc);
24499 return glyph - s->row->glyphs[s->area];
24500 }
24501
24502
24503 /* Fill glyph string S from image glyph S->first_glyph. */
24504
24505 static void
24506 fill_image_glyph_string (struct glyph_string *s)
24507 {
24508 eassert (s->first_glyph->type == IMAGE_GLYPH);
24509 s->img = IMAGE_FROM_ID (s->f, s->first_glyph->u.img_id);
24510 eassert (s->img);
24511 s->slice = s->first_glyph->slice.img;
24512 s->face = FACE_FROM_ID (s->f, s->first_glyph->face_id);
24513 s->font = s->face->font;
24514 s->width = s->first_glyph->pixel_width;
24515
24516 /* Adjust base line for subscript/superscript text. */
24517 s->ybase += s->first_glyph->voffset;
24518 }
24519
24520
24521 /* Fill glyph string S from a sequence of stretch glyphs.
24522
24523 START is the index of the first glyph to consider,
24524 END is the index of the last + 1.
24525
24526 Value is the index of the first glyph not in S. */
24527
24528 static int
24529 fill_stretch_glyph_string (struct glyph_string *s, int start, int end)
24530 {
24531 struct glyph *glyph, *last;
24532 int voffset, face_id;
24533
24534 eassert (s->first_glyph->type == STRETCH_GLYPH);
24535
24536 glyph = s->row->glyphs[s->area] + start;
24537 last = s->row->glyphs[s->area] + end;
24538 face_id = glyph->face_id;
24539 s->face = FACE_FROM_ID (s->f, face_id);
24540 s->font = s->face->font;
24541 s->width = glyph->pixel_width;
24542 s->nchars = 1;
24543 voffset = glyph->voffset;
24544
24545 for (++glyph;
24546 (glyph < last
24547 && glyph->type == STRETCH_GLYPH
24548 && glyph->voffset == voffset
24549 && glyph->face_id == face_id);
24550 ++glyph)
24551 s->width += glyph->pixel_width;
24552
24553 /* Adjust base line for subscript/superscript text. */
24554 s->ybase += voffset;
24555
24556 /* The case that face->gc == 0 is handled when drawing the glyph
24557 string by calling prepare_face_for_display. */
24558 eassert (s->face);
24559 return glyph - s->row->glyphs[s->area];
24560 }
24561
24562 static struct font_metrics *
24563 get_per_char_metric (struct font *font, XChar2b *char2b)
24564 {
24565 static struct font_metrics metrics;
24566 unsigned code;
24567
24568 if (! font)
24569 return NULL;
24570 code = (XCHAR2B_BYTE1 (char2b) << 8) | XCHAR2B_BYTE2 (char2b);
24571 if (code == FONT_INVALID_CODE)
24572 return NULL;
24573 font->driver->text_extents (font, &code, 1, &metrics);
24574 return &metrics;
24575 }
24576
24577 /* EXPORT for RIF:
24578 Set *LEFT and *RIGHT to the left and right overhang of GLYPH on
24579 frame F. Overhangs of glyphs other than type CHAR_GLYPH are
24580 assumed to be zero. */
24581
24582 void
24583 x_get_glyph_overhangs (struct glyph *glyph, struct frame *f, int *left, int *right)
24584 {
24585 *left = *right = 0;
24586
24587 if (glyph->type == CHAR_GLYPH)
24588 {
24589 struct face *face;
24590 XChar2b char2b;
24591 struct font_metrics *pcm;
24592
24593 face = get_glyph_face_and_encoding (f, glyph, &char2b, NULL);
24594 if (face->font && (pcm = get_per_char_metric (face->font, &char2b)))
24595 {
24596 if (pcm->rbearing > pcm->width)
24597 *right = pcm->rbearing - pcm->width;
24598 if (pcm->lbearing < 0)
24599 *left = -pcm->lbearing;
24600 }
24601 }
24602 else if (glyph->type == COMPOSITE_GLYPH)
24603 {
24604 if (! glyph->u.cmp.automatic)
24605 {
24606 struct composition *cmp = composition_table[glyph->u.cmp.id];
24607
24608 if (cmp->rbearing > cmp->pixel_width)
24609 *right = cmp->rbearing - cmp->pixel_width;
24610 if (cmp->lbearing < 0)
24611 *left = - cmp->lbearing;
24612 }
24613 else
24614 {
24615 Lisp_Object gstring = composition_gstring_from_id (glyph->u.cmp.id);
24616 struct font_metrics metrics;
24617
24618 composition_gstring_width (gstring, glyph->slice.cmp.from,
24619 glyph->slice.cmp.to + 1, &metrics);
24620 if (metrics.rbearing > metrics.width)
24621 *right = metrics.rbearing - metrics.width;
24622 if (metrics.lbearing < 0)
24623 *left = - metrics.lbearing;
24624 }
24625 }
24626 }
24627
24628
24629 /* Return the index of the first glyph preceding glyph string S that
24630 is overwritten by S because of S's left overhang. Value is -1
24631 if no glyphs are overwritten. */
24632
24633 static int
24634 left_overwritten (struct glyph_string *s)
24635 {
24636 int k;
24637
24638 if (s->left_overhang)
24639 {
24640 int x = 0, i;
24641 struct glyph *glyphs = s->row->glyphs[s->area];
24642 int first = s->first_glyph - glyphs;
24643
24644 for (i = first - 1; i >= 0 && x > -s->left_overhang; --i)
24645 x -= glyphs[i].pixel_width;
24646
24647 k = i + 1;
24648 }
24649 else
24650 k = -1;
24651
24652 return k;
24653 }
24654
24655
24656 /* Return the index of the first glyph preceding glyph string S that
24657 is overwriting S because of its right overhang. Value is -1 if no
24658 glyph in front of S overwrites S. */
24659
24660 static int
24661 left_overwriting (struct glyph_string *s)
24662 {
24663 int i, k, x;
24664 struct glyph *glyphs = s->row->glyphs[s->area];
24665 int first = s->first_glyph - glyphs;
24666
24667 k = -1;
24668 x = 0;
24669 for (i = first - 1; i >= 0; --i)
24670 {
24671 int left, right;
24672 x_get_glyph_overhangs (glyphs + i, s->f, &left, &right);
24673 if (x + right > 0)
24674 k = i;
24675 x -= glyphs[i].pixel_width;
24676 }
24677
24678 return k;
24679 }
24680
24681
24682 /* Return the index of the last glyph following glyph string S that is
24683 overwritten by S because of S's right overhang. Value is -1 if
24684 no such glyph is found. */
24685
24686 static int
24687 right_overwritten (struct glyph_string *s)
24688 {
24689 int k = -1;
24690
24691 if (s->right_overhang)
24692 {
24693 int x = 0, i;
24694 struct glyph *glyphs = s->row->glyphs[s->area];
24695 int first = (s->first_glyph - glyphs
24696 + (s->first_glyph->type == COMPOSITE_GLYPH ? 1 : s->nchars));
24697 int end = s->row->used[s->area];
24698
24699 for (i = first; i < end && s->right_overhang > x; ++i)
24700 x += glyphs[i].pixel_width;
24701
24702 k = i;
24703 }
24704
24705 return k;
24706 }
24707
24708
24709 /* Return the index of the last glyph following glyph string S that
24710 overwrites S because of its left overhang. Value is negative
24711 if no such glyph is found. */
24712
24713 static int
24714 right_overwriting (struct glyph_string *s)
24715 {
24716 int i, k, x;
24717 int end = s->row->used[s->area];
24718 struct glyph *glyphs = s->row->glyphs[s->area];
24719 int first = (s->first_glyph - glyphs
24720 + (s->first_glyph->type == COMPOSITE_GLYPH ? 1 : s->nchars));
24721
24722 k = -1;
24723 x = 0;
24724 for (i = first; i < end; ++i)
24725 {
24726 int left, right;
24727 x_get_glyph_overhangs (glyphs + i, s->f, &left, &right);
24728 if (x - left < 0)
24729 k = i;
24730 x += glyphs[i].pixel_width;
24731 }
24732
24733 return k;
24734 }
24735
24736
24737 /* Set background width of glyph string S. START is the index of the
24738 first glyph following S. LAST_X is the right-most x-position + 1
24739 in the drawing area. */
24740
24741 static void
24742 set_glyph_string_background_width (struct glyph_string *s, int start, int last_x)
24743 {
24744 /* If the face of this glyph string has to be drawn to the end of
24745 the drawing area, set S->extends_to_end_of_line_p. */
24746
24747 if (start == s->row->used[s->area]
24748 && ((s->row->fill_line_p
24749 && (s->hl == DRAW_NORMAL_TEXT
24750 || s->hl == DRAW_IMAGE_RAISED
24751 || s->hl == DRAW_IMAGE_SUNKEN))
24752 || s->hl == DRAW_MOUSE_FACE))
24753 s->extends_to_end_of_line_p = 1;
24754
24755 /* If S extends its face to the end of the line, set its
24756 background_width to the distance to the right edge of the drawing
24757 area. */
24758 if (s->extends_to_end_of_line_p)
24759 s->background_width = last_x - s->x + 1;
24760 else
24761 s->background_width = s->width;
24762 }
24763
24764
24765 /* Compute overhangs and x-positions for glyph string S and its
24766 predecessors, or successors. X is the starting x-position for S.
24767 BACKWARD_P non-zero means process predecessors. */
24768
24769 static void
24770 compute_overhangs_and_x (struct glyph_string *s, int x, int backward_p)
24771 {
24772 if (backward_p)
24773 {
24774 while (s)
24775 {
24776 if (FRAME_RIF (s->f)->compute_glyph_string_overhangs)
24777 FRAME_RIF (s->f)->compute_glyph_string_overhangs (s);
24778 x -= s->width;
24779 s->x = x;
24780 s = s->prev;
24781 }
24782 }
24783 else
24784 {
24785 while (s)
24786 {
24787 if (FRAME_RIF (s->f)->compute_glyph_string_overhangs)
24788 FRAME_RIF (s->f)->compute_glyph_string_overhangs (s);
24789 s->x = x;
24790 x += s->width;
24791 s = s->next;
24792 }
24793 }
24794 }
24795
24796
24797
24798 /* The following macros are only called from draw_glyphs below.
24799 They reference the following parameters of that function directly:
24800 `w', `row', `area', and `overlap_p'
24801 as well as the following local variables:
24802 `s', `f', and `hdc' (in W32) */
24803
24804 #ifdef HAVE_NTGUI
24805 /* On W32, silently add local `hdc' variable to argument list of
24806 init_glyph_string. */
24807 #define INIT_GLYPH_STRING(s, char2b, w, row, area, start, hl) \
24808 init_glyph_string (s, hdc, char2b, w, row, area, start, hl)
24809 #else
24810 #define INIT_GLYPH_STRING(s, char2b, w, row, area, start, hl) \
24811 init_glyph_string (s, char2b, w, row, area, start, hl)
24812 #endif
24813
24814 /* Add a glyph string for a stretch glyph to the list of strings
24815 between HEAD and TAIL. START is the index of the stretch glyph in
24816 row area AREA of glyph row ROW. END is the index of the last glyph
24817 in that glyph row area. X is the current output position assigned
24818 to the new glyph string constructed. HL overrides that face of the
24819 glyph; e.g. it is DRAW_CURSOR if a cursor has to be drawn. LAST_X
24820 is the right-most x-position of the drawing area. */
24821
24822 /* SunOS 4 bundled cc, barfed on continuations in the arg lists here
24823 and below -- keep them on one line. */
24824 #define BUILD_STRETCH_GLYPH_STRING(START, END, HEAD, TAIL, HL, X, LAST_X) \
24825 do \
24826 { \
24827 s = alloca (sizeof *s); \
24828 INIT_GLYPH_STRING (s, NULL, w, row, area, START, HL); \
24829 START = fill_stretch_glyph_string (s, START, END); \
24830 append_glyph_string (&HEAD, &TAIL, s); \
24831 s->x = (X); \
24832 } \
24833 while (0)
24834
24835
24836 /* Add a glyph string for an image glyph to the list of strings
24837 between HEAD and TAIL. START is the index of the image glyph in
24838 row area AREA of glyph row ROW. END is the index of the last glyph
24839 in that glyph row area. X is the current output position assigned
24840 to the new glyph string constructed. HL overrides that face of the
24841 glyph; e.g. it is DRAW_CURSOR if a cursor has to be drawn. LAST_X
24842 is the right-most x-position of the drawing area. */
24843
24844 #define BUILD_IMAGE_GLYPH_STRING(START, END, HEAD, TAIL, HL, X, LAST_X) \
24845 do \
24846 { \
24847 s = alloca (sizeof *s); \
24848 INIT_GLYPH_STRING (s, NULL, w, row, area, START, HL); \
24849 fill_image_glyph_string (s); \
24850 append_glyph_string (&HEAD, &TAIL, s); \
24851 ++START; \
24852 s->x = (X); \
24853 } \
24854 while (0)
24855
24856
24857 /* Add a glyph string for a sequence of character glyphs to the list
24858 of strings between HEAD and TAIL. START is the index of the first
24859 glyph in row area AREA of glyph row ROW that is part of the new
24860 glyph string. END is the index of the last glyph in that glyph row
24861 area. X is the current output position assigned to the new glyph
24862 string constructed. HL overrides that face of the glyph; e.g. it
24863 is DRAW_CURSOR if a cursor has to be drawn. LAST_X is the
24864 right-most x-position of the drawing area. */
24865
24866 #define BUILD_CHAR_GLYPH_STRINGS(START, END, HEAD, TAIL, HL, X, LAST_X) \
24867 do \
24868 { \
24869 int face_id; \
24870 XChar2b *char2b; \
24871 \
24872 face_id = (row)->glyphs[area][START].face_id; \
24873 \
24874 s = alloca (sizeof *s); \
24875 SAFE_NALLOCA (char2b, 1, (END) - (START)); \
24876 INIT_GLYPH_STRING (s, char2b, w, row, area, START, HL); \
24877 append_glyph_string (&HEAD, &TAIL, s); \
24878 s->x = (X); \
24879 START = fill_glyph_string (s, face_id, START, END, overlaps); \
24880 } \
24881 while (0)
24882
24883
24884 /* Add a glyph string for a composite sequence to the list of strings
24885 between HEAD and TAIL. START is the index of the first glyph in
24886 row area AREA of glyph row ROW that is part of the new glyph
24887 string. END is the index of the last glyph in that glyph row area.
24888 X is the current output position assigned to the new glyph string
24889 constructed. HL overrides that face of the glyph; e.g. it is
24890 DRAW_CURSOR if a cursor has to be drawn. LAST_X is the right-most
24891 x-position of the drawing area. */
24892
24893 #define BUILD_COMPOSITE_GLYPH_STRING(START, END, HEAD, TAIL, HL, X, LAST_X) \
24894 do { \
24895 int face_id = (row)->glyphs[area][START].face_id; \
24896 struct face *base_face = FACE_FROM_ID (f, face_id); \
24897 ptrdiff_t cmp_id = (row)->glyphs[area][START].u.cmp.id; \
24898 struct composition *cmp = composition_table[cmp_id]; \
24899 XChar2b *char2b; \
24900 struct glyph_string *first_s = NULL; \
24901 int n; \
24902 \
24903 SAFE_NALLOCA (char2b, 1, cmp->glyph_len); \
24904 \
24905 /* Make glyph_strings for each glyph sequence that is drawable by \
24906 the same face, and append them to HEAD/TAIL. */ \
24907 for (n = 0; n < cmp->glyph_len;) \
24908 { \
24909 s = alloca (sizeof *s); \
24910 INIT_GLYPH_STRING (s, char2b, w, row, area, START, HL); \
24911 append_glyph_string (&(HEAD), &(TAIL), s); \
24912 s->cmp = cmp; \
24913 s->cmp_from = n; \
24914 s->x = (X); \
24915 if (n == 0) \
24916 first_s = s; \
24917 n = fill_composite_glyph_string (s, base_face, overlaps); \
24918 } \
24919 \
24920 ++START; \
24921 s = first_s; \
24922 } while (0)
24923
24924
24925 /* Add a glyph string for a glyph-string sequence to the list of strings
24926 between HEAD and TAIL. */
24927
24928 #define BUILD_GSTRING_GLYPH_STRING(START, END, HEAD, TAIL, HL, X, LAST_X) \
24929 do { \
24930 int face_id; \
24931 XChar2b *char2b; \
24932 Lisp_Object gstring; \
24933 \
24934 face_id = (row)->glyphs[area][START].face_id; \
24935 gstring = (composition_gstring_from_id \
24936 ((row)->glyphs[area][START].u.cmp.id)); \
24937 s = alloca (sizeof *s); \
24938 SAFE_NALLOCA (char2b, 1, LGSTRING_GLYPH_LEN (gstring)); \
24939 INIT_GLYPH_STRING (s, char2b, w, row, area, START, HL); \
24940 append_glyph_string (&(HEAD), &(TAIL), s); \
24941 s->x = (X); \
24942 START = fill_gstring_glyph_string (s, face_id, START, END, overlaps); \
24943 } while (0)
24944
24945
24946 /* Add a glyph string for a sequence of glyphless character's glyphs
24947 to the list of strings between HEAD and TAIL. The meanings of
24948 arguments are the same as those of BUILD_CHAR_GLYPH_STRINGS. */
24949
24950 #define BUILD_GLYPHLESS_GLYPH_STRING(START, END, HEAD, TAIL, HL, X, LAST_X) \
24951 do \
24952 { \
24953 int face_id; \
24954 \
24955 face_id = (row)->glyphs[area][START].face_id; \
24956 \
24957 s = alloca (sizeof *s); \
24958 INIT_GLYPH_STRING (s, NULL, w, row, area, START, HL); \
24959 append_glyph_string (&HEAD, &TAIL, s); \
24960 s->x = (X); \
24961 START = fill_glyphless_glyph_string (s, face_id, START, END, \
24962 overlaps); \
24963 } \
24964 while (0)
24965
24966
24967 /* Build a list of glyph strings between HEAD and TAIL for the glyphs
24968 of AREA of glyph row ROW on window W between indices START and END.
24969 HL overrides the face for drawing glyph strings, e.g. it is
24970 DRAW_CURSOR to draw a cursor. X and LAST_X are start and end
24971 x-positions of the drawing area.
24972
24973 This is an ugly monster macro construct because we must use alloca
24974 to allocate glyph strings (because draw_glyphs can be called
24975 asynchronously). */
24976
24977 #define BUILD_GLYPH_STRINGS(START, END, HEAD, TAIL, HL, X, LAST_X) \
24978 do \
24979 { \
24980 HEAD = TAIL = NULL; \
24981 while (START < END) \
24982 { \
24983 struct glyph *first_glyph = (row)->glyphs[area] + START; \
24984 switch (first_glyph->type) \
24985 { \
24986 case CHAR_GLYPH: \
24987 BUILD_CHAR_GLYPH_STRINGS (START, END, HEAD, TAIL, \
24988 HL, X, LAST_X); \
24989 break; \
24990 \
24991 case COMPOSITE_GLYPH: \
24992 if (first_glyph->u.cmp.automatic) \
24993 BUILD_GSTRING_GLYPH_STRING (START, END, HEAD, TAIL, \
24994 HL, X, LAST_X); \
24995 else \
24996 BUILD_COMPOSITE_GLYPH_STRING (START, END, HEAD, TAIL, \
24997 HL, X, LAST_X); \
24998 break; \
24999 \
25000 case STRETCH_GLYPH: \
25001 BUILD_STRETCH_GLYPH_STRING (START, END, HEAD, TAIL, \
25002 HL, X, LAST_X); \
25003 break; \
25004 \
25005 case IMAGE_GLYPH: \
25006 BUILD_IMAGE_GLYPH_STRING (START, END, HEAD, TAIL, \
25007 HL, X, LAST_X); \
25008 break; \
25009 \
25010 case GLYPHLESS_GLYPH: \
25011 BUILD_GLYPHLESS_GLYPH_STRING (START, END, HEAD, TAIL, \
25012 HL, X, LAST_X); \
25013 break; \
25014 \
25015 default: \
25016 emacs_abort (); \
25017 } \
25018 \
25019 if (s) \
25020 { \
25021 set_glyph_string_background_width (s, START, LAST_X); \
25022 (X) += s->width; \
25023 } \
25024 } \
25025 } while (0)
25026
25027
25028 /* Draw glyphs between START and END in AREA of ROW on window W,
25029 starting at x-position X. X is relative to AREA in W. HL is a
25030 face-override with the following meaning:
25031
25032 DRAW_NORMAL_TEXT draw normally
25033 DRAW_CURSOR draw in cursor face
25034 DRAW_MOUSE_FACE draw in mouse face.
25035 DRAW_INVERSE_VIDEO draw in mode line face
25036 DRAW_IMAGE_SUNKEN draw an image with a sunken relief around it
25037 DRAW_IMAGE_RAISED draw an image with a raised relief around it
25038
25039 If OVERLAPS is non-zero, draw only the foreground of characters and
25040 clip to the physical height of ROW. Non-zero value also defines
25041 the overlapping part to be drawn:
25042
25043 OVERLAPS_PRED overlap with preceding rows
25044 OVERLAPS_SUCC overlap with succeeding rows
25045 OVERLAPS_BOTH overlap with both preceding/succeeding rows
25046 OVERLAPS_ERASED_CURSOR overlap with erased cursor area
25047
25048 Value is the x-position reached, relative to AREA of W. */
25049
25050 static int
25051 draw_glyphs (struct window *w, int x, struct glyph_row *row,
25052 enum glyph_row_area area, ptrdiff_t start, ptrdiff_t end,
25053 enum draw_glyphs_face hl, int overlaps)
25054 {
25055 struct glyph_string *head, *tail;
25056 struct glyph_string *s;
25057 struct glyph_string *clip_head = NULL, *clip_tail = NULL;
25058 int i, j, x_reached, last_x, area_left = 0;
25059 struct frame *f = XFRAME (WINDOW_FRAME (w));
25060 DECLARE_HDC (hdc);
25061
25062 ALLOCATE_HDC (hdc, f);
25063
25064 /* Let's rather be paranoid than getting a SEGV. */
25065 end = min (end, row->used[area]);
25066 start = clip_to_bounds (0, start, end);
25067
25068 /* Translate X to frame coordinates. Set last_x to the right
25069 end of the drawing area. */
25070 if (row->full_width_p)
25071 {
25072 /* X is relative to the left edge of W, without scroll bars
25073 or fringes. */
25074 area_left = WINDOW_LEFT_EDGE_X (w);
25075 last_x = (WINDOW_LEFT_EDGE_X (w) + WINDOW_PIXEL_WIDTH (w)
25076 - (row->mode_line_p ? WINDOW_RIGHT_DIVIDER_WIDTH (w) : 0));
25077 }
25078 else
25079 {
25080 area_left = window_box_left (w, area);
25081 last_x = area_left + window_box_width (w, area);
25082 }
25083 x += area_left;
25084
25085 /* Build a doubly-linked list of glyph_string structures between
25086 head and tail from what we have to draw. Note that the macro
25087 BUILD_GLYPH_STRINGS will modify its start parameter. That's
25088 the reason we use a separate variable `i'. */
25089 i = start;
25090 USE_SAFE_ALLOCA;
25091 BUILD_GLYPH_STRINGS (i, end, head, tail, hl, x, last_x);
25092 if (tail)
25093 x_reached = tail->x + tail->background_width;
25094 else
25095 x_reached = x;
25096
25097 /* If there are any glyphs with lbearing < 0 or rbearing > width in
25098 the row, redraw some glyphs in front or following the glyph
25099 strings built above. */
25100 if (head && !overlaps && row->contains_overlapping_glyphs_p)
25101 {
25102 struct glyph_string *h, *t;
25103 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
25104 int mouse_beg_col IF_LINT (= 0), mouse_end_col IF_LINT (= 0);
25105 int check_mouse_face = 0;
25106 int dummy_x = 0;
25107
25108 /* If mouse highlighting is on, we may need to draw adjacent
25109 glyphs using mouse-face highlighting. */
25110 if (area == TEXT_AREA && row->mouse_face_p
25111 && hlinfo->mouse_face_beg_row >= 0
25112 && hlinfo->mouse_face_end_row >= 0)
25113 {
25114 ptrdiff_t row_vpos = MATRIX_ROW_VPOS (row, w->current_matrix);
25115
25116 if (row_vpos >= hlinfo->mouse_face_beg_row
25117 && row_vpos <= hlinfo->mouse_face_end_row)
25118 {
25119 check_mouse_face = 1;
25120 mouse_beg_col = (row_vpos == hlinfo->mouse_face_beg_row)
25121 ? hlinfo->mouse_face_beg_col : 0;
25122 mouse_end_col = (row_vpos == hlinfo->mouse_face_end_row)
25123 ? hlinfo->mouse_face_end_col
25124 : row->used[TEXT_AREA];
25125 }
25126 }
25127
25128 /* Compute overhangs for all glyph strings. */
25129 if (FRAME_RIF (f)->compute_glyph_string_overhangs)
25130 for (s = head; s; s = s->next)
25131 FRAME_RIF (f)->compute_glyph_string_overhangs (s);
25132
25133 /* Prepend glyph strings for glyphs in front of the first glyph
25134 string that are overwritten because of the first glyph
25135 string's left overhang. The background of all strings
25136 prepended must be drawn because the first glyph string
25137 draws over it. */
25138 i = left_overwritten (head);
25139 if (i >= 0)
25140 {
25141 enum draw_glyphs_face overlap_hl;
25142
25143 /* If this row contains mouse highlighting, attempt to draw
25144 the overlapped glyphs with the correct highlight. This
25145 code fails if the overlap encompasses more than one glyph
25146 and mouse-highlight spans only some of these glyphs.
25147 However, making it work perfectly involves a lot more
25148 code, and I don't know if the pathological case occurs in
25149 practice, so we'll stick to this for now. --- cyd */
25150 if (check_mouse_face
25151 && mouse_beg_col < start && mouse_end_col > i)
25152 overlap_hl = DRAW_MOUSE_FACE;
25153 else
25154 overlap_hl = DRAW_NORMAL_TEXT;
25155
25156 if (hl != overlap_hl)
25157 clip_head = head;
25158 j = i;
25159 BUILD_GLYPH_STRINGS (j, start, h, t,
25160 overlap_hl, dummy_x, last_x);
25161 start = i;
25162 compute_overhangs_and_x (t, head->x, 1);
25163 prepend_glyph_string_lists (&head, &tail, h, t);
25164 if (clip_head == NULL)
25165 clip_head = head;
25166 }
25167
25168 /* Prepend glyph strings for glyphs in front of the first glyph
25169 string that overwrite that glyph string because of their
25170 right overhang. For these strings, only the foreground must
25171 be drawn, because it draws over the glyph string at `head'.
25172 The background must not be drawn because this would overwrite
25173 right overhangs of preceding glyphs for which no glyph
25174 strings exist. */
25175 i = left_overwriting (head);
25176 if (i >= 0)
25177 {
25178 enum draw_glyphs_face overlap_hl;
25179
25180 if (check_mouse_face
25181 && mouse_beg_col < start && mouse_end_col > i)
25182 overlap_hl = DRAW_MOUSE_FACE;
25183 else
25184 overlap_hl = DRAW_NORMAL_TEXT;
25185
25186 if (hl == overlap_hl || clip_head == NULL)
25187 clip_head = head;
25188 BUILD_GLYPH_STRINGS (i, start, h, t,
25189 overlap_hl, dummy_x, last_x);
25190 for (s = h; s; s = s->next)
25191 s->background_filled_p = 1;
25192 compute_overhangs_and_x (t, head->x, 1);
25193 prepend_glyph_string_lists (&head, &tail, h, t);
25194 }
25195
25196 /* Append glyphs strings for glyphs following the last glyph
25197 string tail that are overwritten by tail. The background of
25198 these strings has to be drawn because tail's foreground draws
25199 over it. */
25200 i = right_overwritten (tail);
25201 if (i >= 0)
25202 {
25203 enum draw_glyphs_face overlap_hl;
25204
25205 if (check_mouse_face
25206 && mouse_beg_col < i && mouse_end_col > end)
25207 overlap_hl = DRAW_MOUSE_FACE;
25208 else
25209 overlap_hl = DRAW_NORMAL_TEXT;
25210
25211 if (hl != overlap_hl)
25212 clip_tail = tail;
25213 BUILD_GLYPH_STRINGS (end, i, h, t,
25214 overlap_hl, x, last_x);
25215 /* Because BUILD_GLYPH_STRINGS updates the first argument,
25216 we don't have `end = i;' here. */
25217 compute_overhangs_and_x (h, tail->x + tail->width, 0);
25218 append_glyph_string_lists (&head, &tail, h, t);
25219 if (clip_tail == NULL)
25220 clip_tail = tail;
25221 }
25222
25223 /* Append glyph strings for glyphs following the last glyph
25224 string tail that overwrite tail. The foreground of such
25225 glyphs has to be drawn because it writes into the background
25226 of tail. The background must not be drawn because it could
25227 paint over the foreground of following glyphs. */
25228 i = right_overwriting (tail);
25229 if (i >= 0)
25230 {
25231 enum draw_glyphs_face overlap_hl;
25232 if (check_mouse_face
25233 && mouse_beg_col < i && mouse_end_col > end)
25234 overlap_hl = DRAW_MOUSE_FACE;
25235 else
25236 overlap_hl = DRAW_NORMAL_TEXT;
25237
25238 if (hl == overlap_hl || clip_tail == NULL)
25239 clip_tail = tail;
25240 i++; /* We must include the Ith glyph. */
25241 BUILD_GLYPH_STRINGS (end, i, h, t,
25242 overlap_hl, x, last_x);
25243 for (s = h; s; s = s->next)
25244 s->background_filled_p = 1;
25245 compute_overhangs_and_x (h, tail->x + tail->width, 0);
25246 append_glyph_string_lists (&head, &tail, h, t);
25247 }
25248 if (clip_head || clip_tail)
25249 for (s = head; s; s = s->next)
25250 {
25251 s->clip_head = clip_head;
25252 s->clip_tail = clip_tail;
25253 }
25254 }
25255
25256 /* Draw all strings. */
25257 for (s = head; s; s = s->next)
25258 FRAME_RIF (f)->draw_glyph_string (s);
25259
25260 #ifndef HAVE_NS
25261 /* When focus a sole frame and move horizontally, this sets on_p to 0
25262 causing a failure to erase prev cursor position. */
25263 if (area == TEXT_AREA
25264 && !row->full_width_p
25265 /* When drawing overlapping rows, only the glyph strings'
25266 foreground is drawn, which doesn't erase a cursor
25267 completely. */
25268 && !overlaps)
25269 {
25270 int x0 = clip_head ? clip_head->x : (head ? head->x : x);
25271 int x1 = (clip_tail ? clip_tail->x + clip_tail->background_width
25272 : (tail ? tail->x + tail->background_width : x));
25273 x0 -= area_left;
25274 x1 -= area_left;
25275
25276 notice_overwritten_cursor (w, TEXT_AREA, x0, x1,
25277 row->y, MATRIX_ROW_BOTTOM_Y (row));
25278 }
25279 #endif
25280
25281 /* Value is the x-position up to which drawn, relative to AREA of W.
25282 This doesn't include parts drawn because of overhangs. */
25283 if (row->full_width_p)
25284 x_reached = FRAME_TO_WINDOW_PIXEL_X (w, x_reached);
25285 else
25286 x_reached -= area_left;
25287
25288 RELEASE_HDC (hdc, f);
25289
25290 SAFE_FREE ();
25291 return x_reached;
25292 }
25293
25294 /* Expand row matrix if too narrow. Don't expand if area
25295 is not present. */
25296
25297 #define IT_EXPAND_MATRIX_WIDTH(it, area) \
25298 { \
25299 if (!it->f->fonts_changed \
25300 && (it->glyph_row->glyphs[area] \
25301 < it->glyph_row->glyphs[area + 1])) \
25302 { \
25303 it->w->ncols_scale_factor++; \
25304 it->f->fonts_changed = 1; \
25305 } \
25306 }
25307
25308 /* Store one glyph for IT->char_to_display in IT->glyph_row.
25309 Called from x_produce_glyphs when IT->glyph_row is non-null. */
25310
25311 static void
25312 append_glyph (struct it *it)
25313 {
25314 struct glyph *glyph;
25315 enum glyph_row_area area = it->area;
25316
25317 eassert (it->glyph_row);
25318 eassert (it->char_to_display != '\n' && it->char_to_display != '\t');
25319
25320 glyph = it->glyph_row->glyphs[area] + it->glyph_row->used[area];
25321 if (glyph < it->glyph_row->glyphs[area + 1])
25322 {
25323 /* If the glyph row is reversed, we need to prepend the glyph
25324 rather than append it. */
25325 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25326 {
25327 struct glyph *g;
25328
25329 /* Make room for the additional glyph. */
25330 for (g = glyph - 1; g >= it->glyph_row->glyphs[area]; g--)
25331 g[1] = *g;
25332 glyph = it->glyph_row->glyphs[area];
25333 }
25334 glyph->charpos = CHARPOS (it->position);
25335 glyph->object = it->object;
25336 if (it->pixel_width > 0)
25337 {
25338 glyph->pixel_width = it->pixel_width;
25339 glyph->padding_p = 0;
25340 }
25341 else
25342 {
25343 /* Assure at least 1-pixel width. Otherwise, cursor can't
25344 be displayed correctly. */
25345 glyph->pixel_width = 1;
25346 glyph->padding_p = 1;
25347 }
25348 glyph->ascent = it->ascent;
25349 glyph->descent = it->descent;
25350 glyph->voffset = it->voffset;
25351 glyph->type = CHAR_GLYPH;
25352 glyph->avoid_cursor_p = it->avoid_cursor_p;
25353 glyph->multibyte_p = it->multibyte_p;
25354 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25355 {
25356 /* In R2L rows, the left and the right box edges need to be
25357 drawn in reverse direction. */
25358 glyph->right_box_line_p = it->start_of_box_run_p;
25359 glyph->left_box_line_p = it->end_of_box_run_p;
25360 }
25361 else
25362 {
25363 glyph->left_box_line_p = it->start_of_box_run_p;
25364 glyph->right_box_line_p = it->end_of_box_run_p;
25365 }
25366 glyph->overlaps_vertically_p = (it->phys_ascent > it->ascent
25367 || it->phys_descent > it->descent);
25368 glyph->glyph_not_available_p = it->glyph_not_available_p;
25369 glyph->face_id = it->face_id;
25370 glyph->u.ch = it->char_to_display;
25371 glyph->slice.img = null_glyph_slice;
25372 glyph->font_type = FONT_TYPE_UNKNOWN;
25373 if (it->bidi_p)
25374 {
25375 glyph->resolved_level = it->bidi_it.resolved_level;
25376 eassert ((it->bidi_it.type & 7) == it->bidi_it.type);
25377 glyph->bidi_type = it->bidi_it.type;
25378 }
25379 else
25380 {
25381 glyph->resolved_level = 0;
25382 glyph->bidi_type = UNKNOWN_BT;
25383 }
25384 ++it->glyph_row->used[area];
25385 }
25386 else
25387 IT_EXPAND_MATRIX_WIDTH (it, area);
25388 }
25389
25390 /* Store one glyph for the composition IT->cmp_it.id in
25391 IT->glyph_row. Called from x_produce_glyphs when IT->glyph_row is
25392 non-null. */
25393
25394 static void
25395 append_composite_glyph (struct it *it)
25396 {
25397 struct glyph *glyph;
25398 enum glyph_row_area area = it->area;
25399
25400 eassert (it->glyph_row);
25401
25402 glyph = it->glyph_row->glyphs[area] + it->glyph_row->used[area];
25403 if (glyph < it->glyph_row->glyphs[area + 1])
25404 {
25405 /* If the glyph row is reversed, we need to prepend the glyph
25406 rather than append it. */
25407 if (it->glyph_row->reversed_p && it->area == TEXT_AREA)
25408 {
25409 struct glyph *g;
25410
25411 /* Make room for the new glyph. */
25412 for (g = glyph - 1; g >= it->glyph_row->glyphs[it->area]; g--)
25413 g[1] = *g;
25414 glyph = it->glyph_row->glyphs[it->area];
25415 }
25416 glyph->charpos = it->cmp_it.charpos;
25417 glyph->object = it->object;
25418 glyph->pixel_width = it->pixel_width;
25419 glyph->ascent = it->ascent;
25420 glyph->descent = it->descent;
25421 glyph->voffset = it->voffset;
25422 glyph->type = COMPOSITE_GLYPH;
25423 if (it->cmp_it.ch < 0)
25424 {
25425 glyph->u.cmp.automatic = 0;
25426 glyph->u.cmp.id = it->cmp_it.id;
25427 glyph->slice.cmp.from = glyph->slice.cmp.to = 0;
25428 }
25429 else
25430 {
25431 glyph->u.cmp.automatic = 1;
25432 glyph->u.cmp.id = it->cmp_it.id;
25433 glyph->slice.cmp.from = it->cmp_it.from;
25434 glyph->slice.cmp.to = it->cmp_it.to - 1;
25435 }
25436 glyph->avoid_cursor_p = it->avoid_cursor_p;
25437 glyph->multibyte_p = it->multibyte_p;
25438 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25439 {
25440 /* In R2L rows, the left and the right box edges need to be
25441 drawn in reverse direction. */
25442 glyph->right_box_line_p = it->start_of_box_run_p;
25443 glyph->left_box_line_p = it->end_of_box_run_p;
25444 }
25445 else
25446 {
25447 glyph->left_box_line_p = it->start_of_box_run_p;
25448 glyph->right_box_line_p = it->end_of_box_run_p;
25449 }
25450 glyph->overlaps_vertically_p = (it->phys_ascent > it->ascent
25451 || it->phys_descent > it->descent);
25452 glyph->padding_p = 0;
25453 glyph->glyph_not_available_p = 0;
25454 glyph->face_id = it->face_id;
25455 glyph->font_type = FONT_TYPE_UNKNOWN;
25456 if (it->bidi_p)
25457 {
25458 glyph->resolved_level = it->bidi_it.resolved_level;
25459 eassert ((it->bidi_it.type & 7) == it->bidi_it.type);
25460 glyph->bidi_type = it->bidi_it.type;
25461 }
25462 ++it->glyph_row->used[area];
25463 }
25464 else
25465 IT_EXPAND_MATRIX_WIDTH (it, area);
25466 }
25467
25468
25469 /* Change IT->ascent and IT->height according to the setting of
25470 IT->voffset. */
25471
25472 static void
25473 take_vertical_position_into_account (struct it *it)
25474 {
25475 if (it->voffset)
25476 {
25477 if (it->voffset < 0)
25478 /* Increase the ascent so that we can display the text higher
25479 in the line. */
25480 it->ascent -= it->voffset;
25481 else
25482 /* Increase the descent so that we can display the text lower
25483 in the line. */
25484 it->descent += it->voffset;
25485 }
25486 }
25487
25488
25489 /* Produce glyphs/get display metrics for the image IT is loaded with.
25490 See the description of struct display_iterator in dispextern.h for
25491 an overview of struct display_iterator. */
25492
25493 static void
25494 produce_image_glyph (struct it *it)
25495 {
25496 struct image *img;
25497 struct face *face;
25498 int glyph_ascent, crop;
25499 struct glyph_slice slice;
25500
25501 eassert (it->what == IT_IMAGE);
25502
25503 face = FACE_FROM_ID (it->f, it->face_id);
25504 eassert (face);
25505 /* Make sure X resources of the face is loaded. */
25506 prepare_face_for_display (it->f, face);
25507
25508 if (it->image_id < 0)
25509 {
25510 /* Fringe bitmap. */
25511 it->ascent = it->phys_ascent = 0;
25512 it->descent = it->phys_descent = 0;
25513 it->pixel_width = 0;
25514 it->nglyphs = 0;
25515 return;
25516 }
25517
25518 img = IMAGE_FROM_ID (it->f, it->image_id);
25519 eassert (img);
25520 /* Make sure X resources of the image is loaded. */
25521 prepare_image_for_display (it->f, img);
25522
25523 slice.x = slice.y = 0;
25524 slice.width = img->width;
25525 slice.height = img->height;
25526
25527 if (INTEGERP (it->slice.x))
25528 slice.x = XINT (it->slice.x);
25529 else if (FLOATP (it->slice.x))
25530 slice.x = XFLOAT_DATA (it->slice.x) * img->width;
25531
25532 if (INTEGERP (it->slice.y))
25533 slice.y = XINT (it->slice.y);
25534 else if (FLOATP (it->slice.y))
25535 slice.y = XFLOAT_DATA (it->slice.y) * img->height;
25536
25537 if (INTEGERP (it->slice.width))
25538 slice.width = XINT (it->slice.width);
25539 else if (FLOATP (it->slice.width))
25540 slice.width = XFLOAT_DATA (it->slice.width) * img->width;
25541
25542 if (INTEGERP (it->slice.height))
25543 slice.height = XINT (it->slice.height);
25544 else if (FLOATP (it->slice.height))
25545 slice.height = XFLOAT_DATA (it->slice.height) * img->height;
25546
25547 if (slice.x >= img->width)
25548 slice.x = img->width;
25549 if (slice.y >= img->height)
25550 slice.y = img->height;
25551 if (slice.x + slice.width >= img->width)
25552 slice.width = img->width - slice.x;
25553 if (slice.y + slice.height > img->height)
25554 slice.height = img->height - slice.y;
25555
25556 if (slice.width == 0 || slice.height == 0)
25557 return;
25558
25559 it->ascent = it->phys_ascent = glyph_ascent = image_ascent (img, face, &slice);
25560
25561 it->descent = slice.height - glyph_ascent;
25562 if (slice.y == 0)
25563 it->descent += img->vmargin;
25564 if (slice.y + slice.height == img->height)
25565 it->descent += img->vmargin;
25566 it->phys_descent = it->descent;
25567
25568 it->pixel_width = slice.width;
25569 if (slice.x == 0)
25570 it->pixel_width += img->hmargin;
25571 if (slice.x + slice.width == img->width)
25572 it->pixel_width += img->hmargin;
25573
25574 /* It's quite possible for images to have an ascent greater than
25575 their height, so don't get confused in that case. */
25576 if (it->descent < 0)
25577 it->descent = 0;
25578
25579 it->nglyphs = 1;
25580
25581 if (face->box != FACE_NO_BOX)
25582 {
25583 if (face->box_line_width > 0)
25584 {
25585 if (slice.y == 0)
25586 it->ascent += face->box_line_width;
25587 if (slice.y + slice.height == img->height)
25588 it->descent += face->box_line_width;
25589 }
25590
25591 if (it->start_of_box_run_p && slice.x == 0)
25592 it->pixel_width += eabs (face->box_line_width);
25593 if (it->end_of_box_run_p && slice.x + slice.width == img->width)
25594 it->pixel_width += eabs (face->box_line_width);
25595 }
25596
25597 take_vertical_position_into_account (it);
25598
25599 /* Automatically crop wide image glyphs at right edge so we can
25600 draw the cursor on same display row. */
25601 if ((crop = it->pixel_width - (it->last_visible_x - it->current_x), crop > 0)
25602 && (it->hpos == 0 || it->pixel_width > it->last_visible_x / 4))
25603 {
25604 it->pixel_width -= crop;
25605 slice.width -= crop;
25606 }
25607
25608 if (it->glyph_row)
25609 {
25610 struct glyph *glyph;
25611 enum glyph_row_area area = it->area;
25612
25613 glyph = it->glyph_row->glyphs[area] + it->glyph_row->used[area];
25614 if (glyph < it->glyph_row->glyphs[area + 1])
25615 {
25616 glyph->charpos = CHARPOS (it->position);
25617 glyph->object = it->object;
25618 glyph->pixel_width = it->pixel_width;
25619 glyph->ascent = glyph_ascent;
25620 glyph->descent = it->descent;
25621 glyph->voffset = it->voffset;
25622 glyph->type = IMAGE_GLYPH;
25623 glyph->avoid_cursor_p = it->avoid_cursor_p;
25624 glyph->multibyte_p = it->multibyte_p;
25625 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25626 {
25627 /* In R2L rows, the left and the right box edges need to be
25628 drawn in reverse direction. */
25629 glyph->right_box_line_p = it->start_of_box_run_p;
25630 glyph->left_box_line_p = it->end_of_box_run_p;
25631 }
25632 else
25633 {
25634 glyph->left_box_line_p = it->start_of_box_run_p;
25635 glyph->right_box_line_p = it->end_of_box_run_p;
25636 }
25637 glyph->overlaps_vertically_p = 0;
25638 glyph->padding_p = 0;
25639 glyph->glyph_not_available_p = 0;
25640 glyph->face_id = it->face_id;
25641 glyph->u.img_id = img->id;
25642 glyph->slice.img = slice;
25643 glyph->font_type = FONT_TYPE_UNKNOWN;
25644 if (it->bidi_p)
25645 {
25646 glyph->resolved_level = it->bidi_it.resolved_level;
25647 eassert ((it->bidi_it.type & 7) == it->bidi_it.type);
25648 glyph->bidi_type = it->bidi_it.type;
25649 }
25650 ++it->glyph_row->used[area];
25651 }
25652 else
25653 IT_EXPAND_MATRIX_WIDTH (it, area);
25654 }
25655 }
25656
25657
25658 /* Append a stretch glyph to IT->glyph_row. OBJECT is the source
25659 of the glyph, WIDTH and HEIGHT are the width and height of the
25660 stretch. ASCENT is the ascent of the glyph (0 <= ASCENT <= HEIGHT). */
25661
25662 static void
25663 append_stretch_glyph (struct it *it, Lisp_Object object,
25664 int width, int height, int ascent)
25665 {
25666 struct glyph *glyph;
25667 enum glyph_row_area area = it->area;
25668
25669 eassert (ascent >= 0 && ascent <= height);
25670
25671 glyph = it->glyph_row->glyphs[area] + it->glyph_row->used[area];
25672 if (glyph < it->glyph_row->glyphs[area + 1])
25673 {
25674 /* If the glyph row is reversed, we need to prepend the glyph
25675 rather than append it. */
25676 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25677 {
25678 struct glyph *g;
25679
25680 /* Make room for the additional glyph. */
25681 for (g = glyph - 1; g >= it->glyph_row->glyphs[area]; g--)
25682 g[1] = *g;
25683 glyph = it->glyph_row->glyphs[area];
25684
25685 /* Decrease the width of the first glyph of the row that
25686 begins before first_visible_x (e.g., due to hscroll).
25687 This is so the overall width of the row becomes smaller
25688 by the scroll amount, and the stretch glyph appended by
25689 extend_face_to_end_of_line will be wider, to shift the
25690 row glyphs to the right. (In L2R rows, the corresponding
25691 left-shift effect is accomplished by setting row->x to a
25692 negative value, which won't work with R2L rows.)
25693
25694 This must leave us with a positive value of WIDTH, since
25695 otherwise the call to move_it_in_display_line_to at the
25696 beginning of display_line would have got past the entire
25697 first glyph, and then it->current_x would have been
25698 greater or equal to it->first_visible_x. */
25699 if (it->current_x < it->first_visible_x)
25700 width -= it->first_visible_x - it->current_x;
25701 eassert (width > 0);
25702 }
25703 glyph->charpos = CHARPOS (it->position);
25704 glyph->object = object;
25705 glyph->pixel_width = width;
25706 glyph->ascent = ascent;
25707 glyph->descent = height - ascent;
25708 glyph->voffset = it->voffset;
25709 glyph->type = STRETCH_GLYPH;
25710 glyph->avoid_cursor_p = it->avoid_cursor_p;
25711 glyph->multibyte_p = it->multibyte_p;
25712 if (it->glyph_row->reversed_p && area == TEXT_AREA)
25713 {
25714 /* In R2L rows, the left and the right box edges need to be
25715 drawn in reverse direction. */
25716 glyph->right_box_line_p = it->start_of_box_run_p;
25717 glyph->left_box_line_p = it->end_of_box_run_p;
25718 }
25719 else
25720 {
25721 glyph->left_box_line_p = it->start_of_box_run_p;
25722 glyph->right_box_line_p = it->end_of_box_run_p;
25723 }
25724 glyph->overlaps_vertically_p = 0;
25725 glyph->padding_p = 0;
25726 glyph->glyph_not_available_p = 0;
25727 glyph->face_id = it->face_id;
25728 glyph->u.stretch.ascent = ascent;
25729 glyph->u.stretch.height = height;
25730 glyph->slice.img = null_glyph_slice;
25731 glyph->font_type = FONT_TYPE_UNKNOWN;
25732 if (it->bidi_p)
25733 {
25734 glyph->resolved_level = it->bidi_it.resolved_level;
25735 eassert ((it->bidi_it.type & 7) == it->bidi_it.type);
25736 glyph->bidi_type = it->bidi_it.type;
25737 }
25738 else
25739 {
25740 glyph->resolved_level = 0;
25741 glyph->bidi_type = UNKNOWN_BT;
25742 }
25743 ++it->glyph_row->used[area];
25744 }
25745 else
25746 IT_EXPAND_MATRIX_WIDTH (it, area);
25747 }
25748
25749 #endif /* HAVE_WINDOW_SYSTEM */
25750
25751 /* Produce a stretch glyph for iterator IT. IT->object is the value
25752 of the glyph property displayed. The value must be a list
25753 `(space KEYWORD VALUE ...)' with the following KEYWORD/VALUE pairs
25754 being recognized:
25755
25756 1. `:width WIDTH' specifies that the space should be WIDTH *
25757 canonical char width wide. WIDTH may be an integer or floating
25758 point number.
25759
25760 2. `:relative-width FACTOR' specifies that the width of the stretch
25761 should be computed from the width of the first character having the
25762 `glyph' property, and should be FACTOR times that width.
25763
25764 3. `:align-to HPOS' specifies that the space should be wide enough
25765 to reach HPOS, a value in canonical character units.
25766
25767 Exactly one of the above pairs must be present.
25768
25769 4. `:height HEIGHT' specifies that the height of the stretch produced
25770 should be HEIGHT, measured in canonical character units.
25771
25772 5. `:relative-height FACTOR' specifies that the height of the
25773 stretch should be FACTOR times the height of the characters having
25774 the glyph property.
25775
25776 Either none or exactly one of 4 or 5 must be present.
25777
25778 6. `:ascent ASCENT' specifies that ASCENT percent of the height
25779 of the stretch should be used for the ascent of the stretch.
25780 ASCENT must be in the range 0 <= ASCENT <= 100. */
25781
25782 void
25783 produce_stretch_glyph (struct it *it)
25784 {
25785 /* (space :width WIDTH :height HEIGHT ...) */
25786 Lisp_Object prop, plist;
25787 int width = 0, height = 0, align_to = -1;
25788 int zero_width_ok_p = 0;
25789 double tem;
25790 struct font *font = NULL;
25791
25792 #ifdef HAVE_WINDOW_SYSTEM
25793 int ascent = 0;
25794 int zero_height_ok_p = 0;
25795
25796 if (FRAME_WINDOW_P (it->f))
25797 {
25798 struct face *face = FACE_FROM_ID (it->f, it->face_id);
25799 font = face->font ? face->font : FRAME_FONT (it->f);
25800 prepare_face_for_display (it->f, face);
25801 }
25802 #endif
25803
25804 /* List should start with `space'. */
25805 eassert (CONSP (it->object) && EQ (XCAR (it->object), Qspace));
25806 plist = XCDR (it->object);
25807
25808 /* Compute the width of the stretch. */
25809 if ((prop = Fplist_get (plist, QCwidth), !NILP (prop))
25810 && calc_pixel_width_or_height (&tem, it, prop, font, 1, 0))
25811 {
25812 /* Absolute width `:width WIDTH' specified and valid. */
25813 zero_width_ok_p = 1;
25814 width = (int)tem;
25815 }
25816 #ifdef HAVE_WINDOW_SYSTEM
25817 else if (FRAME_WINDOW_P (it->f)
25818 && (prop = Fplist_get (plist, QCrelative_width), NUMVAL (prop) > 0))
25819 {
25820 /* Relative width `:relative-width FACTOR' specified and valid.
25821 Compute the width of the characters having the `glyph'
25822 property. */
25823 struct it it2;
25824 unsigned char *p = BYTE_POS_ADDR (IT_BYTEPOS (*it));
25825
25826 it2 = *it;
25827 if (it->multibyte_p)
25828 it2.c = it2.char_to_display = STRING_CHAR_AND_LENGTH (p, it2.len);
25829 else
25830 {
25831 it2.c = it2.char_to_display = *p, it2.len = 1;
25832 if (! ASCII_CHAR_P (it2.c))
25833 it2.char_to_display = BYTE8_TO_CHAR (it2.c);
25834 }
25835
25836 it2.glyph_row = NULL;
25837 it2.what = IT_CHARACTER;
25838 x_produce_glyphs (&it2);
25839 width = NUMVAL (prop) * it2.pixel_width;
25840 }
25841 #endif /* HAVE_WINDOW_SYSTEM */
25842 else if ((prop = Fplist_get (plist, QCalign_to), !NILP (prop))
25843 && calc_pixel_width_or_height (&tem, it, prop, font, 1, &align_to))
25844 {
25845 if (it->glyph_row == NULL || !it->glyph_row->mode_line_p)
25846 align_to = (align_to < 0
25847 ? 0
25848 : align_to - window_box_left_offset (it->w, TEXT_AREA));
25849 else if (align_to < 0)
25850 align_to = window_box_left_offset (it->w, TEXT_AREA);
25851 width = max (0, (int)tem + align_to - it->current_x);
25852 zero_width_ok_p = 1;
25853 }
25854 else
25855 /* Nothing specified -> width defaults to canonical char width. */
25856 width = FRAME_COLUMN_WIDTH (it->f);
25857
25858 if (width <= 0 && (width < 0 || !zero_width_ok_p))
25859 width = 1;
25860
25861 #ifdef HAVE_WINDOW_SYSTEM
25862 /* Compute height. */
25863 if (FRAME_WINDOW_P (it->f))
25864 {
25865 if ((prop = Fplist_get (plist, QCheight), !NILP (prop))
25866 && calc_pixel_width_or_height (&tem, it, prop, font, 0, 0))
25867 {
25868 height = (int)tem;
25869 zero_height_ok_p = 1;
25870 }
25871 else if (prop = Fplist_get (plist, QCrelative_height),
25872 NUMVAL (prop) > 0)
25873 height = FONT_HEIGHT (font) * NUMVAL (prop);
25874 else
25875 height = FONT_HEIGHT (font);
25876
25877 if (height <= 0 && (height < 0 || !zero_height_ok_p))
25878 height = 1;
25879
25880 /* Compute percentage of height used for ascent. If
25881 `:ascent ASCENT' is present and valid, use that. Otherwise,
25882 derive the ascent from the font in use. */
25883 if (prop = Fplist_get (plist, QCascent),
25884 NUMVAL (prop) > 0 && NUMVAL (prop) <= 100)
25885 ascent = height * NUMVAL (prop) / 100.0;
25886 else if (!NILP (prop)
25887 && calc_pixel_width_or_height (&tem, it, prop, font, 0, 0))
25888 ascent = min (max (0, (int)tem), height);
25889 else
25890 ascent = (height * FONT_BASE (font)) / FONT_HEIGHT (font);
25891 }
25892 else
25893 #endif /* HAVE_WINDOW_SYSTEM */
25894 height = 1;
25895
25896 if (width > 0 && it->line_wrap != TRUNCATE
25897 && it->current_x + width > it->last_visible_x)
25898 {
25899 width = it->last_visible_x - it->current_x;
25900 #ifdef HAVE_WINDOW_SYSTEM
25901 /* Subtract one more pixel from the stretch width, but only on
25902 GUI frames, since on a TTY each glyph is one "pixel" wide. */
25903 width -= FRAME_WINDOW_P (it->f);
25904 #endif
25905 }
25906
25907 if (width > 0 && height > 0 && it->glyph_row)
25908 {
25909 Lisp_Object o_object = it->object;
25910 Lisp_Object object = it->stack[it->sp - 1].string;
25911 int n = width;
25912
25913 if (!STRINGP (object))
25914 object = it->w->contents;
25915 #ifdef HAVE_WINDOW_SYSTEM
25916 if (FRAME_WINDOW_P (it->f))
25917 append_stretch_glyph (it, object, width, height, ascent);
25918 else
25919 #endif
25920 {
25921 it->object = object;
25922 it->char_to_display = ' ';
25923 it->pixel_width = it->len = 1;
25924 while (n--)
25925 tty_append_glyph (it);
25926 it->object = o_object;
25927 }
25928 }
25929
25930 it->pixel_width = width;
25931 #ifdef HAVE_WINDOW_SYSTEM
25932 if (FRAME_WINDOW_P (it->f))
25933 {
25934 it->ascent = it->phys_ascent = ascent;
25935 it->descent = it->phys_descent = height - it->ascent;
25936 it->nglyphs = width > 0 && height > 0 ? 1 : 0;
25937 take_vertical_position_into_account (it);
25938 }
25939 else
25940 #endif
25941 it->nglyphs = width;
25942 }
25943
25944 /* Get information about special display element WHAT in an
25945 environment described by IT. WHAT is one of IT_TRUNCATION or
25946 IT_CONTINUATION. Maybe produce glyphs for WHAT if IT has a
25947 non-null glyph_row member. This function ensures that fields like
25948 face_id, c, len of IT are left untouched. */
25949
25950 static void
25951 produce_special_glyphs (struct it *it, enum display_element_type what)
25952 {
25953 struct it temp_it;
25954 Lisp_Object gc;
25955 GLYPH glyph;
25956
25957 temp_it = *it;
25958 temp_it.object = Qnil;
25959 memset (&temp_it.current, 0, sizeof temp_it.current);
25960
25961 if (what == IT_CONTINUATION)
25962 {
25963 /* Continuation glyph. For R2L lines, we mirror it by hand. */
25964 if (it->bidi_it.paragraph_dir == R2L)
25965 SET_GLYPH_FROM_CHAR (glyph, '/');
25966 else
25967 SET_GLYPH_FROM_CHAR (glyph, '\\');
25968 if (it->dp
25969 && (gc = DISP_CONTINUE_GLYPH (it->dp), GLYPH_CODE_P (gc)))
25970 {
25971 /* FIXME: Should we mirror GC for R2L lines? */
25972 SET_GLYPH_FROM_GLYPH_CODE (glyph, gc);
25973 spec_glyph_lookup_face (XWINDOW (it->window), &glyph);
25974 }
25975 }
25976 else if (what == IT_TRUNCATION)
25977 {
25978 /* Truncation glyph. */
25979 SET_GLYPH_FROM_CHAR (glyph, '$');
25980 if (it->dp
25981 && (gc = DISP_TRUNC_GLYPH (it->dp), GLYPH_CODE_P (gc)))
25982 {
25983 /* FIXME: Should we mirror GC for R2L lines? */
25984 SET_GLYPH_FROM_GLYPH_CODE (glyph, gc);
25985 spec_glyph_lookup_face (XWINDOW (it->window), &glyph);
25986 }
25987 }
25988 else
25989 emacs_abort ();
25990
25991 #ifdef HAVE_WINDOW_SYSTEM
25992 /* On a GUI frame, when the right fringe (left fringe for R2L rows)
25993 is turned off, we precede the truncation/continuation glyphs by a
25994 stretch glyph whose width is computed such that these special
25995 glyphs are aligned at the window margin, even when very different
25996 fonts are used in different glyph rows. */
25997 if (FRAME_WINDOW_P (temp_it.f)
25998 /* init_iterator calls this with it->glyph_row == NULL, and it
25999 wants only the pixel width of the truncation/continuation
26000 glyphs. */
26001 && temp_it.glyph_row
26002 /* insert_left_trunc_glyphs calls us at the beginning of the
26003 row, and it has its own calculation of the stretch glyph
26004 width. */
26005 && temp_it.glyph_row->used[TEXT_AREA] > 0
26006 && (temp_it.glyph_row->reversed_p
26007 ? WINDOW_LEFT_FRINGE_WIDTH (temp_it.w)
26008 : WINDOW_RIGHT_FRINGE_WIDTH (temp_it.w)) == 0)
26009 {
26010 int stretch_width = temp_it.last_visible_x - temp_it.current_x;
26011
26012 if (stretch_width > 0)
26013 {
26014 struct face *face = FACE_FROM_ID (temp_it.f, temp_it.face_id);
26015 struct font *font =
26016 face->font ? face->font : FRAME_FONT (temp_it.f);
26017 int stretch_ascent =
26018 (((temp_it.ascent + temp_it.descent)
26019 * FONT_BASE (font)) / FONT_HEIGHT (font));
26020
26021 append_stretch_glyph (&temp_it, Qnil, stretch_width,
26022 temp_it.ascent + temp_it.descent,
26023 stretch_ascent);
26024 }
26025 }
26026 #endif
26027
26028 temp_it.dp = NULL;
26029 temp_it.what = IT_CHARACTER;
26030 temp_it.c = temp_it.char_to_display = GLYPH_CHAR (glyph);
26031 temp_it.face_id = GLYPH_FACE (glyph);
26032 temp_it.len = CHAR_BYTES (temp_it.c);
26033
26034 PRODUCE_GLYPHS (&temp_it);
26035 it->pixel_width = temp_it.pixel_width;
26036 it->nglyphs = temp_it.nglyphs;
26037 }
26038
26039 #ifdef HAVE_WINDOW_SYSTEM
26040
26041 /* Calculate line-height and line-spacing properties.
26042 An integer value specifies explicit pixel value.
26043 A float value specifies relative value to current face height.
26044 A cons (float . face-name) specifies relative value to
26045 height of specified face font.
26046
26047 Returns height in pixels, or nil. */
26048
26049
26050 static Lisp_Object
26051 calc_line_height_property (struct it *it, Lisp_Object val, struct font *font,
26052 int boff, int override)
26053 {
26054 Lisp_Object face_name = Qnil;
26055 int ascent, descent, height;
26056
26057 if (NILP (val) || INTEGERP (val) || (override && EQ (val, Qt)))
26058 return val;
26059
26060 if (CONSP (val))
26061 {
26062 face_name = XCAR (val);
26063 val = XCDR (val);
26064 if (!NUMBERP (val))
26065 val = make_number (1);
26066 if (NILP (face_name))
26067 {
26068 height = it->ascent + it->descent;
26069 goto scale;
26070 }
26071 }
26072
26073 if (NILP (face_name))
26074 {
26075 font = FRAME_FONT (it->f);
26076 boff = FRAME_BASELINE_OFFSET (it->f);
26077 }
26078 else if (EQ (face_name, Qt))
26079 {
26080 override = 0;
26081 }
26082 else
26083 {
26084 int face_id;
26085 struct face *face;
26086
26087 face_id = lookup_named_face (it->f, face_name, false);
26088 if (face_id < 0)
26089 return make_number (-1);
26090
26091 face = FACE_FROM_ID (it->f, face_id);
26092 font = face->font;
26093 if (font == NULL)
26094 return make_number (-1);
26095 boff = font->baseline_offset;
26096 if (font->vertical_centering)
26097 boff = VCENTER_BASELINE_OFFSET (font, it->f) - boff;
26098 }
26099
26100 ascent = FONT_BASE (font) + boff;
26101 descent = FONT_DESCENT (font) - boff;
26102
26103 if (override)
26104 {
26105 it->override_ascent = ascent;
26106 it->override_descent = descent;
26107 it->override_boff = boff;
26108 }
26109
26110 height = ascent + descent;
26111
26112 scale:
26113 if (FLOATP (val))
26114 height = (int)(XFLOAT_DATA (val) * height);
26115 else if (INTEGERP (val))
26116 height *= XINT (val);
26117
26118 return make_number (height);
26119 }
26120
26121
26122 /* Append a glyph for a glyphless character to IT->glyph_row. FACE_ID
26123 is a face ID to be used for the glyph. FOR_NO_FONT is nonzero if
26124 and only if this is for a character for which no font was found.
26125
26126 If the display method (it->glyphless_method) is
26127 GLYPHLESS_DISPLAY_ACRONYM or GLYPHLESS_DISPLAY_HEX_CODE, LEN is a
26128 length of the acronym or the hexadecimal string, UPPER_XOFF and
26129 UPPER_YOFF are pixel offsets for the upper part of the string,
26130 LOWER_XOFF and LOWER_YOFF are for the lower part.
26131
26132 For the other display methods, LEN through LOWER_YOFF are zero. */
26133
26134 static void
26135 append_glyphless_glyph (struct it *it, int face_id, int for_no_font, int len,
26136 short upper_xoff, short upper_yoff,
26137 short lower_xoff, short lower_yoff)
26138 {
26139 struct glyph *glyph;
26140 enum glyph_row_area area = it->area;
26141
26142 glyph = it->glyph_row->glyphs[area] + it->glyph_row->used[area];
26143 if (glyph < it->glyph_row->glyphs[area + 1])
26144 {
26145 /* If the glyph row is reversed, we need to prepend the glyph
26146 rather than append it. */
26147 if (it->glyph_row->reversed_p && area == TEXT_AREA)
26148 {
26149 struct glyph *g;
26150
26151 /* Make room for the additional glyph. */
26152 for (g = glyph - 1; g >= it->glyph_row->glyphs[area]; g--)
26153 g[1] = *g;
26154 glyph = it->glyph_row->glyphs[area];
26155 }
26156 glyph->charpos = CHARPOS (it->position);
26157 glyph->object = it->object;
26158 glyph->pixel_width = it->pixel_width;
26159 glyph->ascent = it->ascent;
26160 glyph->descent = it->descent;
26161 glyph->voffset = it->voffset;
26162 glyph->type = GLYPHLESS_GLYPH;
26163 glyph->u.glyphless.method = it->glyphless_method;
26164 glyph->u.glyphless.for_no_font = for_no_font;
26165 glyph->u.glyphless.len = len;
26166 glyph->u.glyphless.ch = it->c;
26167 glyph->slice.glyphless.upper_xoff = upper_xoff;
26168 glyph->slice.glyphless.upper_yoff = upper_yoff;
26169 glyph->slice.glyphless.lower_xoff = lower_xoff;
26170 glyph->slice.glyphless.lower_yoff = lower_yoff;
26171 glyph->avoid_cursor_p = it->avoid_cursor_p;
26172 glyph->multibyte_p = it->multibyte_p;
26173 if (it->glyph_row->reversed_p && area == TEXT_AREA)
26174 {
26175 /* In R2L rows, the left and the right box edges need to be
26176 drawn in reverse direction. */
26177 glyph->right_box_line_p = it->start_of_box_run_p;
26178 glyph->left_box_line_p = it->end_of_box_run_p;
26179 }
26180 else
26181 {
26182 glyph->left_box_line_p = it->start_of_box_run_p;
26183 glyph->right_box_line_p = it->end_of_box_run_p;
26184 }
26185 glyph->overlaps_vertically_p = (it->phys_ascent > it->ascent
26186 || it->phys_descent > it->descent);
26187 glyph->padding_p = 0;
26188 glyph->glyph_not_available_p = 0;
26189 glyph->face_id = face_id;
26190 glyph->font_type = FONT_TYPE_UNKNOWN;
26191 if (it->bidi_p)
26192 {
26193 glyph->resolved_level = it->bidi_it.resolved_level;
26194 eassert ((it->bidi_it.type & 7) == it->bidi_it.type);
26195 glyph->bidi_type = it->bidi_it.type;
26196 }
26197 ++it->glyph_row->used[area];
26198 }
26199 else
26200 IT_EXPAND_MATRIX_WIDTH (it, area);
26201 }
26202
26203
26204 /* Produce a glyph for a glyphless character for iterator IT.
26205 IT->glyphless_method specifies which method to use for displaying
26206 the character. See the description of enum
26207 glyphless_display_method in dispextern.h for the detail.
26208
26209 FOR_NO_FONT is nonzero if and only if this is for a character for
26210 which no font was found. ACRONYM, if non-nil, is an acronym string
26211 for the character. */
26212
26213 static void
26214 produce_glyphless_glyph (struct it *it, int for_no_font, Lisp_Object acronym)
26215 {
26216 int face_id;
26217 struct face *face;
26218 struct font *font;
26219 int base_width, base_height, width, height;
26220 short upper_xoff, upper_yoff, lower_xoff, lower_yoff;
26221 int len;
26222
26223 /* Get the metrics of the base font. We always refer to the current
26224 ASCII face. */
26225 face = FACE_FROM_ID (it->f, it->face_id)->ascii_face;
26226 font = face->font ? face->font : FRAME_FONT (it->f);
26227 it->ascent = FONT_BASE (font) + font->baseline_offset;
26228 it->descent = FONT_DESCENT (font) - font->baseline_offset;
26229 base_height = it->ascent + it->descent;
26230 base_width = font->average_width;
26231
26232 face_id = merge_glyphless_glyph_face (it);
26233
26234 if (it->glyphless_method == GLYPHLESS_DISPLAY_THIN_SPACE)
26235 {
26236 it->pixel_width = THIN_SPACE_WIDTH;
26237 len = 0;
26238 upper_xoff = upper_yoff = lower_xoff = lower_yoff = 0;
26239 }
26240 else if (it->glyphless_method == GLYPHLESS_DISPLAY_EMPTY_BOX)
26241 {
26242 width = CHAR_WIDTH (it->c);
26243 if (width == 0)
26244 width = 1;
26245 else if (width > 4)
26246 width = 4;
26247 it->pixel_width = base_width * width;
26248 len = 0;
26249 upper_xoff = upper_yoff = lower_xoff = lower_yoff = 0;
26250 }
26251 else
26252 {
26253 char buf[7];
26254 const char *str;
26255 unsigned int code[6];
26256 int upper_len;
26257 int ascent, descent;
26258 struct font_metrics metrics_upper, metrics_lower;
26259
26260 face = FACE_FROM_ID (it->f, face_id);
26261 font = face->font ? face->font : FRAME_FONT (it->f);
26262 prepare_face_for_display (it->f, face);
26263
26264 if (it->glyphless_method == GLYPHLESS_DISPLAY_ACRONYM)
26265 {
26266 if (! STRINGP (acronym) && CHAR_TABLE_P (Vglyphless_char_display))
26267 acronym = CHAR_TABLE_REF (Vglyphless_char_display, it->c);
26268 if (CONSP (acronym))
26269 acronym = XCAR (acronym);
26270 str = STRINGP (acronym) ? SSDATA (acronym) : "";
26271 }
26272 else
26273 {
26274 eassert (it->glyphless_method == GLYPHLESS_DISPLAY_HEX_CODE);
26275 sprintf (buf, "%0*X", it->c < 0x10000 ? 4 : 6, it->c);
26276 str = buf;
26277 }
26278 for (len = 0; str[len] && ASCII_CHAR_P (str[len]) && len < 6; len++)
26279 code[len] = font->driver->encode_char (font, str[len]);
26280 upper_len = (len + 1) / 2;
26281 font->driver->text_extents (font, code, upper_len,
26282 &metrics_upper);
26283 font->driver->text_extents (font, code + upper_len, len - upper_len,
26284 &metrics_lower);
26285
26286
26287
26288 /* +4 is for vertical bars of a box plus 1-pixel spaces at both side. */
26289 width = max (metrics_upper.width, metrics_lower.width) + 4;
26290 upper_xoff = upper_yoff = 2; /* the typical case */
26291 if (base_width >= width)
26292 {
26293 /* Align the upper to the left, the lower to the right. */
26294 it->pixel_width = base_width;
26295 lower_xoff = base_width - 2 - metrics_lower.width;
26296 }
26297 else
26298 {
26299 /* Center the shorter one. */
26300 it->pixel_width = width;
26301 if (metrics_upper.width >= metrics_lower.width)
26302 lower_xoff = (width - metrics_lower.width) / 2;
26303 else
26304 {
26305 /* FIXME: This code doesn't look right. It formerly was
26306 missing the "lower_xoff = 0;", which couldn't have
26307 been right since it left lower_xoff uninitialized. */
26308 lower_xoff = 0;
26309 upper_xoff = (width - metrics_upper.width) / 2;
26310 }
26311 }
26312
26313 /* +5 is for horizontal bars of a box plus 1-pixel spaces at
26314 top, bottom, and between upper and lower strings. */
26315 height = (metrics_upper.ascent + metrics_upper.descent
26316 + metrics_lower.ascent + metrics_lower.descent) + 5;
26317 /* Center vertically.
26318 H:base_height, D:base_descent
26319 h:height, ld:lower_descent, la:lower_ascent, ud:upper_descent
26320
26321 ascent = - (D - H/2 - h/2 + 1); "+ 1" for rounding up
26322 descent = D - H/2 + h/2;
26323 lower_yoff = descent - 2 - ld;
26324 upper_yoff = lower_yoff - la - 1 - ud; */
26325 ascent = - (it->descent - (base_height + height + 1) / 2);
26326 descent = it->descent - (base_height - height) / 2;
26327 lower_yoff = descent - 2 - metrics_lower.descent;
26328 upper_yoff = (lower_yoff - metrics_lower.ascent - 1
26329 - metrics_upper.descent);
26330 /* Don't make the height shorter than the base height. */
26331 if (height > base_height)
26332 {
26333 it->ascent = ascent;
26334 it->descent = descent;
26335 }
26336 }
26337
26338 it->phys_ascent = it->ascent;
26339 it->phys_descent = it->descent;
26340 if (it->glyph_row)
26341 append_glyphless_glyph (it, face_id, for_no_font, len,
26342 upper_xoff, upper_yoff,
26343 lower_xoff, lower_yoff);
26344 it->nglyphs = 1;
26345 take_vertical_position_into_account (it);
26346 }
26347
26348
26349 /* RIF:
26350 Produce glyphs/get display metrics for the display element IT is
26351 loaded with. See the description of struct it in dispextern.h
26352 for an overview of struct it. */
26353
26354 void
26355 x_produce_glyphs (struct it *it)
26356 {
26357 int extra_line_spacing = it->extra_line_spacing;
26358
26359 it->glyph_not_available_p = 0;
26360
26361 if (it->what == IT_CHARACTER)
26362 {
26363 XChar2b char2b;
26364 struct face *face = FACE_FROM_ID (it->f, it->face_id);
26365 struct font *font = face->font;
26366 struct font_metrics *pcm = NULL;
26367 int boff; /* Baseline offset. */
26368
26369 if (font == NULL)
26370 {
26371 /* When no suitable font is found, display this character by
26372 the method specified in the first extra slot of
26373 Vglyphless_char_display. */
26374 Lisp_Object acronym = lookup_glyphless_char_display (-1, it);
26375
26376 eassert (it->what == IT_GLYPHLESS);
26377 produce_glyphless_glyph (it, 1, STRINGP (acronym) ? acronym : Qnil);
26378 goto done;
26379 }
26380
26381 boff = font->baseline_offset;
26382 if (font->vertical_centering)
26383 boff = VCENTER_BASELINE_OFFSET (font, it->f) - boff;
26384
26385 if (it->char_to_display != '\n' && it->char_to_display != '\t')
26386 {
26387 int stretched_p;
26388
26389 it->nglyphs = 1;
26390
26391 if (it->override_ascent >= 0)
26392 {
26393 it->ascent = it->override_ascent;
26394 it->descent = it->override_descent;
26395 boff = it->override_boff;
26396 }
26397 else
26398 {
26399 it->ascent = FONT_BASE (font) + boff;
26400 it->descent = FONT_DESCENT (font) - boff;
26401 }
26402
26403 if (get_char_glyph_code (it->char_to_display, font, &char2b))
26404 {
26405 pcm = get_per_char_metric (font, &char2b);
26406 if (pcm->width == 0
26407 && pcm->rbearing == 0 && pcm->lbearing == 0)
26408 pcm = NULL;
26409 }
26410
26411 if (pcm)
26412 {
26413 it->phys_ascent = pcm->ascent + boff;
26414 it->phys_descent = pcm->descent - boff;
26415 it->pixel_width = pcm->width;
26416 }
26417 else
26418 {
26419 it->glyph_not_available_p = 1;
26420 it->phys_ascent = it->ascent;
26421 it->phys_descent = it->descent;
26422 it->pixel_width = font->space_width;
26423 }
26424
26425 if (it->constrain_row_ascent_descent_p)
26426 {
26427 if (it->descent > it->max_descent)
26428 {
26429 it->ascent += it->descent - it->max_descent;
26430 it->descent = it->max_descent;
26431 }
26432 if (it->ascent > it->max_ascent)
26433 {
26434 it->descent = min (it->max_descent, it->descent + it->ascent - it->max_ascent);
26435 it->ascent = it->max_ascent;
26436 }
26437 it->phys_ascent = min (it->phys_ascent, it->ascent);
26438 it->phys_descent = min (it->phys_descent, it->descent);
26439 extra_line_spacing = 0;
26440 }
26441
26442 /* If this is a space inside a region of text with
26443 `space-width' property, change its width. */
26444 stretched_p = it->char_to_display == ' ' && !NILP (it->space_width);
26445 if (stretched_p)
26446 it->pixel_width *= XFLOATINT (it->space_width);
26447
26448 /* If face has a box, add the box thickness to the character
26449 height. If character has a box line to the left and/or
26450 right, add the box line width to the character's width. */
26451 if (face->box != FACE_NO_BOX)
26452 {
26453 int thick = face->box_line_width;
26454
26455 if (thick > 0)
26456 {
26457 it->ascent += thick;
26458 it->descent += thick;
26459 }
26460 else
26461 thick = -thick;
26462
26463 if (it->start_of_box_run_p)
26464 it->pixel_width += thick;
26465 if (it->end_of_box_run_p)
26466 it->pixel_width += thick;
26467 }
26468
26469 /* If face has an overline, add the height of the overline
26470 (1 pixel) and a 1 pixel margin to the character height. */
26471 if (face->overline_p)
26472 it->ascent += overline_margin;
26473
26474 if (it->constrain_row_ascent_descent_p)
26475 {
26476 if (it->ascent > it->max_ascent)
26477 it->ascent = it->max_ascent;
26478 if (it->descent > it->max_descent)
26479 it->descent = it->max_descent;
26480 }
26481
26482 take_vertical_position_into_account (it);
26483
26484 /* If we have to actually produce glyphs, do it. */
26485 if (it->glyph_row)
26486 {
26487 if (stretched_p)
26488 {
26489 /* Translate a space with a `space-width' property
26490 into a stretch glyph. */
26491 int ascent = (((it->ascent + it->descent) * FONT_BASE (font))
26492 / FONT_HEIGHT (font));
26493 append_stretch_glyph (it, it->object, it->pixel_width,
26494 it->ascent + it->descent, ascent);
26495 }
26496 else
26497 append_glyph (it);
26498
26499 /* If characters with lbearing or rbearing are displayed
26500 in this line, record that fact in a flag of the
26501 glyph row. This is used to optimize X output code. */
26502 if (pcm && (pcm->lbearing < 0 || pcm->rbearing > pcm->width))
26503 it->glyph_row->contains_overlapping_glyphs_p = 1;
26504 }
26505 if (! stretched_p && it->pixel_width == 0)
26506 /* We assure that all visible glyphs have at least 1-pixel
26507 width. */
26508 it->pixel_width = 1;
26509 }
26510 else if (it->char_to_display == '\n')
26511 {
26512 /* A newline has no width, but we need the height of the
26513 line. But if previous part of the line sets a height,
26514 don't increase that height. */
26515
26516 Lisp_Object height;
26517 Lisp_Object total_height = Qnil;
26518
26519 it->override_ascent = -1;
26520 it->pixel_width = 0;
26521 it->nglyphs = 0;
26522
26523 height = get_it_property (it, Qline_height);
26524 /* Split (line-height total-height) list. */
26525 if (CONSP (height)
26526 && CONSP (XCDR (height))
26527 && NILP (XCDR (XCDR (height))))
26528 {
26529 total_height = XCAR (XCDR (height));
26530 height = XCAR (height);
26531 }
26532 height = calc_line_height_property (it, height, font, boff, 1);
26533
26534 if (it->override_ascent >= 0)
26535 {
26536 it->ascent = it->override_ascent;
26537 it->descent = it->override_descent;
26538 boff = it->override_boff;
26539 }
26540 else
26541 {
26542 it->ascent = FONT_BASE (font) + boff;
26543 it->descent = FONT_DESCENT (font) - boff;
26544 }
26545
26546 if (EQ (height, Qt))
26547 {
26548 if (it->descent > it->max_descent)
26549 {
26550 it->ascent += it->descent - it->max_descent;
26551 it->descent = it->max_descent;
26552 }
26553 if (it->ascent > it->max_ascent)
26554 {
26555 it->descent = min (it->max_descent, it->descent + it->ascent - it->max_ascent);
26556 it->ascent = it->max_ascent;
26557 }
26558 it->phys_ascent = min (it->phys_ascent, it->ascent);
26559 it->phys_descent = min (it->phys_descent, it->descent);
26560 it->constrain_row_ascent_descent_p = 1;
26561 extra_line_spacing = 0;
26562 }
26563 else
26564 {
26565 Lisp_Object spacing;
26566
26567 it->phys_ascent = it->ascent;
26568 it->phys_descent = it->descent;
26569
26570 if ((it->max_ascent > 0 || it->max_descent > 0)
26571 && face->box != FACE_NO_BOX
26572 && face->box_line_width > 0)
26573 {
26574 it->ascent += face->box_line_width;
26575 it->descent += face->box_line_width;
26576 }
26577 if (!NILP (height)
26578 && XINT (height) > it->ascent + it->descent)
26579 it->ascent = XINT (height) - it->descent;
26580
26581 if (!NILP (total_height))
26582 spacing = calc_line_height_property (it, total_height, font, boff, 0);
26583 else
26584 {
26585 spacing = get_it_property (it, Qline_spacing);
26586 spacing = calc_line_height_property (it, spacing, font, boff, 0);
26587 }
26588 if (INTEGERP (spacing))
26589 {
26590 extra_line_spacing = XINT (spacing);
26591 if (!NILP (total_height))
26592 extra_line_spacing -= (it->phys_ascent + it->phys_descent);
26593 }
26594 }
26595 }
26596 else /* i.e. (it->char_to_display == '\t') */
26597 {
26598 if (font->space_width > 0)
26599 {
26600 int tab_width = it->tab_width * font->space_width;
26601 int x = it->current_x + it->continuation_lines_width;
26602 int next_tab_x = ((1 + x + tab_width - 1) / tab_width) * tab_width;
26603
26604 /* If the distance from the current position to the next tab
26605 stop is less than a space character width, use the
26606 tab stop after that. */
26607 if (next_tab_x - x < font->space_width)
26608 next_tab_x += tab_width;
26609
26610 it->pixel_width = next_tab_x - x;
26611 it->nglyphs = 1;
26612 it->ascent = it->phys_ascent = FONT_BASE (font) + boff;
26613 it->descent = it->phys_descent = FONT_DESCENT (font) - boff;
26614
26615 if (it->glyph_row)
26616 {
26617 append_stretch_glyph (it, it->object, it->pixel_width,
26618 it->ascent + it->descent, it->ascent);
26619 }
26620 }
26621 else
26622 {
26623 it->pixel_width = 0;
26624 it->nglyphs = 1;
26625 }
26626 }
26627 }
26628 else if (it->what == IT_COMPOSITION && it->cmp_it.ch < 0)
26629 {
26630 /* A static composition.
26631
26632 Note: A composition is represented as one glyph in the
26633 glyph matrix. There are no padding glyphs.
26634
26635 Important note: pixel_width, ascent, and descent are the
26636 values of what is drawn by draw_glyphs (i.e. the values of
26637 the overall glyphs composed). */
26638 struct face *face = FACE_FROM_ID (it->f, it->face_id);
26639 int boff; /* baseline offset */
26640 struct composition *cmp = composition_table[it->cmp_it.id];
26641 int glyph_len = cmp->glyph_len;
26642 struct font *font = face->font;
26643
26644 it->nglyphs = 1;
26645
26646 /* If we have not yet calculated pixel size data of glyphs of
26647 the composition for the current face font, calculate them
26648 now. Theoretically, we have to check all fonts for the
26649 glyphs, but that requires much time and memory space. So,
26650 here we check only the font of the first glyph. This may
26651 lead to incorrect display, but it's very rare, and C-l
26652 (recenter-top-bottom) can correct the display anyway. */
26653 if (! cmp->font || cmp->font != font)
26654 {
26655 /* Ascent and descent of the font of the first character
26656 of this composition (adjusted by baseline offset).
26657 Ascent and descent of overall glyphs should not be less
26658 than these, respectively. */
26659 int font_ascent, font_descent, font_height;
26660 /* Bounding box of the overall glyphs. */
26661 int leftmost, rightmost, lowest, highest;
26662 int lbearing, rbearing;
26663 int i, width, ascent, descent;
26664 int left_padded = 0, right_padded = 0;
26665 int c IF_LINT (= 0); /* cmp->glyph_len can't be zero; see Bug#8512 */
26666 XChar2b char2b;
26667 struct font_metrics *pcm;
26668 int font_not_found_p;
26669 ptrdiff_t pos;
26670
26671 for (glyph_len = cmp->glyph_len; glyph_len > 0; glyph_len--)
26672 if ((c = COMPOSITION_GLYPH (cmp, glyph_len - 1)) != '\t')
26673 break;
26674 if (glyph_len < cmp->glyph_len)
26675 right_padded = 1;
26676 for (i = 0; i < glyph_len; i++)
26677 {
26678 if ((c = COMPOSITION_GLYPH (cmp, i)) != '\t')
26679 break;
26680 cmp->offsets[i * 2] = cmp->offsets[i * 2 + 1] = 0;
26681 }
26682 if (i > 0)
26683 left_padded = 1;
26684
26685 pos = (STRINGP (it->string) ? IT_STRING_CHARPOS (*it)
26686 : IT_CHARPOS (*it));
26687 /* If no suitable font is found, use the default font. */
26688 font_not_found_p = font == NULL;
26689 if (font_not_found_p)
26690 {
26691 face = face->ascii_face;
26692 font = face->font;
26693 }
26694 boff = font->baseline_offset;
26695 if (font->vertical_centering)
26696 boff = VCENTER_BASELINE_OFFSET (font, it->f) - boff;
26697 font_ascent = FONT_BASE (font) + boff;
26698 font_descent = FONT_DESCENT (font) - boff;
26699 font_height = FONT_HEIGHT (font);
26700
26701 cmp->font = font;
26702
26703 pcm = NULL;
26704 if (! font_not_found_p)
26705 {
26706 get_char_face_and_encoding (it->f, c, it->face_id,
26707 &char2b, 0);
26708 pcm = get_per_char_metric (font, &char2b);
26709 }
26710
26711 /* Initialize the bounding box. */
26712 if (pcm)
26713 {
26714 width = cmp->glyph_len > 0 ? pcm->width : 0;
26715 ascent = pcm->ascent;
26716 descent = pcm->descent;
26717 lbearing = pcm->lbearing;
26718 rbearing = pcm->rbearing;
26719 }
26720 else
26721 {
26722 width = cmp->glyph_len > 0 ? font->space_width : 0;
26723 ascent = FONT_BASE (font);
26724 descent = FONT_DESCENT (font);
26725 lbearing = 0;
26726 rbearing = width;
26727 }
26728
26729 rightmost = width;
26730 leftmost = 0;
26731 lowest = - descent + boff;
26732 highest = ascent + boff;
26733
26734 if (! font_not_found_p
26735 && font->default_ascent
26736 && CHAR_TABLE_P (Vuse_default_ascent)
26737 && !NILP (Faref (Vuse_default_ascent,
26738 make_number (it->char_to_display))))
26739 highest = font->default_ascent + boff;
26740
26741 /* Draw the first glyph at the normal position. It may be
26742 shifted to right later if some other glyphs are drawn
26743 at the left. */
26744 cmp->offsets[i * 2] = 0;
26745 cmp->offsets[i * 2 + 1] = boff;
26746 cmp->lbearing = lbearing;
26747 cmp->rbearing = rbearing;
26748
26749 /* Set cmp->offsets for the remaining glyphs. */
26750 for (i++; i < glyph_len; i++)
26751 {
26752 int left, right, btm, top;
26753 int ch = COMPOSITION_GLYPH (cmp, i);
26754 int face_id;
26755 struct face *this_face;
26756
26757 if (ch == '\t')
26758 ch = ' ';
26759 face_id = FACE_FOR_CHAR (it->f, face, ch, pos, it->string);
26760 this_face = FACE_FROM_ID (it->f, face_id);
26761 font = this_face->font;
26762
26763 if (font == NULL)
26764 pcm = NULL;
26765 else
26766 {
26767 get_char_face_and_encoding (it->f, ch, face_id,
26768 &char2b, 0);
26769 pcm = get_per_char_metric (font, &char2b);
26770 }
26771 if (! pcm)
26772 cmp->offsets[i * 2] = cmp->offsets[i * 2 + 1] = 0;
26773 else
26774 {
26775 width = pcm->width;
26776 ascent = pcm->ascent;
26777 descent = pcm->descent;
26778 lbearing = pcm->lbearing;
26779 rbearing = pcm->rbearing;
26780 if (cmp->method != COMPOSITION_WITH_RULE_ALTCHARS)
26781 {
26782 /* Relative composition with or without
26783 alternate chars. */
26784 left = (leftmost + rightmost - width) / 2;
26785 btm = - descent + boff;
26786 if (font->relative_compose
26787 && (! CHAR_TABLE_P (Vignore_relative_composition)
26788 || NILP (Faref (Vignore_relative_composition,
26789 make_number (ch)))))
26790 {
26791
26792 if (- descent >= font->relative_compose)
26793 /* One extra pixel between two glyphs. */
26794 btm = highest + 1;
26795 else if (ascent <= 0)
26796 /* One extra pixel between two glyphs. */
26797 btm = lowest - 1 - ascent - descent;
26798 }
26799 }
26800 else
26801 {
26802 /* A composition rule is specified by an integer
26803 value that encodes global and new reference
26804 points (GREF and NREF). GREF and NREF are
26805 specified by numbers as below:
26806
26807 0---1---2 -- ascent
26808 | |
26809 | |
26810 | |
26811 9--10--11 -- center
26812 | |
26813 ---3---4---5--- baseline
26814 | |
26815 6---7---8 -- descent
26816 */
26817 int rule = COMPOSITION_RULE (cmp, i);
26818 int gref, nref, grefx, grefy, nrefx, nrefy, xoff, yoff;
26819
26820 COMPOSITION_DECODE_RULE (rule, gref, nref, xoff, yoff);
26821 grefx = gref % 3, nrefx = nref % 3;
26822 grefy = gref / 3, nrefy = nref / 3;
26823 if (xoff)
26824 xoff = font_height * (xoff - 128) / 256;
26825 if (yoff)
26826 yoff = font_height * (yoff - 128) / 256;
26827
26828 left = (leftmost
26829 + grefx * (rightmost - leftmost) / 2
26830 - nrefx * width / 2
26831 + xoff);
26832
26833 btm = ((grefy == 0 ? highest
26834 : grefy == 1 ? 0
26835 : grefy == 2 ? lowest
26836 : (highest + lowest) / 2)
26837 - (nrefy == 0 ? ascent + descent
26838 : nrefy == 1 ? descent - boff
26839 : nrefy == 2 ? 0
26840 : (ascent + descent) / 2)
26841 + yoff);
26842 }
26843
26844 cmp->offsets[i * 2] = left;
26845 cmp->offsets[i * 2 + 1] = btm + descent;
26846
26847 /* Update the bounding box of the overall glyphs. */
26848 if (width > 0)
26849 {
26850 right = left + width;
26851 if (left < leftmost)
26852 leftmost = left;
26853 if (right > rightmost)
26854 rightmost = right;
26855 }
26856 top = btm + descent + ascent;
26857 if (top > highest)
26858 highest = top;
26859 if (btm < lowest)
26860 lowest = btm;
26861
26862 if (cmp->lbearing > left + lbearing)
26863 cmp->lbearing = left + lbearing;
26864 if (cmp->rbearing < left + rbearing)
26865 cmp->rbearing = left + rbearing;
26866 }
26867 }
26868
26869 /* If there are glyphs whose x-offsets are negative,
26870 shift all glyphs to the right and make all x-offsets
26871 non-negative. */
26872 if (leftmost < 0)
26873 {
26874 for (i = 0; i < cmp->glyph_len; i++)
26875 cmp->offsets[i * 2] -= leftmost;
26876 rightmost -= leftmost;
26877 cmp->lbearing -= leftmost;
26878 cmp->rbearing -= leftmost;
26879 }
26880
26881 if (left_padded && cmp->lbearing < 0)
26882 {
26883 for (i = 0; i < cmp->glyph_len; i++)
26884 cmp->offsets[i * 2] -= cmp->lbearing;
26885 rightmost -= cmp->lbearing;
26886 cmp->rbearing -= cmp->lbearing;
26887 cmp->lbearing = 0;
26888 }
26889 if (right_padded && rightmost < cmp->rbearing)
26890 {
26891 rightmost = cmp->rbearing;
26892 }
26893
26894 cmp->pixel_width = rightmost;
26895 cmp->ascent = highest;
26896 cmp->descent = - lowest;
26897 if (cmp->ascent < font_ascent)
26898 cmp->ascent = font_ascent;
26899 if (cmp->descent < font_descent)
26900 cmp->descent = font_descent;
26901 }
26902
26903 if (it->glyph_row
26904 && (cmp->lbearing < 0
26905 || cmp->rbearing > cmp->pixel_width))
26906 it->glyph_row->contains_overlapping_glyphs_p = 1;
26907
26908 it->pixel_width = cmp->pixel_width;
26909 it->ascent = it->phys_ascent = cmp->ascent;
26910 it->descent = it->phys_descent = cmp->descent;
26911 if (face->box != FACE_NO_BOX)
26912 {
26913 int thick = face->box_line_width;
26914
26915 if (thick > 0)
26916 {
26917 it->ascent += thick;
26918 it->descent += thick;
26919 }
26920 else
26921 thick = - thick;
26922
26923 if (it->start_of_box_run_p)
26924 it->pixel_width += thick;
26925 if (it->end_of_box_run_p)
26926 it->pixel_width += thick;
26927 }
26928
26929 /* If face has an overline, add the height of the overline
26930 (1 pixel) and a 1 pixel margin to the character height. */
26931 if (face->overline_p)
26932 it->ascent += overline_margin;
26933
26934 take_vertical_position_into_account (it);
26935 if (it->ascent < 0)
26936 it->ascent = 0;
26937 if (it->descent < 0)
26938 it->descent = 0;
26939
26940 if (it->glyph_row && cmp->glyph_len > 0)
26941 append_composite_glyph (it);
26942 }
26943 else if (it->what == IT_COMPOSITION)
26944 {
26945 /* A dynamic (automatic) composition. */
26946 struct face *face = FACE_FROM_ID (it->f, it->face_id);
26947 Lisp_Object gstring;
26948 struct font_metrics metrics;
26949
26950 it->nglyphs = 1;
26951
26952 gstring = composition_gstring_from_id (it->cmp_it.id);
26953 it->pixel_width
26954 = composition_gstring_width (gstring, it->cmp_it.from, it->cmp_it.to,
26955 &metrics);
26956 if (it->glyph_row
26957 && (metrics.lbearing < 0 || metrics.rbearing > metrics.width))
26958 it->glyph_row->contains_overlapping_glyphs_p = 1;
26959 it->ascent = it->phys_ascent = metrics.ascent;
26960 it->descent = it->phys_descent = metrics.descent;
26961 if (face->box != FACE_NO_BOX)
26962 {
26963 int thick = face->box_line_width;
26964
26965 if (thick > 0)
26966 {
26967 it->ascent += thick;
26968 it->descent += thick;
26969 }
26970 else
26971 thick = - thick;
26972
26973 if (it->start_of_box_run_p)
26974 it->pixel_width += thick;
26975 if (it->end_of_box_run_p)
26976 it->pixel_width += thick;
26977 }
26978 /* If face has an overline, add the height of the overline
26979 (1 pixel) and a 1 pixel margin to the character height. */
26980 if (face->overline_p)
26981 it->ascent += overline_margin;
26982 take_vertical_position_into_account (it);
26983 if (it->ascent < 0)
26984 it->ascent = 0;
26985 if (it->descent < 0)
26986 it->descent = 0;
26987
26988 if (it->glyph_row)
26989 append_composite_glyph (it);
26990 }
26991 else if (it->what == IT_GLYPHLESS)
26992 produce_glyphless_glyph (it, 0, Qnil);
26993 else if (it->what == IT_IMAGE)
26994 produce_image_glyph (it);
26995 else if (it->what == IT_STRETCH)
26996 produce_stretch_glyph (it);
26997
26998 done:
26999 /* Accumulate dimensions. Note: can't assume that it->descent > 0
27000 because this isn't true for images with `:ascent 100'. */
27001 eassert (it->ascent >= 0 && it->descent >= 0);
27002 if (it->area == TEXT_AREA)
27003 it->current_x += it->pixel_width;
27004
27005 if (extra_line_spacing > 0)
27006 {
27007 it->descent += extra_line_spacing;
27008 if (extra_line_spacing > it->max_extra_line_spacing)
27009 it->max_extra_line_spacing = extra_line_spacing;
27010 }
27011
27012 it->max_ascent = max (it->max_ascent, it->ascent);
27013 it->max_descent = max (it->max_descent, it->descent);
27014 it->max_phys_ascent = max (it->max_phys_ascent, it->phys_ascent);
27015 it->max_phys_descent = max (it->max_phys_descent, it->phys_descent);
27016 }
27017
27018 /* EXPORT for RIF:
27019 Output LEN glyphs starting at START at the nominal cursor position.
27020 Advance the nominal cursor over the text. UPDATED_ROW is the glyph row
27021 being updated, and UPDATED_AREA is the area of that row being updated. */
27022
27023 void
27024 x_write_glyphs (struct window *w, struct glyph_row *updated_row,
27025 struct glyph *start, enum glyph_row_area updated_area, int len)
27026 {
27027 int x, hpos, chpos = w->phys_cursor.hpos;
27028
27029 eassert (updated_row);
27030 /* When the window is hscrolled, cursor hpos can legitimately be out
27031 of bounds, but we draw the cursor at the corresponding window
27032 margin in that case. */
27033 if (!updated_row->reversed_p && chpos < 0)
27034 chpos = 0;
27035 if (updated_row->reversed_p && chpos >= updated_row->used[TEXT_AREA])
27036 chpos = updated_row->used[TEXT_AREA] - 1;
27037
27038 block_input ();
27039
27040 /* Write glyphs. */
27041
27042 hpos = start - updated_row->glyphs[updated_area];
27043 x = draw_glyphs (w, w->output_cursor.x,
27044 updated_row, updated_area,
27045 hpos, hpos + len,
27046 DRAW_NORMAL_TEXT, 0);
27047
27048 /* Invalidate old phys cursor if the glyph at its hpos is redrawn. */
27049 if (updated_area == TEXT_AREA
27050 && w->phys_cursor_on_p
27051 && w->phys_cursor.vpos == w->output_cursor.vpos
27052 && chpos >= hpos
27053 && chpos < hpos + len)
27054 w->phys_cursor_on_p = 0;
27055
27056 unblock_input ();
27057
27058 /* Advance the output cursor. */
27059 w->output_cursor.hpos += len;
27060 w->output_cursor.x = x;
27061 }
27062
27063
27064 /* EXPORT for RIF:
27065 Insert LEN glyphs from START at the nominal cursor position. */
27066
27067 void
27068 x_insert_glyphs (struct window *w, struct glyph_row *updated_row,
27069 struct glyph *start, enum glyph_row_area updated_area, int len)
27070 {
27071 struct frame *f;
27072 int line_height, shift_by_width, shifted_region_width;
27073 struct glyph_row *row;
27074 struct glyph *glyph;
27075 int frame_x, frame_y;
27076 ptrdiff_t hpos;
27077
27078 eassert (updated_row);
27079 block_input ();
27080 f = XFRAME (WINDOW_FRAME (w));
27081
27082 /* Get the height of the line we are in. */
27083 row = updated_row;
27084 line_height = row->height;
27085
27086 /* Get the width of the glyphs to insert. */
27087 shift_by_width = 0;
27088 for (glyph = start; glyph < start + len; ++glyph)
27089 shift_by_width += glyph->pixel_width;
27090
27091 /* Get the width of the region to shift right. */
27092 shifted_region_width = (window_box_width (w, updated_area)
27093 - w->output_cursor.x
27094 - shift_by_width);
27095
27096 /* Shift right. */
27097 frame_x = window_box_left (w, updated_area) + w->output_cursor.x;
27098 frame_y = WINDOW_TO_FRAME_PIXEL_Y (w, w->output_cursor.y);
27099
27100 FRAME_RIF (f)->shift_glyphs_for_insert (f, frame_x, frame_y, shifted_region_width,
27101 line_height, shift_by_width);
27102
27103 /* Write the glyphs. */
27104 hpos = start - row->glyphs[updated_area];
27105 draw_glyphs (w, w->output_cursor.x, row, updated_area,
27106 hpos, hpos + len,
27107 DRAW_NORMAL_TEXT, 0);
27108
27109 /* Advance the output cursor. */
27110 w->output_cursor.hpos += len;
27111 w->output_cursor.x += shift_by_width;
27112 unblock_input ();
27113 }
27114
27115
27116 /* EXPORT for RIF:
27117 Erase the current text line from the nominal cursor position
27118 (inclusive) to pixel column TO_X (exclusive). The idea is that
27119 everything from TO_X onward is already erased.
27120
27121 TO_X is a pixel position relative to UPDATED_AREA of currently
27122 updated window W. TO_X == -1 means clear to the end of this area. */
27123
27124 void
27125 x_clear_end_of_line (struct window *w, struct glyph_row *updated_row,
27126 enum glyph_row_area updated_area, int to_x)
27127 {
27128 struct frame *f;
27129 int max_x, min_y, max_y;
27130 int from_x, from_y, to_y;
27131
27132 eassert (updated_row);
27133 f = XFRAME (w->frame);
27134
27135 if (updated_row->full_width_p)
27136 max_x = (WINDOW_PIXEL_WIDTH (w)
27137 - (updated_row->mode_line_p ? WINDOW_RIGHT_DIVIDER_WIDTH (w) : 0));
27138 else
27139 max_x = window_box_width (w, updated_area);
27140 max_y = window_text_bottom_y (w);
27141
27142 /* TO_X == 0 means don't do anything. TO_X < 0 means clear to end
27143 of window. For TO_X > 0, truncate to end of drawing area. */
27144 if (to_x == 0)
27145 return;
27146 else if (to_x < 0)
27147 to_x = max_x;
27148 else
27149 to_x = min (to_x, max_x);
27150
27151 to_y = min (max_y, w->output_cursor.y + updated_row->height);
27152
27153 /* Notice if the cursor will be cleared by this operation. */
27154 if (!updated_row->full_width_p)
27155 notice_overwritten_cursor (w, updated_area,
27156 w->output_cursor.x, -1,
27157 updated_row->y,
27158 MATRIX_ROW_BOTTOM_Y (updated_row));
27159
27160 from_x = w->output_cursor.x;
27161
27162 /* Translate to frame coordinates. */
27163 if (updated_row->full_width_p)
27164 {
27165 from_x = WINDOW_TO_FRAME_PIXEL_X (w, from_x);
27166 to_x = WINDOW_TO_FRAME_PIXEL_X (w, to_x);
27167 }
27168 else
27169 {
27170 int area_left = window_box_left (w, updated_area);
27171 from_x += area_left;
27172 to_x += area_left;
27173 }
27174
27175 min_y = WINDOW_HEADER_LINE_HEIGHT (w);
27176 from_y = WINDOW_TO_FRAME_PIXEL_Y (w, max (min_y, w->output_cursor.y));
27177 to_y = WINDOW_TO_FRAME_PIXEL_Y (w, to_y);
27178
27179 /* Prevent inadvertently clearing to end of the X window. */
27180 if (to_x > from_x && to_y > from_y)
27181 {
27182 block_input ();
27183 FRAME_RIF (f)->clear_frame_area (f, from_x, from_y,
27184 to_x - from_x, to_y - from_y);
27185 unblock_input ();
27186 }
27187 }
27188
27189 #endif /* HAVE_WINDOW_SYSTEM */
27190
27191
27192 \f
27193 /***********************************************************************
27194 Cursor types
27195 ***********************************************************************/
27196
27197 /* Value is the internal representation of the specified cursor type
27198 ARG. If type is BAR_CURSOR, return in *WIDTH the specified width
27199 of the bar cursor. */
27200
27201 static enum text_cursor_kinds
27202 get_specified_cursor_type (Lisp_Object arg, int *width)
27203 {
27204 enum text_cursor_kinds type;
27205
27206 if (NILP (arg))
27207 return NO_CURSOR;
27208
27209 if (EQ (arg, Qbox))
27210 return FILLED_BOX_CURSOR;
27211
27212 if (EQ (arg, Qhollow))
27213 return HOLLOW_BOX_CURSOR;
27214
27215 if (EQ (arg, Qbar))
27216 {
27217 *width = 2;
27218 return BAR_CURSOR;
27219 }
27220
27221 if (CONSP (arg)
27222 && EQ (XCAR (arg), Qbar)
27223 && RANGED_INTEGERP (0, XCDR (arg), INT_MAX))
27224 {
27225 *width = XINT (XCDR (arg));
27226 return BAR_CURSOR;
27227 }
27228
27229 if (EQ (arg, Qhbar))
27230 {
27231 *width = 2;
27232 return HBAR_CURSOR;
27233 }
27234
27235 if (CONSP (arg)
27236 && EQ (XCAR (arg), Qhbar)
27237 && RANGED_INTEGERP (0, XCDR (arg), INT_MAX))
27238 {
27239 *width = XINT (XCDR (arg));
27240 return HBAR_CURSOR;
27241 }
27242
27243 /* Treat anything unknown as "hollow box cursor".
27244 It was bad to signal an error; people have trouble fixing
27245 .Xdefaults with Emacs, when it has something bad in it. */
27246 type = HOLLOW_BOX_CURSOR;
27247
27248 return type;
27249 }
27250
27251 /* Set the default cursor types for specified frame. */
27252 void
27253 set_frame_cursor_types (struct frame *f, Lisp_Object arg)
27254 {
27255 int width = 1;
27256 Lisp_Object tem;
27257
27258 FRAME_DESIRED_CURSOR (f) = get_specified_cursor_type (arg, &width);
27259 FRAME_CURSOR_WIDTH (f) = width;
27260
27261 /* By default, set up the blink-off state depending on the on-state. */
27262
27263 tem = Fassoc (arg, Vblink_cursor_alist);
27264 if (!NILP (tem))
27265 {
27266 FRAME_BLINK_OFF_CURSOR (f)
27267 = get_specified_cursor_type (XCDR (tem), &width);
27268 FRAME_BLINK_OFF_CURSOR_WIDTH (f) = width;
27269 }
27270 else
27271 FRAME_BLINK_OFF_CURSOR (f) = DEFAULT_CURSOR;
27272
27273 /* Make sure the cursor gets redrawn. */
27274 f->cursor_type_changed = 1;
27275 }
27276
27277
27278 #ifdef HAVE_WINDOW_SYSTEM
27279
27280 /* Return the cursor we want to be displayed in window W. Return
27281 width of bar/hbar cursor through WIDTH arg. Return with
27282 ACTIVE_CURSOR arg set to 1 if cursor in window W is `active'
27283 (i.e. if the `system caret' should track this cursor).
27284
27285 In a mini-buffer window, we want the cursor only to appear if we
27286 are reading input from this window. For the selected window, we
27287 want the cursor type given by the frame parameter or buffer local
27288 setting of cursor-type. If explicitly marked off, draw no cursor.
27289 In all other cases, we want a hollow box cursor. */
27290
27291 static enum text_cursor_kinds
27292 get_window_cursor_type (struct window *w, struct glyph *glyph, int *width,
27293 int *active_cursor)
27294 {
27295 struct frame *f = XFRAME (w->frame);
27296 struct buffer *b = XBUFFER (w->contents);
27297 int cursor_type = DEFAULT_CURSOR;
27298 Lisp_Object alt_cursor;
27299 int non_selected = 0;
27300
27301 *active_cursor = 1;
27302
27303 /* Echo area */
27304 if (cursor_in_echo_area
27305 && FRAME_HAS_MINIBUF_P (f)
27306 && EQ (FRAME_MINIBUF_WINDOW (f), echo_area_window))
27307 {
27308 if (w == XWINDOW (echo_area_window))
27309 {
27310 if (EQ (BVAR (b, cursor_type), Qt) || NILP (BVAR (b, cursor_type)))
27311 {
27312 *width = FRAME_CURSOR_WIDTH (f);
27313 return FRAME_DESIRED_CURSOR (f);
27314 }
27315 else
27316 return get_specified_cursor_type (BVAR (b, cursor_type), width);
27317 }
27318
27319 *active_cursor = 0;
27320 non_selected = 1;
27321 }
27322
27323 /* Detect a nonselected window or nonselected frame. */
27324 else if (w != XWINDOW (f->selected_window)
27325 || f != FRAME_DISPLAY_INFO (f)->x_highlight_frame)
27326 {
27327 *active_cursor = 0;
27328
27329 if (MINI_WINDOW_P (w) && minibuf_level == 0)
27330 return NO_CURSOR;
27331
27332 non_selected = 1;
27333 }
27334
27335 /* Never display a cursor in a window in which cursor-type is nil. */
27336 if (NILP (BVAR (b, cursor_type)))
27337 return NO_CURSOR;
27338
27339 /* Get the normal cursor type for this window. */
27340 if (EQ (BVAR (b, cursor_type), Qt))
27341 {
27342 cursor_type = FRAME_DESIRED_CURSOR (f);
27343 *width = FRAME_CURSOR_WIDTH (f);
27344 }
27345 else
27346 cursor_type = get_specified_cursor_type (BVAR (b, cursor_type), width);
27347
27348 /* Use cursor-in-non-selected-windows instead
27349 for non-selected window or frame. */
27350 if (non_selected)
27351 {
27352 alt_cursor = BVAR (b, cursor_in_non_selected_windows);
27353 if (!EQ (Qt, alt_cursor))
27354 return get_specified_cursor_type (alt_cursor, width);
27355 /* t means modify the normal cursor type. */
27356 if (cursor_type == FILLED_BOX_CURSOR)
27357 cursor_type = HOLLOW_BOX_CURSOR;
27358 else if (cursor_type == BAR_CURSOR && *width > 1)
27359 --*width;
27360 return cursor_type;
27361 }
27362
27363 /* Use normal cursor if not blinked off. */
27364 if (!w->cursor_off_p)
27365 {
27366 if (glyph != NULL && glyph->type == IMAGE_GLYPH)
27367 {
27368 if (cursor_type == FILLED_BOX_CURSOR)
27369 {
27370 /* Using a block cursor on large images can be very annoying.
27371 So use a hollow cursor for "large" images.
27372 If image is not transparent (no mask), also use hollow cursor. */
27373 struct image *img = IMAGE_FROM_ID (f, glyph->u.img_id);
27374 if (img != NULL && IMAGEP (img->spec))
27375 {
27376 /* Arbitrarily, interpret "Large" as >32x32 and >NxN
27377 where N = size of default frame font size.
27378 This should cover most of the "tiny" icons people may use. */
27379 if (!img->mask
27380 || img->width > max (32, WINDOW_FRAME_COLUMN_WIDTH (w))
27381 || img->height > max (32, WINDOW_FRAME_LINE_HEIGHT (w)))
27382 cursor_type = HOLLOW_BOX_CURSOR;
27383 }
27384 }
27385 else if (cursor_type != NO_CURSOR)
27386 {
27387 /* Display current only supports BOX and HOLLOW cursors for images.
27388 So for now, unconditionally use a HOLLOW cursor when cursor is
27389 not a solid box cursor. */
27390 cursor_type = HOLLOW_BOX_CURSOR;
27391 }
27392 }
27393 return cursor_type;
27394 }
27395
27396 /* Cursor is blinked off, so determine how to "toggle" it. */
27397
27398 /* First look for an entry matching the buffer's cursor-type in blink-cursor-alist. */
27399 if ((alt_cursor = Fassoc (BVAR (b, cursor_type), Vblink_cursor_alist), !NILP (alt_cursor)))
27400 return get_specified_cursor_type (XCDR (alt_cursor), width);
27401
27402 /* Then see if frame has specified a specific blink off cursor type. */
27403 if (FRAME_BLINK_OFF_CURSOR (f) != DEFAULT_CURSOR)
27404 {
27405 *width = FRAME_BLINK_OFF_CURSOR_WIDTH (f);
27406 return FRAME_BLINK_OFF_CURSOR (f);
27407 }
27408
27409 #if 0
27410 /* Some people liked having a permanently visible blinking cursor,
27411 while others had very strong opinions against it. So it was
27412 decided to remove it. KFS 2003-09-03 */
27413
27414 /* Finally perform built-in cursor blinking:
27415 filled box <-> hollow box
27416 wide [h]bar <-> narrow [h]bar
27417 narrow [h]bar <-> no cursor
27418 other type <-> no cursor */
27419
27420 if (cursor_type == FILLED_BOX_CURSOR)
27421 return HOLLOW_BOX_CURSOR;
27422
27423 if ((cursor_type == BAR_CURSOR || cursor_type == HBAR_CURSOR) && *width > 1)
27424 {
27425 *width = 1;
27426 return cursor_type;
27427 }
27428 #endif
27429
27430 return NO_CURSOR;
27431 }
27432
27433
27434 /* Notice when the text cursor of window W has been completely
27435 overwritten by a drawing operation that outputs glyphs in AREA
27436 starting at X0 and ending at X1 in the line starting at Y0 and
27437 ending at Y1. X coordinates are area-relative. X1 < 0 means all
27438 the rest of the line after X0 has been written. Y coordinates
27439 are window-relative. */
27440
27441 static void
27442 notice_overwritten_cursor (struct window *w, enum glyph_row_area area,
27443 int x0, int x1, int y0, int y1)
27444 {
27445 int cx0, cx1, cy0, cy1;
27446 struct glyph_row *row;
27447
27448 if (!w->phys_cursor_on_p)
27449 return;
27450 if (area != TEXT_AREA)
27451 return;
27452
27453 if (w->phys_cursor.vpos < 0
27454 || w->phys_cursor.vpos >= w->current_matrix->nrows
27455 || (row = w->current_matrix->rows + w->phys_cursor.vpos,
27456 !(row->enabled_p && MATRIX_ROW_DISPLAYS_TEXT_P (row))))
27457 return;
27458
27459 if (row->cursor_in_fringe_p)
27460 {
27461 row->cursor_in_fringe_p = 0;
27462 draw_fringe_bitmap (w, row, row->reversed_p);
27463 w->phys_cursor_on_p = 0;
27464 return;
27465 }
27466
27467 cx0 = w->phys_cursor.x;
27468 cx1 = cx0 + w->phys_cursor_width;
27469 if (x0 > cx0 || (x1 >= 0 && x1 < cx1))
27470 return;
27471
27472 /* The cursor image will be completely removed from the
27473 screen if the output area intersects the cursor area in
27474 y-direction. When we draw in [y0 y1[, and some part of
27475 the cursor is at y < y0, that part must have been drawn
27476 before. When scrolling, the cursor is erased before
27477 actually scrolling, so we don't come here. When not
27478 scrolling, the rows above the old cursor row must have
27479 changed, and in this case these rows must have written
27480 over the cursor image.
27481
27482 Likewise if part of the cursor is below y1, with the
27483 exception of the cursor being in the first blank row at
27484 the buffer and window end because update_text_area
27485 doesn't draw that row. (Except when it does, but
27486 that's handled in update_text_area.) */
27487
27488 cy0 = w->phys_cursor.y;
27489 cy1 = cy0 + w->phys_cursor_height;
27490 if ((y0 < cy0 || y0 >= cy1) && (y1 <= cy0 || y1 >= cy1))
27491 return;
27492
27493 w->phys_cursor_on_p = 0;
27494 }
27495
27496 #endif /* HAVE_WINDOW_SYSTEM */
27497
27498 \f
27499 /************************************************************************
27500 Mouse Face
27501 ************************************************************************/
27502
27503 #ifdef HAVE_WINDOW_SYSTEM
27504
27505 /* EXPORT for RIF:
27506 Fix the display of area AREA of overlapping row ROW in window W
27507 with respect to the overlapping part OVERLAPS. */
27508
27509 void
27510 x_fix_overlapping_area (struct window *w, struct glyph_row *row,
27511 enum glyph_row_area area, int overlaps)
27512 {
27513 int i, x;
27514
27515 block_input ();
27516
27517 x = 0;
27518 for (i = 0; i < row->used[area];)
27519 {
27520 if (row->glyphs[area][i].overlaps_vertically_p)
27521 {
27522 int start = i, start_x = x;
27523
27524 do
27525 {
27526 x += row->glyphs[area][i].pixel_width;
27527 ++i;
27528 }
27529 while (i < row->used[area]
27530 && row->glyphs[area][i].overlaps_vertically_p);
27531
27532 draw_glyphs (w, start_x, row, area,
27533 start, i,
27534 DRAW_NORMAL_TEXT, overlaps);
27535 }
27536 else
27537 {
27538 x += row->glyphs[area][i].pixel_width;
27539 ++i;
27540 }
27541 }
27542
27543 unblock_input ();
27544 }
27545
27546
27547 /* EXPORT:
27548 Draw the cursor glyph of window W in glyph row ROW. See the
27549 comment of draw_glyphs for the meaning of HL. */
27550
27551 void
27552 draw_phys_cursor_glyph (struct window *w, struct glyph_row *row,
27553 enum draw_glyphs_face hl)
27554 {
27555 /* If cursor hpos is out of bounds, don't draw garbage. This can
27556 happen in mini-buffer windows when switching between echo area
27557 glyphs and mini-buffer. */
27558 if ((row->reversed_p
27559 ? (w->phys_cursor.hpos >= 0)
27560 : (w->phys_cursor.hpos < row->used[TEXT_AREA])))
27561 {
27562 int on_p = w->phys_cursor_on_p;
27563 int x1;
27564 int hpos = w->phys_cursor.hpos;
27565
27566 /* When the window is hscrolled, cursor hpos can legitimately be
27567 out of bounds, but we draw the cursor at the corresponding
27568 window margin in that case. */
27569 if (!row->reversed_p && hpos < 0)
27570 hpos = 0;
27571 if (row->reversed_p && hpos >= row->used[TEXT_AREA])
27572 hpos = row->used[TEXT_AREA] - 1;
27573
27574 x1 = draw_glyphs (w, w->phys_cursor.x, row, TEXT_AREA, hpos, hpos + 1,
27575 hl, 0);
27576 w->phys_cursor_on_p = on_p;
27577
27578 if (hl == DRAW_CURSOR)
27579 w->phys_cursor_width = x1 - w->phys_cursor.x;
27580 /* When we erase the cursor, and ROW is overlapped by other
27581 rows, make sure that these overlapping parts of other rows
27582 are redrawn. */
27583 else if (hl == DRAW_NORMAL_TEXT && row->overlapped_p)
27584 {
27585 w->phys_cursor_width = x1 - w->phys_cursor.x;
27586
27587 if (row > w->current_matrix->rows
27588 && MATRIX_ROW_OVERLAPS_SUCC_P (row - 1))
27589 x_fix_overlapping_area (w, row - 1, TEXT_AREA,
27590 OVERLAPS_ERASED_CURSOR);
27591
27592 if (MATRIX_ROW_BOTTOM_Y (row) < window_text_bottom_y (w)
27593 && MATRIX_ROW_OVERLAPS_PRED_P (row + 1))
27594 x_fix_overlapping_area (w, row + 1, TEXT_AREA,
27595 OVERLAPS_ERASED_CURSOR);
27596 }
27597 }
27598 }
27599
27600
27601 /* Erase the image of a cursor of window W from the screen. */
27602
27603 void
27604 erase_phys_cursor (struct window *w)
27605 {
27606 struct frame *f = XFRAME (w->frame);
27607 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
27608 int hpos = w->phys_cursor.hpos;
27609 int vpos = w->phys_cursor.vpos;
27610 int mouse_face_here_p = 0;
27611 struct glyph_matrix *active_glyphs = w->current_matrix;
27612 struct glyph_row *cursor_row;
27613 struct glyph *cursor_glyph;
27614 enum draw_glyphs_face hl;
27615
27616 /* No cursor displayed or row invalidated => nothing to do on the
27617 screen. */
27618 if (w->phys_cursor_type == NO_CURSOR)
27619 goto mark_cursor_off;
27620
27621 /* VPOS >= active_glyphs->nrows means that window has been resized.
27622 Don't bother to erase the cursor. */
27623 if (vpos >= active_glyphs->nrows)
27624 goto mark_cursor_off;
27625
27626 /* If row containing cursor is marked invalid, there is nothing we
27627 can do. */
27628 cursor_row = MATRIX_ROW (active_glyphs, vpos);
27629 if (!cursor_row->enabled_p)
27630 goto mark_cursor_off;
27631
27632 /* If line spacing is > 0, old cursor may only be partially visible in
27633 window after split-window. So adjust visible height. */
27634 cursor_row->visible_height = min (cursor_row->visible_height,
27635 window_text_bottom_y (w) - cursor_row->y);
27636
27637 /* If row is completely invisible, don't attempt to delete a cursor which
27638 isn't there. This can happen if cursor is at top of a window, and
27639 we switch to a buffer with a header line in that window. */
27640 if (cursor_row->visible_height <= 0)
27641 goto mark_cursor_off;
27642
27643 /* If cursor is in the fringe, erase by drawing actual bitmap there. */
27644 if (cursor_row->cursor_in_fringe_p)
27645 {
27646 cursor_row->cursor_in_fringe_p = 0;
27647 draw_fringe_bitmap (w, cursor_row, cursor_row->reversed_p);
27648 goto mark_cursor_off;
27649 }
27650
27651 /* This can happen when the new row is shorter than the old one.
27652 In this case, either draw_glyphs or clear_end_of_line
27653 should have cleared the cursor. Note that we wouldn't be
27654 able to erase the cursor in this case because we don't have a
27655 cursor glyph at hand. */
27656 if ((cursor_row->reversed_p
27657 ? (w->phys_cursor.hpos < 0)
27658 : (w->phys_cursor.hpos >= cursor_row->used[TEXT_AREA])))
27659 goto mark_cursor_off;
27660
27661 /* When the window is hscrolled, cursor hpos can legitimately be out
27662 of bounds, but we draw the cursor at the corresponding window
27663 margin in that case. */
27664 if (!cursor_row->reversed_p && hpos < 0)
27665 hpos = 0;
27666 if (cursor_row->reversed_p && hpos >= cursor_row->used[TEXT_AREA])
27667 hpos = cursor_row->used[TEXT_AREA] - 1;
27668
27669 /* If the cursor is in the mouse face area, redisplay that when
27670 we clear the cursor. */
27671 if (! NILP (hlinfo->mouse_face_window)
27672 && coords_in_mouse_face_p (w, hpos, vpos)
27673 /* Don't redraw the cursor's spot in mouse face if it is at the
27674 end of a line (on a newline). The cursor appears there, but
27675 mouse highlighting does not. */
27676 && cursor_row->used[TEXT_AREA] > hpos && hpos >= 0)
27677 mouse_face_here_p = 1;
27678
27679 /* Maybe clear the display under the cursor. */
27680 if (w->phys_cursor_type == HOLLOW_BOX_CURSOR)
27681 {
27682 int x, y;
27683 int header_line_height = WINDOW_HEADER_LINE_HEIGHT (w);
27684 int width;
27685
27686 cursor_glyph = get_phys_cursor_glyph (w);
27687 if (cursor_glyph == NULL)
27688 goto mark_cursor_off;
27689
27690 width = cursor_glyph->pixel_width;
27691 x = w->phys_cursor.x;
27692 if (x < 0)
27693 {
27694 width += x;
27695 x = 0;
27696 }
27697 width = min (width, window_box_width (w, TEXT_AREA) - x);
27698 y = WINDOW_TO_FRAME_PIXEL_Y (w, max (header_line_height, cursor_row->y));
27699 x = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, x);
27700
27701 if (width > 0)
27702 FRAME_RIF (f)->clear_frame_area (f, x, y, width, cursor_row->visible_height);
27703 }
27704
27705 /* Erase the cursor by redrawing the character underneath it. */
27706 if (mouse_face_here_p)
27707 hl = DRAW_MOUSE_FACE;
27708 else
27709 hl = DRAW_NORMAL_TEXT;
27710 draw_phys_cursor_glyph (w, cursor_row, hl);
27711
27712 mark_cursor_off:
27713 w->phys_cursor_on_p = 0;
27714 w->phys_cursor_type = NO_CURSOR;
27715 }
27716
27717
27718 /* EXPORT:
27719 Display or clear cursor of window W. If ON is zero, clear the
27720 cursor. If it is non-zero, display the cursor. If ON is nonzero,
27721 where to put the cursor is specified by HPOS, VPOS, X and Y. */
27722
27723 void
27724 display_and_set_cursor (struct window *w, bool on,
27725 int hpos, int vpos, int x, int y)
27726 {
27727 struct frame *f = XFRAME (w->frame);
27728 int new_cursor_type;
27729 int new_cursor_width;
27730 int active_cursor;
27731 struct glyph_row *glyph_row;
27732 struct glyph *glyph;
27733
27734 /* This is pointless on invisible frames, and dangerous on garbaged
27735 windows and frames; in the latter case, the frame or window may
27736 be in the midst of changing its size, and x and y may be off the
27737 window. */
27738 if (! FRAME_VISIBLE_P (f)
27739 || FRAME_GARBAGED_P (f)
27740 || vpos >= w->current_matrix->nrows
27741 || hpos >= w->current_matrix->matrix_w)
27742 return;
27743
27744 /* If cursor is off and we want it off, return quickly. */
27745 if (!on && !w->phys_cursor_on_p)
27746 return;
27747
27748 glyph_row = MATRIX_ROW (w->current_matrix, vpos);
27749 /* If cursor row is not enabled, we don't really know where to
27750 display the cursor. */
27751 if (!glyph_row->enabled_p)
27752 {
27753 w->phys_cursor_on_p = 0;
27754 return;
27755 }
27756
27757 glyph = NULL;
27758 if (!glyph_row->exact_window_width_line_p
27759 || (0 <= hpos && hpos < glyph_row->used[TEXT_AREA]))
27760 glyph = glyph_row->glyphs[TEXT_AREA] + hpos;
27761
27762 eassert (input_blocked_p ());
27763
27764 /* Set new_cursor_type to the cursor we want to be displayed. */
27765 new_cursor_type = get_window_cursor_type (w, glyph,
27766 &new_cursor_width, &active_cursor);
27767
27768 /* If cursor is currently being shown and we don't want it to be or
27769 it is in the wrong place, or the cursor type is not what we want,
27770 erase it. */
27771 if (w->phys_cursor_on_p
27772 && (!on
27773 || w->phys_cursor.x != x
27774 || w->phys_cursor.y != y
27775 /* HPOS can be negative in R2L rows whose
27776 exact_window_width_line_p flag is set (i.e. their newline
27777 would "overflow into the fringe"). */
27778 || hpos < 0
27779 || new_cursor_type != w->phys_cursor_type
27780 || ((new_cursor_type == BAR_CURSOR || new_cursor_type == HBAR_CURSOR)
27781 && new_cursor_width != w->phys_cursor_width)))
27782 erase_phys_cursor (w);
27783
27784 /* Don't check phys_cursor_on_p here because that flag is only set
27785 to zero in some cases where we know that the cursor has been
27786 completely erased, to avoid the extra work of erasing the cursor
27787 twice. In other words, phys_cursor_on_p can be 1 and the cursor
27788 still not be visible, or it has only been partly erased. */
27789 if (on)
27790 {
27791 w->phys_cursor_ascent = glyph_row->ascent;
27792 w->phys_cursor_height = glyph_row->height;
27793
27794 /* Set phys_cursor_.* before x_draw_.* is called because some
27795 of them may need the information. */
27796 w->phys_cursor.x = x;
27797 w->phys_cursor.y = glyph_row->y;
27798 w->phys_cursor.hpos = hpos;
27799 w->phys_cursor.vpos = vpos;
27800 }
27801
27802 FRAME_RIF (f)->draw_window_cursor (w, glyph_row, x, y,
27803 new_cursor_type, new_cursor_width,
27804 on, active_cursor);
27805 }
27806
27807
27808 /* Switch the display of W's cursor on or off, according to the value
27809 of ON. */
27810
27811 static void
27812 update_window_cursor (struct window *w, bool on)
27813 {
27814 /* Don't update cursor in windows whose frame is in the process
27815 of being deleted. */
27816 if (w->current_matrix)
27817 {
27818 int hpos = w->phys_cursor.hpos;
27819 int vpos = w->phys_cursor.vpos;
27820 struct glyph_row *row;
27821
27822 if (vpos >= w->current_matrix->nrows
27823 || hpos >= w->current_matrix->matrix_w)
27824 return;
27825
27826 row = MATRIX_ROW (w->current_matrix, vpos);
27827
27828 /* When the window is hscrolled, cursor hpos can legitimately be
27829 out of bounds, but we draw the cursor at the corresponding
27830 window margin in that case. */
27831 if (!row->reversed_p && hpos < 0)
27832 hpos = 0;
27833 if (row->reversed_p && hpos >= row->used[TEXT_AREA])
27834 hpos = row->used[TEXT_AREA] - 1;
27835
27836 block_input ();
27837 display_and_set_cursor (w, on, hpos, vpos,
27838 w->phys_cursor.x, w->phys_cursor.y);
27839 unblock_input ();
27840 }
27841 }
27842
27843
27844 /* Call update_window_cursor with parameter ON_P on all leaf windows
27845 in the window tree rooted at W. */
27846
27847 static void
27848 update_cursor_in_window_tree (struct window *w, bool on_p)
27849 {
27850 while (w)
27851 {
27852 if (WINDOWP (w->contents))
27853 update_cursor_in_window_tree (XWINDOW (w->contents), on_p);
27854 else
27855 update_window_cursor (w, on_p);
27856
27857 w = NILP (w->next) ? 0 : XWINDOW (w->next);
27858 }
27859 }
27860
27861
27862 /* EXPORT:
27863 Display the cursor on window W, or clear it, according to ON_P.
27864 Don't change the cursor's position. */
27865
27866 void
27867 x_update_cursor (struct frame *f, bool on_p)
27868 {
27869 update_cursor_in_window_tree (XWINDOW (f->root_window), on_p);
27870 }
27871
27872
27873 /* EXPORT:
27874 Clear the cursor of window W to background color, and mark the
27875 cursor as not shown. This is used when the text where the cursor
27876 is about to be rewritten. */
27877
27878 void
27879 x_clear_cursor (struct window *w)
27880 {
27881 if (FRAME_VISIBLE_P (XFRAME (w->frame)) && w->phys_cursor_on_p)
27882 update_window_cursor (w, 0);
27883 }
27884
27885 #endif /* HAVE_WINDOW_SYSTEM */
27886
27887 /* Implementation of draw_row_with_mouse_face for GUI sessions, GPM,
27888 and MSDOS. */
27889 static void
27890 draw_row_with_mouse_face (struct window *w, int start_x, struct glyph_row *row,
27891 int start_hpos, int end_hpos,
27892 enum draw_glyphs_face draw)
27893 {
27894 #ifdef HAVE_WINDOW_SYSTEM
27895 if (FRAME_WINDOW_P (XFRAME (w->frame)))
27896 {
27897 draw_glyphs (w, start_x, row, TEXT_AREA, start_hpos, end_hpos, draw, 0);
27898 return;
27899 }
27900 #endif
27901 #if defined (HAVE_GPM) || defined (MSDOS) || defined (WINDOWSNT)
27902 tty_draw_row_with_mouse_face (w, row, start_hpos, end_hpos, draw);
27903 #endif
27904 }
27905
27906 /* Display the active region described by mouse_face_* according to DRAW. */
27907
27908 static void
27909 show_mouse_face (Mouse_HLInfo *hlinfo, enum draw_glyphs_face draw)
27910 {
27911 struct window *w = XWINDOW (hlinfo->mouse_face_window);
27912 struct frame *f = XFRAME (WINDOW_FRAME (w));
27913
27914 if (/* If window is in the process of being destroyed, don't bother
27915 to do anything. */
27916 w->current_matrix != NULL
27917 /* Don't update mouse highlight if hidden. */
27918 && (draw != DRAW_MOUSE_FACE || !hlinfo->mouse_face_hidden)
27919 /* Recognize when we are called to operate on rows that don't exist
27920 anymore. This can happen when a window is split. */
27921 && hlinfo->mouse_face_end_row < w->current_matrix->nrows)
27922 {
27923 int phys_cursor_on_p = w->phys_cursor_on_p;
27924 struct glyph_row *row, *first, *last;
27925
27926 first = MATRIX_ROW (w->current_matrix, hlinfo->mouse_face_beg_row);
27927 last = MATRIX_ROW (w->current_matrix, hlinfo->mouse_face_end_row);
27928
27929 for (row = first; row <= last && row->enabled_p; ++row)
27930 {
27931 int start_hpos, end_hpos, start_x;
27932
27933 /* For all but the first row, the highlight starts at column 0. */
27934 if (row == first)
27935 {
27936 /* R2L rows have BEG and END in reversed order, but the
27937 screen drawing geometry is always left to right. So
27938 we need to mirror the beginning and end of the
27939 highlighted area in R2L rows. */
27940 if (!row->reversed_p)
27941 {
27942 start_hpos = hlinfo->mouse_face_beg_col;
27943 start_x = hlinfo->mouse_face_beg_x;
27944 }
27945 else if (row == last)
27946 {
27947 start_hpos = hlinfo->mouse_face_end_col;
27948 start_x = hlinfo->mouse_face_end_x;
27949 }
27950 else
27951 {
27952 start_hpos = 0;
27953 start_x = 0;
27954 }
27955 }
27956 else if (row->reversed_p && row == last)
27957 {
27958 start_hpos = hlinfo->mouse_face_end_col;
27959 start_x = hlinfo->mouse_face_end_x;
27960 }
27961 else
27962 {
27963 start_hpos = 0;
27964 start_x = 0;
27965 }
27966
27967 if (row == last)
27968 {
27969 if (!row->reversed_p)
27970 end_hpos = hlinfo->mouse_face_end_col;
27971 else if (row == first)
27972 end_hpos = hlinfo->mouse_face_beg_col;
27973 else
27974 {
27975 end_hpos = row->used[TEXT_AREA];
27976 if (draw == DRAW_NORMAL_TEXT)
27977 row->fill_line_p = 1; /* Clear to end of line */
27978 }
27979 }
27980 else if (row->reversed_p && row == first)
27981 end_hpos = hlinfo->mouse_face_beg_col;
27982 else
27983 {
27984 end_hpos = row->used[TEXT_AREA];
27985 if (draw == DRAW_NORMAL_TEXT)
27986 row->fill_line_p = 1; /* Clear to end of line */
27987 }
27988
27989 if (end_hpos > start_hpos)
27990 {
27991 draw_row_with_mouse_face (w, start_x, row,
27992 start_hpos, end_hpos, draw);
27993
27994 row->mouse_face_p
27995 = draw == DRAW_MOUSE_FACE || draw == DRAW_IMAGE_RAISED;
27996 }
27997 }
27998
27999 #ifdef HAVE_WINDOW_SYSTEM
28000 /* When we've written over the cursor, arrange for it to
28001 be displayed again. */
28002 if (FRAME_WINDOW_P (f)
28003 && phys_cursor_on_p && !w->phys_cursor_on_p)
28004 {
28005 int hpos = w->phys_cursor.hpos;
28006
28007 /* When the window is hscrolled, cursor hpos can legitimately be
28008 out of bounds, but we draw the cursor at the corresponding
28009 window margin in that case. */
28010 if (!row->reversed_p && hpos < 0)
28011 hpos = 0;
28012 if (row->reversed_p && hpos >= row->used[TEXT_AREA])
28013 hpos = row->used[TEXT_AREA] - 1;
28014
28015 block_input ();
28016 display_and_set_cursor (w, 1, hpos, w->phys_cursor.vpos,
28017 w->phys_cursor.x, w->phys_cursor.y);
28018 unblock_input ();
28019 }
28020 #endif /* HAVE_WINDOW_SYSTEM */
28021 }
28022
28023 #ifdef HAVE_WINDOW_SYSTEM
28024 /* Change the mouse cursor. */
28025 if (FRAME_WINDOW_P (f) && NILP (do_mouse_tracking))
28026 {
28027 #if ! defined (USE_GTK) && ! defined (HAVE_NS)
28028 if (draw == DRAW_NORMAL_TEXT
28029 && !EQ (hlinfo->mouse_face_window, f->tool_bar_window))
28030 FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->text_cursor);
28031 else
28032 #endif
28033 if (draw == DRAW_MOUSE_FACE)
28034 FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->hand_cursor);
28035 else
28036 FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->nontext_cursor);
28037 }
28038 #endif /* HAVE_WINDOW_SYSTEM */
28039 }
28040
28041 /* EXPORT:
28042 Clear out the mouse-highlighted active region.
28043 Redraw it un-highlighted first. Value is non-zero if mouse
28044 face was actually drawn unhighlighted. */
28045
28046 int
28047 clear_mouse_face (Mouse_HLInfo *hlinfo)
28048 {
28049 int cleared = 0;
28050
28051 if (!hlinfo->mouse_face_hidden && !NILP (hlinfo->mouse_face_window))
28052 {
28053 show_mouse_face (hlinfo, DRAW_NORMAL_TEXT);
28054 cleared = 1;
28055 }
28056
28057 hlinfo->mouse_face_beg_row = hlinfo->mouse_face_beg_col = -1;
28058 hlinfo->mouse_face_end_row = hlinfo->mouse_face_end_col = -1;
28059 hlinfo->mouse_face_window = Qnil;
28060 hlinfo->mouse_face_overlay = Qnil;
28061 return cleared;
28062 }
28063
28064 /* Return true if the coordinates HPOS and VPOS on windows W are
28065 within the mouse face on that window. */
28066 static bool
28067 coords_in_mouse_face_p (struct window *w, int hpos, int vpos)
28068 {
28069 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (XFRAME (w->frame));
28070
28071 /* Quickly resolve the easy cases. */
28072 if (!(WINDOWP (hlinfo->mouse_face_window)
28073 && XWINDOW (hlinfo->mouse_face_window) == w))
28074 return false;
28075 if (vpos < hlinfo->mouse_face_beg_row
28076 || vpos > hlinfo->mouse_face_end_row)
28077 return false;
28078 if (vpos > hlinfo->mouse_face_beg_row
28079 && vpos < hlinfo->mouse_face_end_row)
28080 return true;
28081
28082 if (!MATRIX_ROW (w->current_matrix, vpos)->reversed_p)
28083 {
28084 if (hlinfo->mouse_face_beg_row == hlinfo->mouse_face_end_row)
28085 {
28086 if (hlinfo->mouse_face_beg_col <= hpos && hpos < hlinfo->mouse_face_end_col)
28087 return true;
28088 }
28089 else if ((vpos == hlinfo->mouse_face_beg_row
28090 && hpos >= hlinfo->mouse_face_beg_col)
28091 || (vpos == hlinfo->mouse_face_end_row
28092 && hpos < hlinfo->mouse_face_end_col))
28093 return true;
28094 }
28095 else
28096 {
28097 if (hlinfo->mouse_face_beg_row == hlinfo->mouse_face_end_row)
28098 {
28099 if (hlinfo->mouse_face_end_col < hpos && hpos <= hlinfo->mouse_face_beg_col)
28100 return true;
28101 }
28102 else if ((vpos == hlinfo->mouse_face_beg_row
28103 && hpos <= hlinfo->mouse_face_beg_col)
28104 || (vpos == hlinfo->mouse_face_end_row
28105 && hpos > hlinfo->mouse_face_end_col))
28106 return true;
28107 }
28108 return false;
28109 }
28110
28111
28112 /* EXPORT:
28113 True if physical cursor of window W is within mouse face. */
28114
28115 bool
28116 cursor_in_mouse_face_p (struct window *w)
28117 {
28118 int hpos = w->phys_cursor.hpos;
28119 int vpos = w->phys_cursor.vpos;
28120 struct glyph_row *row = MATRIX_ROW (w->current_matrix, vpos);
28121
28122 /* When the window is hscrolled, cursor hpos can legitimately be out
28123 of bounds, but we draw the cursor at the corresponding window
28124 margin in that case. */
28125 if (!row->reversed_p && hpos < 0)
28126 hpos = 0;
28127 if (row->reversed_p && hpos >= row->used[TEXT_AREA])
28128 hpos = row->used[TEXT_AREA] - 1;
28129
28130 return coords_in_mouse_face_p (w, hpos, vpos);
28131 }
28132
28133
28134 \f
28135 /* Find the glyph rows START_ROW and END_ROW of window W that display
28136 characters between buffer positions START_CHARPOS and END_CHARPOS
28137 (excluding END_CHARPOS). DISP_STRING is a display string that
28138 covers these buffer positions. This is similar to
28139 row_containing_pos, but is more accurate when bidi reordering makes
28140 buffer positions change non-linearly with glyph rows. */
28141 static void
28142 rows_from_pos_range (struct window *w,
28143 ptrdiff_t start_charpos, ptrdiff_t end_charpos,
28144 Lisp_Object disp_string,
28145 struct glyph_row **start, struct glyph_row **end)
28146 {
28147 struct glyph_row *first = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
28148 int last_y = window_text_bottom_y (w);
28149 struct glyph_row *row;
28150
28151 *start = NULL;
28152 *end = NULL;
28153
28154 while (!first->enabled_p
28155 && first < MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w))
28156 first++;
28157
28158 /* Find the START row. */
28159 for (row = first;
28160 row->enabled_p && MATRIX_ROW_BOTTOM_Y (row) <= last_y;
28161 row++)
28162 {
28163 /* A row can potentially be the START row if the range of the
28164 characters it displays intersects the range
28165 [START_CHARPOS..END_CHARPOS). */
28166 if (! ((start_charpos < MATRIX_ROW_START_CHARPOS (row)
28167 && end_charpos < MATRIX_ROW_START_CHARPOS (row))
28168 /* See the commentary in row_containing_pos, for the
28169 explanation of the complicated way to check whether
28170 some position is beyond the end of the characters
28171 displayed by a row. */
28172 || ((start_charpos > MATRIX_ROW_END_CHARPOS (row)
28173 || (start_charpos == MATRIX_ROW_END_CHARPOS (row)
28174 && !row->ends_at_zv_p
28175 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row)))
28176 && (end_charpos > MATRIX_ROW_END_CHARPOS (row)
28177 || (end_charpos == MATRIX_ROW_END_CHARPOS (row)
28178 && !row->ends_at_zv_p
28179 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))))))
28180 {
28181 /* Found a candidate row. Now make sure at least one of the
28182 glyphs it displays has a charpos from the range
28183 [START_CHARPOS..END_CHARPOS).
28184
28185 This is not obvious because bidi reordering could make
28186 buffer positions of a row be 1,2,3,102,101,100, and if we
28187 want to highlight characters in [50..60), we don't want
28188 this row, even though [50..60) does intersect [1..103),
28189 the range of character positions given by the row's start
28190 and end positions. */
28191 struct glyph *g = row->glyphs[TEXT_AREA];
28192 struct glyph *e = g + row->used[TEXT_AREA];
28193
28194 while (g < e)
28195 {
28196 if (((BUFFERP (g->object) || NILP (g->object))
28197 && start_charpos <= g->charpos && g->charpos < end_charpos)
28198 /* A glyph that comes from DISP_STRING is by
28199 definition to be highlighted. */
28200 || EQ (g->object, disp_string))
28201 *start = row;
28202 g++;
28203 }
28204 if (*start)
28205 break;
28206 }
28207 }
28208
28209 /* Find the END row. */
28210 if (!*start
28211 /* If the last row is partially visible, start looking for END
28212 from that row, instead of starting from FIRST. */
28213 && !(row->enabled_p
28214 && row->y < last_y && MATRIX_ROW_BOTTOM_Y (row) > last_y))
28215 row = first;
28216 for ( ; row->enabled_p && MATRIX_ROW_BOTTOM_Y (row) <= last_y; row++)
28217 {
28218 struct glyph_row *next = row + 1;
28219 ptrdiff_t next_start = MATRIX_ROW_START_CHARPOS (next);
28220
28221 if (!next->enabled_p
28222 || next >= MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w)
28223 /* The first row >= START whose range of displayed characters
28224 does NOT intersect the range [START_CHARPOS..END_CHARPOS]
28225 is the row END + 1. */
28226 || (start_charpos < next_start
28227 && end_charpos < next_start)
28228 || ((start_charpos > MATRIX_ROW_END_CHARPOS (next)
28229 || (start_charpos == MATRIX_ROW_END_CHARPOS (next)
28230 && !next->ends_at_zv_p
28231 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (next)))
28232 && (end_charpos > MATRIX_ROW_END_CHARPOS (next)
28233 || (end_charpos == MATRIX_ROW_END_CHARPOS (next)
28234 && !next->ends_at_zv_p
28235 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (next)))))
28236 {
28237 *end = row;
28238 break;
28239 }
28240 else
28241 {
28242 /* If the next row's edges intersect [START_CHARPOS..END_CHARPOS],
28243 but none of the characters it displays are in the range, it is
28244 also END + 1. */
28245 struct glyph *g = next->glyphs[TEXT_AREA];
28246 struct glyph *s = g;
28247 struct glyph *e = g + next->used[TEXT_AREA];
28248
28249 while (g < e)
28250 {
28251 if (((BUFFERP (g->object) || NILP (g->object))
28252 && ((start_charpos <= g->charpos && g->charpos < end_charpos)
28253 /* If the buffer position of the first glyph in
28254 the row is equal to END_CHARPOS, it means
28255 the last character to be highlighted is the
28256 newline of ROW, and we must consider NEXT as
28257 END, not END+1. */
28258 || (((!next->reversed_p && g == s)
28259 || (next->reversed_p && g == e - 1))
28260 && (g->charpos == end_charpos
28261 /* Special case for when NEXT is an
28262 empty line at ZV. */
28263 || (g->charpos == -1
28264 && !row->ends_at_zv_p
28265 && next_start == end_charpos)))))
28266 /* A glyph that comes from DISP_STRING is by
28267 definition to be highlighted. */
28268 || EQ (g->object, disp_string))
28269 break;
28270 g++;
28271 }
28272 if (g == e)
28273 {
28274 *end = row;
28275 break;
28276 }
28277 /* The first row that ends at ZV must be the last to be
28278 highlighted. */
28279 else if (next->ends_at_zv_p)
28280 {
28281 *end = next;
28282 break;
28283 }
28284 }
28285 }
28286 }
28287
28288 /* This function sets the mouse_face_* elements of HLINFO, assuming
28289 the mouse cursor is on a glyph with buffer charpos MOUSE_CHARPOS in
28290 window WINDOW. START_CHARPOS and END_CHARPOS are buffer positions
28291 for the overlay or run of text properties specifying the mouse
28292 face. BEFORE_STRING and AFTER_STRING, if non-nil, are a
28293 before-string and after-string that must also be highlighted.
28294 DISP_STRING, if non-nil, is a display string that may cover some
28295 or all of the highlighted text. */
28296
28297 static void
28298 mouse_face_from_buffer_pos (Lisp_Object window,
28299 Mouse_HLInfo *hlinfo,
28300 ptrdiff_t mouse_charpos,
28301 ptrdiff_t start_charpos,
28302 ptrdiff_t end_charpos,
28303 Lisp_Object before_string,
28304 Lisp_Object after_string,
28305 Lisp_Object disp_string)
28306 {
28307 struct window *w = XWINDOW (window);
28308 struct glyph_row *first = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
28309 struct glyph_row *r1, *r2;
28310 struct glyph *glyph, *end;
28311 ptrdiff_t ignore, pos;
28312 int x;
28313
28314 eassert (NILP (disp_string) || STRINGP (disp_string));
28315 eassert (NILP (before_string) || STRINGP (before_string));
28316 eassert (NILP (after_string) || STRINGP (after_string));
28317
28318 /* Find the rows corresponding to START_CHARPOS and END_CHARPOS. */
28319 rows_from_pos_range (w, start_charpos, end_charpos, disp_string, &r1, &r2);
28320 if (r1 == NULL)
28321 r1 = MATRIX_ROW (w->current_matrix, w->window_end_vpos);
28322 /* If the before-string or display-string contains newlines,
28323 rows_from_pos_range skips to its last row. Move back. */
28324 if (!NILP (before_string) || !NILP (disp_string))
28325 {
28326 struct glyph_row *prev;
28327 while ((prev = r1 - 1, prev >= first)
28328 && MATRIX_ROW_END_CHARPOS (prev) == start_charpos
28329 && prev->used[TEXT_AREA] > 0)
28330 {
28331 struct glyph *beg = prev->glyphs[TEXT_AREA];
28332 glyph = beg + prev->used[TEXT_AREA];
28333 while (--glyph >= beg && NILP (glyph->object));
28334 if (glyph < beg
28335 || !(EQ (glyph->object, before_string)
28336 || EQ (glyph->object, disp_string)))
28337 break;
28338 r1 = prev;
28339 }
28340 }
28341 if (r2 == NULL)
28342 {
28343 r2 = MATRIX_ROW (w->current_matrix, w->window_end_vpos);
28344 hlinfo->mouse_face_past_end = 1;
28345 }
28346 else if (!NILP (after_string))
28347 {
28348 /* If the after-string has newlines, advance to its last row. */
28349 struct glyph_row *next;
28350 struct glyph_row *last
28351 = MATRIX_ROW (w->current_matrix, w->window_end_vpos);
28352
28353 for (next = r2 + 1;
28354 next <= last
28355 && next->used[TEXT_AREA] > 0
28356 && EQ (next->glyphs[TEXT_AREA]->object, after_string);
28357 ++next)
28358 r2 = next;
28359 }
28360 /* The rest of the display engine assumes that mouse_face_beg_row is
28361 either above mouse_face_end_row or identical to it. But with
28362 bidi-reordered continued lines, the row for START_CHARPOS could
28363 be below the row for END_CHARPOS. If so, swap the rows and store
28364 them in correct order. */
28365 if (r1->y > r2->y)
28366 {
28367 struct glyph_row *tem = r2;
28368
28369 r2 = r1;
28370 r1 = tem;
28371 }
28372
28373 hlinfo->mouse_face_beg_row = MATRIX_ROW_VPOS (r1, w->current_matrix);
28374 hlinfo->mouse_face_end_row = MATRIX_ROW_VPOS (r2, w->current_matrix);
28375
28376 /* For a bidi-reordered row, the positions of BEFORE_STRING,
28377 AFTER_STRING, DISP_STRING, START_CHARPOS, and END_CHARPOS
28378 could be anywhere in the row and in any order. The strategy
28379 below is to find the leftmost and the rightmost glyph that
28380 belongs to either of these 3 strings, or whose position is
28381 between START_CHARPOS and END_CHARPOS, and highlight all the
28382 glyphs between those two. This may cover more than just the text
28383 between START_CHARPOS and END_CHARPOS if the range of characters
28384 strides the bidi level boundary, e.g. if the beginning is in R2L
28385 text while the end is in L2R text or vice versa. */
28386 if (!r1->reversed_p)
28387 {
28388 /* This row is in a left to right paragraph. Scan it left to
28389 right. */
28390 glyph = r1->glyphs[TEXT_AREA];
28391 end = glyph + r1->used[TEXT_AREA];
28392 x = r1->x;
28393
28394 /* Skip truncation glyphs at the start of the glyph row. */
28395 if (MATRIX_ROW_DISPLAYS_TEXT_P (r1))
28396 for (; glyph < end
28397 && NILP (glyph->object)
28398 && glyph->charpos < 0;
28399 ++glyph)
28400 x += glyph->pixel_width;
28401
28402 /* Scan the glyph row, looking for BEFORE_STRING, AFTER_STRING,
28403 or DISP_STRING, and the first glyph from buffer whose
28404 position is between START_CHARPOS and END_CHARPOS. */
28405 for (; glyph < end
28406 && !NILP (glyph->object)
28407 && !EQ (glyph->object, disp_string)
28408 && !(BUFFERP (glyph->object)
28409 && (glyph->charpos >= start_charpos
28410 && glyph->charpos < end_charpos));
28411 ++glyph)
28412 {
28413 /* BEFORE_STRING or AFTER_STRING are only relevant if they
28414 are present at buffer positions between START_CHARPOS and
28415 END_CHARPOS, or if they come from an overlay. */
28416 if (EQ (glyph->object, before_string))
28417 {
28418 pos = string_buffer_position (before_string,
28419 start_charpos);
28420 /* If pos == 0, it means before_string came from an
28421 overlay, not from a buffer position. */
28422 if (!pos || (pos >= start_charpos && pos < end_charpos))
28423 break;
28424 }
28425 else if (EQ (glyph->object, after_string))
28426 {
28427 pos = string_buffer_position (after_string, end_charpos);
28428 if (!pos || (pos >= start_charpos && pos < end_charpos))
28429 break;
28430 }
28431 x += glyph->pixel_width;
28432 }
28433 hlinfo->mouse_face_beg_x = x;
28434 hlinfo->mouse_face_beg_col = glyph - r1->glyphs[TEXT_AREA];
28435 }
28436 else
28437 {
28438 /* This row is in a right to left paragraph. Scan it right to
28439 left. */
28440 struct glyph *g;
28441
28442 end = r1->glyphs[TEXT_AREA] - 1;
28443 glyph = end + r1->used[TEXT_AREA];
28444
28445 /* Skip truncation glyphs at the start of the glyph row. */
28446 if (MATRIX_ROW_DISPLAYS_TEXT_P (r1))
28447 for (; glyph > end
28448 && NILP (glyph->object)
28449 && glyph->charpos < 0;
28450 --glyph)
28451 ;
28452
28453 /* Scan the glyph row, looking for BEFORE_STRING, AFTER_STRING,
28454 or DISP_STRING, and the first glyph from buffer whose
28455 position is between START_CHARPOS and END_CHARPOS. */
28456 for (; glyph > end
28457 && !NILP (glyph->object)
28458 && !EQ (glyph->object, disp_string)
28459 && !(BUFFERP (glyph->object)
28460 && (glyph->charpos >= start_charpos
28461 && glyph->charpos < end_charpos));
28462 --glyph)
28463 {
28464 /* BEFORE_STRING or AFTER_STRING are only relevant if they
28465 are present at buffer positions between START_CHARPOS and
28466 END_CHARPOS, or if they come from an overlay. */
28467 if (EQ (glyph->object, before_string))
28468 {
28469 pos = string_buffer_position (before_string, start_charpos);
28470 /* If pos == 0, it means before_string came from an
28471 overlay, not from a buffer position. */
28472 if (!pos || (pos >= start_charpos && pos < end_charpos))
28473 break;
28474 }
28475 else if (EQ (glyph->object, after_string))
28476 {
28477 pos = string_buffer_position (after_string, end_charpos);
28478 if (!pos || (pos >= start_charpos && pos < end_charpos))
28479 break;
28480 }
28481 }
28482
28483 glyph++; /* first glyph to the right of the highlighted area */
28484 for (g = r1->glyphs[TEXT_AREA], x = r1->x; g < glyph; g++)
28485 x += g->pixel_width;
28486 hlinfo->mouse_face_beg_x = x;
28487 hlinfo->mouse_face_beg_col = glyph - r1->glyphs[TEXT_AREA];
28488 }
28489
28490 /* If the highlight ends in a different row, compute GLYPH and END
28491 for the end row. Otherwise, reuse the values computed above for
28492 the row where the highlight begins. */
28493 if (r2 != r1)
28494 {
28495 if (!r2->reversed_p)
28496 {
28497 glyph = r2->glyphs[TEXT_AREA];
28498 end = glyph + r2->used[TEXT_AREA];
28499 x = r2->x;
28500 }
28501 else
28502 {
28503 end = r2->glyphs[TEXT_AREA] - 1;
28504 glyph = end + r2->used[TEXT_AREA];
28505 }
28506 }
28507
28508 if (!r2->reversed_p)
28509 {
28510 /* Skip truncation and continuation glyphs near the end of the
28511 row, and also blanks and stretch glyphs inserted by
28512 extend_face_to_end_of_line. */
28513 while (end > glyph
28514 && NILP ((end - 1)->object))
28515 --end;
28516 /* Scan the rest of the glyph row from the end, looking for the
28517 first glyph that comes from BEFORE_STRING, AFTER_STRING, or
28518 DISP_STRING, or whose position is between START_CHARPOS
28519 and END_CHARPOS */
28520 for (--end;
28521 end > glyph
28522 && !NILP (end->object)
28523 && !EQ (end->object, disp_string)
28524 && !(BUFFERP (end->object)
28525 && (end->charpos >= start_charpos
28526 && end->charpos < end_charpos));
28527 --end)
28528 {
28529 /* BEFORE_STRING or AFTER_STRING are only relevant if they
28530 are present at buffer positions between START_CHARPOS and
28531 END_CHARPOS, or if they come from an overlay. */
28532 if (EQ (end->object, before_string))
28533 {
28534 pos = string_buffer_position (before_string, start_charpos);
28535 if (!pos || (pos >= start_charpos && pos < end_charpos))
28536 break;
28537 }
28538 else if (EQ (end->object, after_string))
28539 {
28540 pos = string_buffer_position (after_string, end_charpos);
28541 if (!pos || (pos >= start_charpos && pos < end_charpos))
28542 break;
28543 }
28544 }
28545 /* Find the X coordinate of the last glyph to be highlighted. */
28546 for (; glyph <= end; ++glyph)
28547 x += glyph->pixel_width;
28548
28549 hlinfo->mouse_face_end_x = x;
28550 hlinfo->mouse_face_end_col = glyph - r2->glyphs[TEXT_AREA];
28551 }
28552 else
28553 {
28554 /* Skip truncation and continuation glyphs near the end of the
28555 row, and also blanks and stretch glyphs inserted by
28556 extend_face_to_end_of_line. */
28557 x = r2->x;
28558 end++;
28559 while (end < glyph
28560 && NILP (end->object))
28561 {
28562 x += end->pixel_width;
28563 ++end;
28564 }
28565 /* Scan the rest of the glyph row from the end, looking for the
28566 first glyph that comes from BEFORE_STRING, AFTER_STRING, or
28567 DISP_STRING, or whose position is between START_CHARPOS
28568 and END_CHARPOS */
28569 for ( ;
28570 end < glyph
28571 && !NILP (end->object)
28572 && !EQ (end->object, disp_string)
28573 && !(BUFFERP (end->object)
28574 && (end->charpos >= start_charpos
28575 && end->charpos < end_charpos));
28576 ++end)
28577 {
28578 /* BEFORE_STRING or AFTER_STRING are only relevant if they
28579 are present at buffer positions between START_CHARPOS and
28580 END_CHARPOS, or if they come from an overlay. */
28581 if (EQ (end->object, before_string))
28582 {
28583 pos = string_buffer_position (before_string, start_charpos);
28584 if (!pos || (pos >= start_charpos && pos < end_charpos))
28585 break;
28586 }
28587 else if (EQ (end->object, after_string))
28588 {
28589 pos = string_buffer_position (after_string, end_charpos);
28590 if (!pos || (pos >= start_charpos && pos < end_charpos))
28591 break;
28592 }
28593 x += end->pixel_width;
28594 }
28595 /* If we exited the above loop because we arrived at the last
28596 glyph of the row, and its buffer position is still not in
28597 range, it means the last character in range is the preceding
28598 newline. Bump the end column and x values to get past the
28599 last glyph. */
28600 if (end == glyph
28601 && BUFFERP (end->object)
28602 && (end->charpos < start_charpos
28603 || end->charpos >= end_charpos))
28604 {
28605 x += end->pixel_width;
28606 ++end;
28607 }
28608 hlinfo->mouse_face_end_x = x;
28609 hlinfo->mouse_face_end_col = end - r2->glyphs[TEXT_AREA];
28610 }
28611
28612 hlinfo->mouse_face_window = window;
28613 hlinfo->mouse_face_face_id
28614 = face_at_buffer_position (w, mouse_charpos, &ignore,
28615 mouse_charpos + 1,
28616 !hlinfo->mouse_face_hidden, -1);
28617 show_mouse_face (hlinfo, DRAW_MOUSE_FACE);
28618 }
28619
28620 /* The following function is not used anymore (replaced with
28621 mouse_face_from_string_pos), but I leave it here for the time
28622 being, in case someone would. */
28623
28624 #if 0 /* not used */
28625
28626 /* Find the position of the glyph for position POS in OBJECT in
28627 window W's current matrix, and return in *X, *Y the pixel
28628 coordinates, and return in *HPOS, *VPOS the column/row of the glyph.
28629
28630 RIGHT_P non-zero means return the position of the right edge of the
28631 glyph, RIGHT_P zero means return the left edge position.
28632
28633 If no glyph for POS exists in the matrix, return the position of
28634 the glyph with the next smaller position that is in the matrix, if
28635 RIGHT_P is zero. If RIGHT_P is non-zero, and no glyph for POS
28636 exists in the matrix, return the position of the glyph with the
28637 next larger position in OBJECT.
28638
28639 Value is non-zero if a glyph was found. */
28640
28641 static int
28642 fast_find_string_pos (struct window *w, ptrdiff_t pos, Lisp_Object object,
28643 int *hpos, int *vpos, int *x, int *y, int right_p)
28644 {
28645 int yb = window_text_bottom_y (w);
28646 struct glyph_row *r;
28647 struct glyph *best_glyph = NULL;
28648 struct glyph_row *best_row = NULL;
28649 int best_x = 0;
28650
28651 for (r = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
28652 r->enabled_p && r->y < yb;
28653 ++r)
28654 {
28655 struct glyph *g = r->glyphs[TEXT_AREA];
28656 struct glyph *e = g + r->used[TEXT_AREA];
28657 int gx;
28658
28659 for (gx = r->x; g < e; gx += g->pixel_width, ++g)
28660 if (EQ (g->object, object))
28661 {
28662 if (g->charpos == pos)
28663 {
28664 best_glyph = g;
28665 best_x = gx;
28666 best_row = r;
28667 goto found;
28668 }
28669 else if (best_glyph == NULL
28670 || ((eabs (g->charpos - pos)
28671 < eabs (best_glyph->charpos - pos))
28672 && (right_p
28673 ? g->charpos < pos
28674 : g->charpos > pos)))
28675 {
28676 best_glyph = g;
28677 best_x = gx;
28678 best_row = r;
28679 }
28680 }
28681 }
28682
28683 found:
28684
28685 if (best_glyph)
28686 {
28687 *x = best_x;
28688 *hpos = best_glyph - best_row->glyphs[TEXT_AREA];
28689
28690 if (right_p)
28691 {
28692 *x += best_glyph->pixel_width;
28693 ++*hpos;
28694 }
28695
28696 *y = best_row->y;
28697 *vpos = MATRIX_ROW_VPOS (best_row, w->current_matrix);
28698 }
28699
28700 return best_glyph != NULL;
28701 }
28702 #endif /* not used */
28703
28704 /* Find the positions of the first and the last glyphs in window W's
28705 current matrix that occlude positions [STARTPOS..ENDPOS) in OBJECT
28706 (assumed to be a string), and return in HLINFO's mouse_face_*
28707 members the pixel and column/row coordinates of those glyphs. */
28708
28709 static void
28710 mouse_face_from_string_pos (struct window *w, Mouse_HLInfo *hlinfo,
28711 Lisp_Object object,
28712 ptrdiff_t startpos, ptrdiff_t endpos)
28713 {
28714 int yb = window_text_bottom_y (w);
28715 struct glyph_row *r;
28716 struct glyph *g, *e;
28717 int gx;
28718 int found = 0;
28719
28720 /* Find the glyph row with at least one position in the range
28721 [STARTPOS..ENDPOS), and the first glyph in that row whose
28722 position belongs to that range. */
28723 for (r = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
28724 r->enabled_p && r->y < yb;
28725 ++r)
28726 {
28727 if (!r->reversed_p)
28728 {
28729 g = r->glyphs[TEXT_AREA];
28730 e = g + r->used[TEXT_AREA];
28731 for (gx = r->x; g < e; gx += g->pixel_width, ++g)
28732 if (EQ (g->object, object)
28733 && startpos <= g->charpos && g->charpos < endpos)
28734 {
28735 hlinfo->mouse_face_beg_row
28736 = MATRIX_ROW_VPOS (r, w->current_matrix);
28737 hlinfo->mouse_face_beg_col = g - r->glyphs[TEXT_AREA];
28738 hlinfo->mouse_face_beg_x = gx;
28739 found = 1;
28740 break;
28741 }
28742 }
28743 else
28744 {
28745 struct glyph *g1;
28746
28747 e = r->glyphs[TEXT_AREA];
28748 g = e + r->used[TEXT_AREA];
28749 for ( ; g > e; --g)
28750 if (EQ ((g-1)->object, object)
28751 && startpos <= (g-1)->charpos && (g-1)->charpos < endpos)
28752 {
28753 hlinfo->mouse_face_beg_row
28754 = MATRIX_ROW_VPOS (r, w->current_matrix);
28755 hlinfo->mouse_face_beg_col = g - r->glyphs[TEXT_AREA];
28756 for (gx = r->x, g1 = r->glyphs[TEXT_AREA]; g1 < g; ++g1)
28757 gx += g1->pixel_width;
28758 hlinfo->mouse_face_beg_x = gx;
28759 found = 1;
28760 break;
28761 }
28762 }
28763 if (found)
28764 break;
28765 }
28766
28767 if (!found)
28768 return;
28769
28770 /* Starting with the next row, look for the first row which does NOT
28771 include any glyphs whose positions are in the range. */
28772 for (++r; r->enabled_p && r->y < yb; ++r)
28773 {
28774 g = r->glyphs[TEXT_AREA];
28775 e = g + r->used[TEXT_AREA];
28776 found = 0;
28777 for ( ; g < e; ++g)
28778 if (EQ (g->object, object)
28779 && startpos <= g->charpos && g->charpos < endpos)
28780 {
28781 found = 1;
28782 break;
28783 }
28784 if (!found)
28785 break;
28786 }
28787
28788 /* The highlighted region ends on the previous row. */
28789 r--;
28790
28791 /* Set the end row. */
28792 hlinfo->mouse_face_end_row = MATRIX_ROW_VPOS (r, w->current_matrix);
28793
28794 /* Compute and set the end column and the end column's horizontal
28795 pixel coordinate. */
28796 if (!r->reversed_p)
28797 {
28798 g = r->glyphs[TEXT_AREA];
28799 e = g + r->used[TEXT_AREA];
28800 for ( ; e > g; --e)
28801 if (EQ ((e-1)->object, object)
28802 && startpos <= (e-1)->charpos && (e-1)->charpos < endpos)
28803 break;
28804 hlinfo->mouse_face_end_col = e - g;
28805
28806 for (gx = r->x; g < e; ++g)
28807 gx += g->pixel_width;
28808 hlinfo->mouse_face_end_x = gx;
28809 }
28810 else
28811 {
28812 e = r->glyphs[TEXT_AREA];
28813 g = e + r->used[TEXT_AREA];
28814 for (gx = r->x ; e < g; ++e)
28815 {
28816 if (EQ (e->object, object)
28817 && startpos <= e->charpos && e->charpos < endpos)
28818 break;
28819 gx += e->pixel_width;
28820 }
28821 hlinfo->mouse_face_end_col = e - r->glyphs[TEXT_AREA];
28822 hlinfo->mouse_face_end_x = gx;
28823 }
28824 }
28825
28826 #ifdef HAVE_WINDOW_SYSTEM
28827
28828 /* See if position X, Y is within a hot-spot of an image. */
28829
28830 static int
28831 on_hot_spot_p (Lisp_Object hot_spot, int x, int y)
28832 {
28833 if (!CONSP (hot_spot))
28834 return 0;
28835
28836 if (EQ (XCAR (hot_spot), Qrect))
28837 {
28838 /* CDR is (Top-Left . Bottom-Right) = ((x0 . y0) . (x1 . y1)) */
28839 Lisp_Object rect = XCDR (hot_spot);
28840 Lisp_Object tem;
28841 if (!CONSP (rect))
28842 return 0;
28843 if (!CONSP (XCAR (rect)))
28844 return 0;
28845 if (!CONSP (XCDR (rect)))
28846 return 0;
28847 if (!(tem = XCAR (XCAR (rect)), INTEGERP (tem) && x >= XINT (tem)))
28848 return 0;
28849 if (!(tem = XCDR (XCAR (rect)), INTEGERP (tem) && y >= XINT (tem)))
28850 return 0;
28851 if (!(tem = XCAR (XCDR (rect)), INTEGERP (tem) && x <= XINT (tem)))
28852 return 0;
28853 if (!(tem = XCDR (XCDR (rect)), INTEGERP (tem) && y <= XINT (tem)))
28854 return 0;
28855 return 1;
28856 }
28857 else if (EQ (XCAR (hot_spot), Qcircle))
28858 {
28859 /* CDR is (Center . Radius) = ((x0 . y0) . r) */
28860 Lisp_Object circ = XCDR (hot_spot);
28861 Lisp_Object lr, lx0, ly0;
28862 if (CONSP (circ)
28863 && CONSP (XCAR (circ))
28864 && (lr = XCDR (circ), INTEGERP (lr) || FLOATP (lr))
28865 && (lx0 = XCAR (XCAR (circ)), INTEGERP (lx0))
28866 && (ly0 = XCDR (XCAR (circ)), INTEGERP (ly0)))
28867 {
28868 double r = XFLOATINT (lr);
28869 double dx = XINT (lx0) - x;
28870 double dy = XINT (ly0) - y;
28871 return (dx * dx + dy * dy <= r * r);
28872 }
28873 }
28874 else if (EQ (XCAR (hot_spot), Qpoly))
28875 {
28876 /* CDR is [x0 y0 x1 y1 x2 y2 ...x(n-1) y(n-1)] */
28877 if (VECTORP (XCDR (hot_spot)))
28878 {
28879 struct Lisp_Vector *v = XVECTOR (XCDR (hot_spot));
28880 Lisp_Object *poly = v->contents;
28881 ptrdiff_t n = v->header.size;
28882 ptrdiff_t i;
28883 int inside = 0;
28884 Lisp_Object lx, ly;
28885 int x0, y0;
28886
28887 /* Need an even number of coordinates, and at least 3 edges. */
28888 if (n < 6 || n & 1)
28889 return 0;
28890
28891 /* Count edge segments intersecting line from (X,Y) to (X,infinity).
28892 If count is odd, we are inside polygon. Pixels on edges
28893 may or may not be included depending on actual geometry of the
28894 polygon. */
28895 if ((lx = poly[n-2], !INTEGERP (lx))
28896 || (ly = poly[n-1], !INTEGERP (lx)))
28897 return 0;
28898 x0 = XINT (lx), y0 = XINT (ly);
28899 for (i = 0; i < n; i += 2)
28900 {
28901 int x1 = x0, y1 = y0;
28902 if ((lx = poly[i], !INTEGERP (lx))
28903 || (ly = poly[i+1], !INTEGERP (ly)))
28904 return 0;
28905 x0 = XINT (lx), y0 = XINT (ly);
28906
28907 /* Does this segment cross the X line? */
28908 if (x0 >= x)
28909 {
28910 if (x1 >= x)
28911 continue;
28912 }
28913 else if (x1 < x)
28914 continue;
28915 if (y > y0 && y > y1)
28916 continue;
28917 if (y < y0 + ((y1 - y0) * (x - x0)) / (x1 - x0))
28918 inside = !inside;
28919 }
28920 return inside;
28921 }
28922 }
28923 return 0;
28924 }
28925
28926 Lisp_Object
28927 find_hot_spot (Lisp_Object map, int x, int y)
28928 {
28929 while (CONSP (map))
28930 {
28931 if (CONSP (XCAR (map))
28932 && on_hot_spot_p (XCAR (XCAR (map)), x, y))
28933 return XCAR (map);
28934 map = XCDR (map);
28935 }
28936
28937 return Qnil;
28938 }
28939
28940 DEFUN ("lookup-image-map", Flookup_image_map, Slookup_image_map,
28941 3, 3, 0,
28942 doc: /* Lookup in image map MAP coordinates X and Y.
28943 An image map is an alist where each element has the format (AREA ID PLIST).
28944 An AREA is specified as either a rectangle, a circle, or a polygon:
28945 A rectangle is a cons (rect . ((x0 . y0) . (x1 . y1))) specifying the
28946 pixel coordinates of the upper left and bottom right corners.
28947 A circle is a cons (circle . ((x0 . y0) . r)) specifying the center
28948 and the radius of the circle; r may be a float or integer.
28949 A polygon is a cons (poly . [x0 y0 x1 y1 ...]) where each pair in the
28950 vector describes one corner in the polygon.
28951 Returns the alist element for the first matching AREA in MAP. */)
28952 (Lisp_Object map, Lisp_Object x, Lisp_Object y)
28953 {
28954 if (NILP (map))
28955 return Qnil;
28956
28957 CHECK_NUMBER (x);
28958 CHECK_NUMBER (y);
28959
28960 return find_hot_spot (map,
28961 clip_to_bounds (INT_MIN, XINT (x), INT_MAX),
28962 clip_to_bounds (INT_MIN, XINT (y), INT_MAX));
28963 }
28964
28965
28966 /* Display frame CURSOR, optionally using shape defined by POINTER. */
28967 static void
28968 define_frame_cursor1 (struct frame *f, Cursor cursor, Lisp_Object pointer)
28969 {
28970 /* Do not change cursor shape while dragging mouse. */
28971 if (!NILP (do_mouse_tracking))
28972 return;
28973
28974 if (!NILP (pointer))
28975 {
28976 if (EQ (pointer, Qarrow))
28977 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
28978 else if (EQ (pointer, Qhand))
28979 cursor = FRAME_X_OUTPUT (f)->hand_cursor;
28980 else if (EQ (pointer, Qtext))
28981 cursor = FRAME_X_OUTPUT (f)->text_cursor;
28982 else if (EQ (pointer, intern ("hdrag")))
28983 cursor = FRAME_X_OUTPUT (f)->horizontal_drag_cursor;
28984 else if (EQ (pointer, intern ("nhdrag")))
28985 cursor = FRAME_X_OUTPUT (f)->vertical_drag_cursor;
28986 #ifdef HAVE_X_WINDOWS
28987 else if (EQ (pointer, intern ("vdrag")))
28988 cursor = FRAME_DISPLAY_INFO (f)->vertical_scroll_bar_cursor;
28989 #endif
28990 else if (EQ (pointer, intern ("hourglass")))
28991 cursor = FRAME_X_OUTPUT (f)->hourglass_cursor;
28992 else if (EQ (pointer, Qmodeline))
28993 cursor = FRAME_X_OUTPUT (f)->modeline_cursor;
28994 else
28995 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
28996 }
28997
28998 if (cursor != No_Cursor)
28999 FRAME_RIF (f)->define_frame_cursor (f, cursor);
29000 }
29001
29002 #endif /* HAVE_WINDOW_SYSTEM */
29003
29004 /* Take proper action when mouse has moved to the mode or header line
29005 or marginal area AREA of window W, x-position X and y-position Y.
29006 X is relative to the start of the text display area of W, so the
29007 width of bitmap areas and scroll bars must be subtracted to get a
29008 position relative to the start of the mode line. */
29009
29010 static void
29011 note_mode_line_or_margin_highlight (Lisp_Object window, int x, int y,
29012 enum window_part area)
29013 {
29014 struct window *w = XWINDOW (window);
29015 struct frame *f = XFRAME (w->frame);
29016 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
29017 #ifdef HAVE_WINDOW_SYSTEM
29018 Display_Info *dpyinfo;
29019 #endif
29020 Cursor cursor = No_Cursor;
29021 Lisp_Object pointer = Qnil;
29022 int dx, dy, width, height;
29023 ptrdiff_t charpos;
29024 Lisp_Object string, object = Qnil;
29025 Lisp_Object pos IF_LINT (= Qnil), help;
29026
29027 Lisp_Object mouse_face;
29028 int original_x_pixel = x;
29029 struct glyph * glyph = NULL, * row_start_glyph = NULL;
29030 struct glyph_row *row IF_LINT (= 0);
29031
29032 if (area == ON_MODE_LINE || area == ON_HEADER_LINE)
29033 {
29034 int x0;
29035 struct glyph *end;
29036
29037 /* Kludge alert: mode_line_string takes X/Y in pixels, but
29038 returns them in row/column units! */
29039 string = mode_line_string (w, area, &x, &y, &charpos,
29040 &object, &dx, &dy, &width, &height);
29041
29042 row = (area == ON_MODE_LINE
29043 ? MATRIX_MODE_LINE_ROW (w->current_matrix)
29044 : MATRIX_HEADER_LINE_ROW (w->current_matrix));
29045
29046 /* Find the glyph under the mouse pointer. */
29047 if (row->mode_line_p && row->enabled_p)
29048 {
29049 glyph = row_start_glyph = row->glyphs[TEXT_AREA];
29050 end = glyph + row->used[TEXT_AREA];
29051
29052 for (x0 = original_x_pixel;
29053 glyph < end && x0 >= glyph->pixel_width;
29054 ++glyph)
29055 x0 -= glyph->pixel_width;
29056
29057 if (glyph >= end)
29058 glyph = NULL;
29059 }
29060 }
29061 else
29062 {
29063 x -= WINDOW_LEFT_SCROLL_BAR_AREA_WIDTH (w);
29064 /* Kludge alert: marginal_area_string takes X/Y in pixels, but
29065 returns them in row/column units! */
29066 string = marginal_area_string (w, area, &x, &y, &charpos,
29067 &object, &dx, &dy, &width, &height);
29068 }
29069
29070 help = Qnil;
29071
29072 #ifdef HAVE_WINDOW_SYSTEM
29073 if (IMAGEP (object))
29074 {
29075 Lisp_Object image_map, hotspot;
29076 if ((image_map = Fplist_get (XCDR (object), QCmap),
29077 !NILP (image_map))
29078 && (hotspot = find_hot_spot (image_map, dx, dy),
29079 CONSP (hotspot))
29080 && (hotspot = XCDR (hotspot), CONSP (hotspot)))
29081 {
29082 Lisp_Object plist;
29083
29084 /* Could check XCAR (hotspot) to see if we enter/leave this hot-spot.
29085 If so, we could look for mouse-enter, mouse-leave
29086 properties in PLIST (and do something...). */
29087 hotspot = XCDR (hotspot);
29088 if (CONSP (hotspot)
29089 && (plist = XCAR (hotspot), CONSP (plist)))
29090 {
29091 pointer = Fplist_get (plist, Qpointer);
29092 if (NILP (pointer))
29093 pointer = Qhand;
29094 help = Fplist_get (plist, Qhelp_echo);
29095 if (!NILP (help))
29096 {
29097 help_echo_string = help;
29098 XSETWINDOW (help_echo_window, w);
29099 help_echo_object = w->contents;
29100 help_echo_pos = charpos;
29101 }
29102 }
29103 }
29104 if (NILP (pointer))
29105 pointer = Fplist_get (XCDR (object), QCpointer);
29106 }
29107 #endif /* HAVE_WINDOW_SYSTEM */
29108
29109 if (STRINGP (string))
29110 pos = make_number (charpos);
29111
29112 /* Set the help text and mouse pointer. If the mouse is on a part
29113 of the mode line without any text (e.g. past the right edge of
29114 the mode line text), use the default help text and pointer. */
29115 if (STRINGP (string) || area == ON_MODE_LINE)
29116 {
29117 /* Arrange to display the help by setting the global variables
29118 help_echo_string, help_echo_object, and help_echo_pos. */
29119 if (NILP (help))
29120 {
29121 if (STRINGP (string))
29122 help = Fget_text_property (pos, Qhelp_echo, string);
29123
29124 if (!NILP (help))
29125 {
29126 help_echo_string = help;
29127 XSETWINDOW (help_echo_window, w);
29128 help_echo_object = string;
29129 help_echo_pos = charpos;
29130 }
29131 else if (area == ON_MODE_LINE)
29132 {
29133 Lisp_Object default_help
29134 = buffer_local_value (Qmode_line_default_help_echo,
29135 w->contents);
29136
29137 if (STRINGP (default_help))
29138 {
29139 help_echo_string = default_help;
29140 XSETWINDOW (help_echo_window, w);
29141 help_echo_object = Qnil;
29142 help_echo_pos = -1;
29143 }
29144 }
29145 }
29146
29147 #ifdef HAVE_WINDOW_SYSTEM
29148 /* Change the mouse pointer according to what is under it. */
29149 if (FRAME_WINDOW_P (f))
29150 {
29151 bool draggable = (! WINDOW_BOTTOMMOST_P (w)
29152 || minibuf_level
29153 || NILP (Vresize_mini_windows));
29154
29155 dpyinfo = FRAME_DISPLAY_INFO (f);
29156 if (STRINGP (string))
29157 {
29158 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
29159
29160 if (NILP (pointer))
29161 pointer = Fget_text_property (pos, Qpointer, string);
29162
29163 /* Change the mouse pointer according to what is under X/Y. */
29164 if (NILP (pointer)
29165 && ((area == ON_MODE_LINE) || (area == ON_HEADER_LINE)))
29166 {
29167 Lisp_Object map;
29168 map = Fget_text_property (pos, Qlocal_map, string);
29169 if (!KEYMAPP (map))
29170 map = Fget_text_property (pos, Qkeymap, string);
29171 if (!KEYMAPP (map) && draggable)
29172 cursor = dpyinfo->vertical_scroll_bar_cursor;
29173 }
29174 }
29175 else if (draggable)
29176 /* Default mode-line pointer. */
29177 cursor = FRAME_DISPLAY_INFO (f)->vertical_scroll_bar_cursor;
29178 }
29179 #endif
29180 }
29181
29182 /* Change the mouse face according to what is under X/Y. */
29183 if (STRINGP (string))
29184 {
29185 mouse_face = Fget_text_property (pos, Qmouse_face, string);
29186 if (!NILP (Vmouse_highlight) && !NILP (mouse_face)
29187 && ((area == ON_MODE_LINE) || (area == ON_HEADER_LINE))
29188 && glyph)
29189 {
29190 Lisp_Object b, e;
29191
29192 struct glyph * tmp_glyph;
29193
29194 int gpos;
29195 int gseq_length;
29196 int total_pixel_width;
29197 ptrdiff_t begpos, endpos, ignore;
29198
29199 int vpos, hpos;
29200
29201 b = Fprevious_single_property_change (make_number (charpos + 1),
29202 Qmouse_face, string, Qnil);
29203 if (NILP (b))
29204 begpos = 0;
29205 else
29206 begpos = XINT (b);
29207
29208 e = Fnext_single_property_change (pos, Qmouse_face, string, Qnil);
29209 if (NILP (e))
29210 endpos = SCHARS (string);
29211 else
29212 endpos = XINT (e);
29213
29214 /* Calculate the glyph position GPOS of GLYPH in the
29215 displayed string, relative to the beginning of the
29216 highlighted part of the string.
29217
29218 Note: GPOS is different from CHARPOS. CHARPOS is the
29219 position of GLYPH in the internal string object. A mode
29220 line string format has structures which are converted to
29221 a flattened string by the Emacs Lisp interpreter. The
29222 internal string is an element of those structures. The
29223 displayed string is the flattened string. */
29224 tmp_glyph = row_start_glyph;
29225 while (tmp_glyph < glyph
29226 && (!(EQ (tmp_glyph->object, glyph->object)
29227 && begpos <= tmp_glyph->charpos
29228 && tmp_glyph->charpos < endpos)))
29229 tmp_glyph++;
29230 gpos = glyph - tmp_glyph;
29231
29232 /* Calculate the length GSEQ_LENGTH of the glyph sequence of
29233 the highlighted part of the displayed string to which
29234 GLYPH belongs. Note: GSEQ_LENGTH is different from
29235 SCHARS (STRING), because the latter returns the length of
29236 the internal string. */
29237 for (tmp_glyph = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1;
29238 tmp_glyph > glyph
29239 && (!(EQ (tmp_glyph->object, glyph->object)
29240 && begpos <= tmp_glyph->charpos
29241 && tmp_glyph->charpos < endpos));
29242 tmp_glyph--)
29243 ;
29244 gseq_length = gpos + (tmp_glyph - glyph) + 1;
29245
29246 /* Calculate the total pixel width of all the glyphs between
29247 the beginning of the highlighted area and GLYPH. */
29248 total_pixel_width = 0;
29249 for (tmp_glyph = glyph - gpos; tmp_glyph != glyph; tmp_glyph++)
29250 total_pixel_width += tmp_glyph->pixel_width;
29251
29252 /* Pre calculation of re-rendering position. Note: X is in
29253 column units here, after the call to mode_line_string or
29254 marginal_area_string. */
29255 hpos = x - gpos;
29256 vpos = (area == ON_MODE_LINE
29257 ? (w->current_matrix)->nrows - 1
29258 : 0);
29259
29260 /* If GLYPH's position is included in the region that is
29261 already drawn in mouse face, we have nothing to do. */
29262 if ( EQ (window, hlinfo->mouse_face_window)
29263 && (!row->reversed_p
29264 ? (hlinfo->mouse_face_beg_col <= hpos
29265 && hpos < hlinfo->mouse_face_end_col)
29266 /* In R2L rows we swap BEG and END, see below. */
29267 : (hlinfo->mouse_face_end_col <= hpos
29268 && hpos < hlinfo->mouse_face_beg_col))
29269 && hlinfo->mouse_face_beg_row == vpos )
29270 return;
29271
29272 if (clear_mouse_face (hlinfo))
29273 cursor = No_Cursor;
29274
29275 if (!row->reversed_p)
29276 {
29277 hlinfo->mouse_face_beg_col = hpos;
29278 hlinfo->mouse_face_beg_x = original_x_pixel
29279 - (total_pixel_width + dx);
29280 hlinfo->mouse_face_end_col = hpos + gseq_length;
29281 hlinfo->mouse_face_end_x = 0;
29282 }
29283 else
29284 {
29285 /* In R2L rows, show_mouse_face expects BEG and END
29286 coordinates to be swapped. */
29287 hlinfo->mouse_face_end_col = hpos;
29288 hlinfo->mouse_face_end_x = original_x_pixel
29289 - (total_pixel_width + dx);
29290 hlinfo->mouse_face_beg_col = hpos + gseq_length;
29291 hlinfo->mouse_face_beg_x = 0;
29292 }
29293
29294 hlinfo->mouse_face_beg_row = vpos;
29295 hlinfo->mouse_face_end_row = hlinfo->mouse_face_beg_row;
29296 hlinfo->mouse_face_past_end = 0;
29297 hlinfo->mouse_face_window = window;
29298
29299 hlinfo->mouse_face_face_id = face_at_string_position (w, string,
29300 charpos,
29301 0, &ignore,
29302 glyph->face_id,
29303 true);
29304 show_mouse_face (hlinfo, DRAW_MOUSE_FACE);
29305
29306 if (NILP (pointer))
29307 pointer = Qhand;
29308 }
29309 else if ((area == ON_MODE_LINE) || (area == ON_HEADER_LINE))
29310 clear_mouse_face (hlinfo);
29311 }
29312 #ifdef HAVE_WINDOW_SYSTEM
29313 if (FRAME_WINDOW_P (f))
29314 define_frame_cursor1 (f, cursor, pointer);
29315 #endif
29316 }
29317
29318
29319 /* EXPORT:
29320 Take proper action when the mouse has moved to position X, Y on
29321 frame F with regards to highlighting portions of display that have
29322 mouse-face properties. Also de-highlight portions of display where
29323 the mouse was before, set the mouse pointer shape as appropriate
29324 for the mouse coordinates, and activate help echo (tooltips).
29325 X and Y can be negative or out of range. */
29326
29327 void
29328 note_mouse_highlight (struct frame *f, int x, int y)
29329 {
29330 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
29331 enum window_part part = ON_NOTHING;
29332 Lisp_Object window;
29333 struct window *w;
29334 Cursor cursor = No_Cursor;
29335 Lisp_Object pointer = Qnil; /* Takes precedence over cursor! */
29336 struct buffer *b;
29337
29338 /* When a menu is active, don't highlight because this looks odd. */
29339 #if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS) || defined (MSDOS)
29340 if (popup_activated ())
29341 return;
29342 #endif
29343
29344 if (!f->glyphs_initialized_p
29345 || f->pointer_invisible)
29346 return;
29347
29348 hlinfo->mouse_face_mouse_x = x;
29349 hlinfo->mouse_face_mouse_y = y;
29350 hlinfo->mouse_face_mouse_frame = f;
29351
29352 if (hlinfo->mouse_face_defer)
29353 return;
29354
29355 /* Which window is that in? */
29356 window = window_from_coordinates (f, x, y, &part, 1);
29357
29358 /* If displaying active text in another window, clear that. */
29359 if (! EQ (window, hlinfo->mouse_face_window)
29360 /* Also clear if we move out of text area in same window. */
29361 || (!NILP (hlinfo->mouse_face_window)
29362 && !NILP (window)
29363 && part != ON_TEXT
29364 && part != ON_MODE_LINE
29365 && part != ON_HEADER_LINE))
29366 clear_mouse_face (hlinfo);
29367
29368 /* Not on a window -> return. */
29369 if (!WINDOWP (window))
29370 return;
29371
29372 /* Reset help_echo_string. It will get recomputed below. */
29373 help_echo_string = Qnil;
29374
29375 /* Convert to window-relative pixel coordinates. */
29376 w = XWINDOW (window);
29377 frame_to_window_pixel_xy (w, &x, &y);
29378
29379 #if defined (HAVE_WINDOW_SYSTEM) && ! defined (USE_GTK) && ! defined (HAVE_NS)
29380 /* Handle tool-bar window differently since it doesn't display a
29381 buffer. */
29382 if (EQ (window, f->tool_bar_window))
29383 {
29384 note_tool_bar_highlight (f, x, y);
29385 return;
29386 }
29387 #endif
29388
29389 /* Mouse is on the mode, header line or margin? */
29390 if (part == ON_MODE_LINE || part == ON_HEADER_LINE
29391 || part == ON_LEFT_MARGIN || part == ON_RIGHT_MARGIN)
29392 {
29393 note_mode_line_or_margin_highlight (window, x, y, part);
29394
29395 #ifdef HAVE_WINDOW_SYSTEM
29396 if (part == ON_LEFT_MARGIN || part == ON_RIGHT_MARGIN)
29397 {
29398 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
29399 /* Show non-text cursor (Bug#16647). */
29400 goto set_cursor;
29401 }
29402 else
29403 #endif
29404 return;
29405 }
29406
29407 #ifdef HAVE_WINDOW_SYSTEM
29408 if (part == ON_VERTICAL_BORDER)
29409 {
29410 cursor = FRAME_X_OUTPUT (f)->horizontal_drag_cursor;
29411 help_echo_string = build_string ("drag-mouse-1: resize");
29412 }
29413 else if (part == ON_RIGHT_DIVIDER)
29414 {
29415 cursor = FRAME_X_OUTPUT (f)->horizontal_drag_cursor;
29416 help_echo_string = build_string ("drag-mouse-1: resize");
29417 }
29418 else if (part == ON_BOTTOM_DIVIDER)
29419 if (! WINDOW_BOTTOMMOST_P (w)
29420 || minibuf_level
29421 || NILP (Vresize_mini_windows))
29422 {
29423 cursor = FRAME_X_OUTPUT (f)->vertical_drag_cursor;
29424 help_echo_string = build_string ("drag-mouse-1: resize");
29425 }
29426 else
29427 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
29428 else if (part == ON_LEFT_FRINGE || part == ON_RIGHT_FRINGE
29429 || part == ON_VERTICAL_SCROLL_BAR
29430 || part == ON_HORIZONTAL_SCROLL_BAR)
29431 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
29432 else
29433 cursor = FRAME_X_OUTPUT (f)->text_cursor;
29434 #endif
29435
29436 /* Are we in a window whose display is up to date?
29437 And verify the buffer's text has not changed. */
29438 b = XBUFFER (w->contents);
29439 if (part == ON_TEXT && w->window_end_valid && !window_outdated (w))
29440 {
29441 int hpos, vpos, dx, dy, area = LAST_AREA;
29442 ptrdiff_t pos;
29443 struct glyph *glyph;
29444 Lisp_Object object;
29445 Lisp_Object mouse_face = Qnil, position;
29446 Lisp_Object *overlay_vec = NULL;
29447 ptrdiff_t i, noverlays;
29448 struct buffer *obuf;
29449 ptrdiff_t obegv, ozv;
29450 int same_region;
29451
29452 /* Find the glyph under X/Y. */
29453 glyph = x_y_to_hpos_vpos (w, x, y, &hpos, &vpos, &dx, &dy, &area);
29454
29455 #ifdef HAVE_WINDOW_SYSTEM
29456 /* Look for :pointer property on image. */
29457 if (glyph != NULL && glyph->type == IMAGE_GLYPH)
29458 {
29459 struct image *img = IMAGE_FROM_ID (f, glyph->u.img_id);
29460 if (img != NULL && IMAGEP (img->spec))
29461 {
29462 Lisp_Object image_map, hotspot;
29463 if ((image_map = Fplist_get (XCDR (img->spec), QCmap),
29464 !NILP (image_map))
29465 && (hotspot = find_hot_spot (image_map,
29466 glyph->slice.img.x + dx,
29467 glyph->slice.img.y + dy),
29468 CONSP (hotspot))
29469 && (hotspot = XCDR (hotspot), CONSP (hotspot)))
29470 {
29471 Lisp_Object plist;
29472
29473 /* Could check XCAR (hotspot) to see if we enter/leave
29474 this hot-spot.
29475 If so, we could look for mouse-enter, mouse-leave
29476 properties in PLIST (and do something...). */
29477 hotspot = XCDR (hotspot);
29478 if (CONSP (hotspot)
29479 && (plist = XCAR (hotspot), CONSP (plist)))
29480 {
29481 pointer = Fplist_get (plist, Qpointer);
29482 if (NILP (pointer))
29483 pointer = Qhand;
29484 help_echo_string = Fplist_get (plist, Qhelp_echo);
29485 if (!NILP (help_echo_string))
29486 {
29487 help_echo_window = window;
29488 help_echo_object = glyph->object;
29489 help_echo_pos = glyph->charpos;
29490 }
29491 }
29492 }
29493 if (NILP (pointer))
29494 pointer = Fplist_get (XCDR (img->spec), QCpointer);
29495 }
29496 }
29497 #endif /* HAVE_WINDOW_SYSTEM */
29498
29499 /* Clear mouse face if X/Y not over text. */
29500 if (glyph == NULL
29501 || area != TEXT_AREA
29502 || !MATRIX_ROW_DISPLAYS_TEXT_P (MATRIX_ROW (w->current_matrix, vpos))
29503 /* Glyph's OBJECT is nil for glyphs inserted by the
29504 display engine for its internal purposes, like truncation
29505 and continuation glyphs and blanks beyond the end of
29506 line's text on text terminals. If we are over such a
29507 glyph, we are not over any text. */
29508 || NILP (glyph->object)
29509 /* R2L rows have a stretch glyph at their front, which
29510 stands for no text, whereas L2R rows have no glyphs at
29511 all beyond the end of text. Treat such stretch glyphs
29512 like we do with NULL glyphs in L2R rows. */
29513 || (MATRIX_ROW (w->current_matrix, vpos)->reversed_p
29514 && glyph == MATRIX_ROW_GLYPH_START (w->current_matrix, vpos)
29515 && glyph->type == STRETCH_GLYPH
29516 && glyph->avoid_cursor_p))
29517 {
29518 if (clear_mouse_face (hlinfo))
29519 cursor = No_Cursor;
29520 #ifdef HAVE_WINDOW_SYSTEM
29521 if (FRAME_WINDOW_P (f) && NILP (pointer))
29522 {
29523 if (area != TEXT_AREA)
29524 cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
29525 else
29526 pointer = Vvoid_text_area_pointer;
29527 }
29528 #endif
29529 goto set_cursor;
29530 }
29531
29532 pos = glyph->charpos;
29533 object = glyph->object;
29534 if (!STRINGP (object) && !BUFFERP (object))
29535 goto set_cursor;
29536
29537 /* If we get an out-of-range value, return now; avoid an error. */
29538 if (BUFFERP (object) && pos > BUF_Z (b))
29539 goto set_cursor;
29540
29541 /* Make the window's buffer temporarily current for
29542 overlays_at and compute_char_face. */
29543 obuf = current_buffer;
29544 current_buffer = b;
29545 obegv = BEGV;
29546 ozv = ZV;
29547 BEGV = BEG;
29548 ZV = Z;
29549
29550 /* Is this char mouse-active or does it have help-echo? */
29551 position = make_number (pos);
29552
29553 USE_SAFE_ALLOCA;
29554
29555 if (BUFFERP (object))
29556 {
29557 /* Put all the overlays we want in a vector in overlay_vec. */
29558 GET_OVERLAYS_AT (pos, overlay_vec, noverlays, NULL, 0);
29559 /* Sort overlays into increasing priority order. */
29560 noverlays = sort_overlays (overlay_vec, noverlays, w);
29561 }
29562 else
29563 noverlays = 0;
29564
29565 if (NILP (Vmouse_highlight))
29566 {
29567 clear_mouse_face (hlinfo);
29568 goto check_help_echo;
29569 }
29570
29571 same_region = coords_in_mouse_face_p (w, hpos, vpos);
29572
29573 if (same_region)
29574 cursor = No_Cursor;
29575
29576 /* Check mouse-face highlighting. */
29577 if (! same_region
29578 /* If there exists an overlay with mouse-face overlapping
29579 the one we are currently highlighting, we have to
29580 check if we enter the overlapping overlay, and then
29581 highlight only that. */
29582 || (OVERLAYP (hlinfo->mouse_face_overlay)
29583 && mouse_face_overlay_overlaps (hlinfo->mouse_face_overlay)))
29584 {
29585 /* Find the highest priority overlay with a mouse-face. */
29586 Lisp_Object overlay = Qnil;
29587 for (i = noverlays - 1; i >= 0 && NILP (overlay); --i)
29588 {
29589 mouse_face = Foverlay_get (overlay_vec[i], Qmouse_face);
29590 if (!NILP (mouse_face))
29591 overlay = overlay_vec[i];
29592 }
29593
29594 /* If we're highlighting the same overlay as before, there's
29595 no need to do that again. */
29596 if (!NILP (overlay) && EQ (overlay, hlinfo->mouse_face_overlay))
29597 goto check_help_echo;
29598 hlinfo->mouse_face_overlay = overlay;
29599
29600 /* Clear the display of the old active region, if any. */
29601 if (clear_mouse_face (hlinfo))
29602 cursor = No_Cursor;
29603
29604 /* If no overlay applies, get a text property. */
29605 if (NILP (overlay))
29606 mouse_face = Fget_text_property (position, Qmouse_face, object);
29607
29608 /* Next, compute the bounds of the mouse highlighting and
29609 display it. */
29610 if (!NILP (mouse_face) && STRINGP (object))
29611 {
29612 /* The mouse-highlighting comes from a display string
29613 with a mouse-face. */
29614 Lisp_Object s, e;
29615 ptrdiff_t ignore;
29616
29617 s = Fprevious_single_property_change
29618 (make_number (pos + 1), Qmouse_face, object, Qnil);
29619 e = Fnext_single_property_change
29620 (position, Qmouse_face, object, Qnil);
29621 if (NILP (s))
29622 s = make_number (0);
29623 if (NILP (e))
29624 e = make_number (SCHARS (object));
29625 mouse_face_from_string_pos (w, hlinfo, object,
29626 XINT (s), XINT (e));
29627 hlinfo->mouse_face_past_end = 0;
29628 hlinfo->mouse_face_window = window;
29629 hlinfo->mouse_face_face_id
29630 = face_at_string_position (w, object, pos, 0, &ignore,
29631 glyph->face_id, true);
29632 show_mouse_face (hlinfo, DRAW_MOUSE_FACE);
29633 cursor = No_Cursor;
29634 }
29635 else
29636 {
29637 /* The mouse-highlighting, if any, comes from an overlay
29638 or text property in the buffer. */
29639 Lisp_Object buffer IF_LINT (= Qnil);
29640 Lisp_Object disp_string IF_LINT (= Qnil);
29641
29642 if (STRINGP (object))
29643 {
29644 /* If we are on a display string with no mouse-face,
29645 check if the text under it has one. */
29646 struct glyph_row *r = MATRIX_ROW (w->current_matrix, vpos);
29647 ptrdiff_t start = MATRIX_ROW_START_CHARPOS (r);
29648 pos = string_buffer_position (object, start);
29649 if (pos > 0)
29650 {
29651 mouse_face = get_char_property_and_overlay
29652 (make_number (pos), Qmouse_face, w->contents, &overlay);
29653 buffer = w->contents;
29654 disp_string = object;
29655 }
29656 }
29657 else
29658 {
29659 buffer = object;
29660 disp_string = Qnil;
29661 }
29662
29663 if (!NILP (mouse_face))
29664 {
29665 Lisp_Object before, after;
29666 Lisp_Object before_string, after_string;
29667 /* To correctly find the limits of mouse highlight
29668 in a bidi-reordered buffer, we must not use the
29669 optimization of limiting the search in
29670 previous-single-property-change and
29671 next-single-property-change, because
29672 rows_from_pos_range needs the real start and end
29673 positions to DTRT in this case. That's because
29674 the first row visible in a window does not
29675 necessarily display the character whose position
29676 is the smallest. */
29677 Lisp_Object lim1
29678 = NILP (BVAR (XBUFFER (buffer), bidi_display_reordering))
29679 ? Fmarker_position (w->start)
29680 : Qnil;
29681 Lisp_Object lim2
29682 = NILP (BVAR (XBUFFER (buffer), bidi_display_reordering))
29683 ? make_number (BUF_Z (XBUFFER (buffer))
29684 - w->window_end_pos)
29685 : Qnil;
29686
29687 if (NILP (overlay))
29688 {
29689 /* Handle the text property case. */
29690 before = Fprevious_single_property_change
29691 (make_number (pos + 1), Qmouse_face, buffer, lim1);
29692 after = Fnext_single_property_change
29693 (make_number (pos), Qmouse_face, buffer, lim2);
29694 before_string = after_string = Qnil;
29695 }
29696 else
29697 {
29698 /* Handle the overlay case. */
29699 before = Foverlay_start (overlay);
29700 after = Foverlay_end (overlay);
29701 before_string = Foverlay_get (overlay, Qbefore_string);
29702 after_string = Foverlay_get (overlay, Qafter_string);
29703
29704 if (!STRINGP (before_string)) before_string = Qnil;
29705 if (!STRINGP (after_string)) after_string = Qnil;
29706 }
29707
29708 mouse_face_from_buffer_pos (window, hlinfo, pos,
29709 NILP (before)
29710 ? 1
29711 : XFASTINT (before),
29712 NILP (after)
29713 ? BUF_Z (XBUFFER (buffer))
29714 : XFASTINT (after),
29715 before_string, after_string,
29716 disp_string);
29717 cursor = No_Cursor;
29718 }
29719 }
29720 }
29721
29722 check_help_echo:
29723
29724 /* Look for a `help-echo' property. */
29725 if (NILP (help_echo_string)) {
29726 Lisp_Object help, overlay;
29727
29728 /* Check overlays first. */
29729 help = overlay = Qnil;
29730 for (i = noverlays - 1; i >= 0 && NILP (help); --i)
29731 {
29732 overlay = overlay_vec[i];
29733 help = Foverlay_get (overlay, Qhelp_echo);
29734 }
29735
29736 if (!NILP (help))
29737 {
29738 help_echo_string = help;
29739 help_echo_window = window;
29740 help_echo_object = overlay;
29741 help_echo_pos = pos;
29742 }
29743 else
29744 {
29745 Lisp_Object obj = glyph->object;
29746 ptrdiff_t charpos = glyph->charpos;
29747
29748 /* Try text properties. */
29749 if (STRINGP (obj)
29750 && charpos >= 0
29751 && charpos < SCHARS (obj))
29752 {
29753 help = Fget_text_property (make_number (charpos),
29754 Qhelp_echo, obj);
29755 if (NILP (help))
29756 {
29757 /* If the string itself doesn't specify a help-echo,
29758 see if the buffer text ``under'' it does. */
29759 struct glyph_row *r
29760 = MATRIX_ROW (w->current_matrix, vpos);
29761 ptrdiff_t start = MATRIX_ROW_START_CHARPOS (r);
29762 ptrdiff_t p = string_buffer_position (obj, start);
29763 if (p > 0)
29764 {
29765 help = Fget_char_property (make_number (p),
29766 Qhelp_echo, w->contents);
29767 if (!NILP (help))
29768 {
29769 charpos = p;
29770 obj = w->contents;
29771 }
29772 }
29773 }
29774 }
29775 else if (BUFFERP (obj)
29776 && charpos >= BEGV
29777 && charpos < ZV)
29778 help = Fget_text_property (make_number (charpos), Qhelp_echo,
29779 obj);
29780
29781 if (!NILP (help))
29782 {
29783 help_echo_string = help;
29784 help_echo_window = window;
29785 help_echo_object = obj;
29786 help_echo_pos = charpos;
29787 }
29788 }
29789 }
29790
29791 #ifdef HAVE_WINDOW_SYSTEM
29792 /* Look for a `pointer' property. */
29793 if (FRAME_WINDOW_P (f) && NILP (pointer))
29794 {
29795 /* Check overlays first. */
29796 for (i = noverlays - 1; i >= 0 && NILP (pointer); --i)
29797 pointer = Foverlay_get (overlay_vec[i], Qpointer);
29798
29799 if (NILP (pointer))
29800 {
29801 Lisp_Object obj = glyph->object;
29802 ptrdiff_t charpos = glyph->charpos;
29803
29804 /* Try text properties. */
29805 if (STRINGP (obj)
29806 && charpos >= 0
29807 && charpos < SCHARS (obj))
29808 {
29809 pointer = Fget_text_property (make_number (charpos),
29810 Qpointer, obj);
29811 if (NILP (pointer))
29812 {
29813 /* If the string itself doesn't specify a pointer,
29814 see if the buffer text ``under'' it does. */
29815 struct glyph_row *r
29816 = MATRIX_ROW (w->current_matrix, vpos);
29817 ptrdiff_t start = MATRIX_ROW_START_CHARPOS (r);
29818 ptrdiff_t p = string_buffer_position (obj, start);
29819 if (p > 0)
29820 pointer = Fget_char_property (make_number (p),
29821 Qpointer, w->contents);
29822 }
29823 }
29824 else if (BUFFERP (obj)
29825 && charpos >= BEGV
29826 && charpos < ZV)
29827 pointer = Fget_text_property (make_number (charpos),
29828 Qpointer, obj);
29829 }
29830 }
29831 #endif /* HAVE_WINDOW_SYSTEM */
29832
29833 BEGV = obegv;
29834 ZV = ozv;
29835 current_buffer = obuf;
29836 SAFE_FREE ();
29837 }
29838
29839 set_cursor:
29840
29841 #ifdef HAVE_WINDOW_SYSTEM
29842 if (FRAME_WINDOW_P (f))
29843 define_frame_cursor1 (f, cursor, pointer);
29844 #else
29845 /* This is here to prevent a compiler error, about "label at end of
29846 compound statement". */
29847 return;
29848 #endif
29849 }
29850
29851
29852 /* EXPORT for RIF:
29853 Clear any mouse-face on window W. This function is part of the
29854 redisplay interface, and is called from try_window_id and similar
29855 functions to ensure the mouse-highlight is off. */
29856
29857 void
29858 x_clear_window_mouse_face (struct window *w)
29859 {
29860 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (XFRAME (w->frame));
29861 Lisp_Object window;
29862
29863 block_input ();
29864 XSETWINDOW (window, w);
29865 if (EQ (window, hlinfo->mouse_face_window))
29866 clear_mouse_face (hlinfo);
29867 unblock_input ();
29868 }
29869
29870
29871 /* EXPORT:
29872 Just discard the mouse face information for frame F, if any.
29873 This is used when the size of F is changed. */
29874
29875 void
29876 cancel_mouse_face (struct frame *f)
29877 {
29878 Lisp_Object window;
29879 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
29880
29881 window = hlinfo->mouse_face_window;
29882 if (! NILP (window) && XFRAME (XWINDOW (window)->frame) == f)
29883 reset_mouse_highlight (hlinfo);
29884 }
29885
29886
29887 \f
29888 /***********************************************************************
29889 Exposure Events
29890 ***********************************************************************/
29891
29892 #ifdef HAVE_WINDOW_SYSTEM
29893
29894 /* Redraw the part of glyph row area AREA of glyph row ROW on window W
29895 which intersects rectangle R. R is in window-relative coordinates. */
29896
29897 static void
29898 expose_area (struct window *w, struct glyph_row *row, XRectangle *r,
29899 enum glyph_row_area area)
29900 {
29901 struct glyph *first = row->glyphs[area];
29902 struct glyph *end = row->glyphs[area] + row->used[area];
29903 struct glyph *last;
29904 int first_x, start_x, x;
29905
29906 if (area == TEXT_AREA && row->fill_line_p)
29907 /* If row extends face to end of line write the whole line. */
29908 draw_glyphs (w, 0, row, area,
29909 0, row->used[area],
29910 DRAW_NORMAL_TEXT, 0);
29911 else
29912 {
29913 /* Set START_X to the window-relative start position for drawing glyphs of
29914 AREA. The first glyph of the text area can be partially visible.
29915 The first glyphs of other areas cannot. */
29916 start_x = window_box_left_offset (w, area);
29917 x = start_x;
29918 if (area == TEXT_AREA)
29919 x += row->x;
29920
29921 /* Find the first glyph that must be redrawn. */
29922 while (first < end
29923 && x + first->pixel_width < r->x)
29924 {
29925 x += first->pixel_width;
29926 ++first;
29927 }
29928
29929 /* Find the last one. */
29930 last = first;
29931 first_x = x;
29932 while (last < end
29933 && x < r->x + r->width)
29934 {
29935 x += last->pixel_width;
29936 ++last;
29937 }
29938
29939 /* Repaint. */
29940 if (last > first)
29941 draw_glyphs (w, first_x - start_x, row, area,
29942 first - row->glyphs[area], last - row->glyphs[area],
29943 DRAW_NORMAL_TEXT, 0);
29944 }
29945 }
29946
29947
29948 /* Redraw the parts of the glyph row ROW on window W intersecting
29949 rectangle R. R is in window-relative coordinates. Value is
29950 non-zero if mouse-face was overwritten. */
29951
29952 static int
29953 expose_line (struct window *w, struct glyph_row *row, XRectangle *r)
29954 {
29955 eassert (row->enabled_p);
29956
29957 if (row->mode_line_p || w->pseudo_window_p)
29958 draw_glyphs (w, 0, row, TEXT_AREA,
29959 0, row->used[TEXT_AREA],
29960 DRAW_NORMAL_TEXT, 0);
29961 else
29962 {
29963 if (row->used[LEFT_MARGIN_AREA])
29964 expose_area (w, row, r, LEFT_MARGIN_AREA);
29965 if (row->used[TEXT_AREA])
29966 expose_area (w, row, r, TEXT_AREA);
29967 if (row->used[RIGHT_MARGIN_AREA])
29968 expose_area (w, row, r, RIGHT_MARGIN_AREA);
29969 draw_row_fringe_bitmaps (w, row);
29970 }
29971
29972 return row->mouse_face_p;
29973 }
29974
29975
29976 /* Redraw those parts of glyphs rows during expose event handling that
29977 overlap other rows. Redrawing of an exposed line writes over parts
29978 of lines overlapping that exposed line; this function fixes that.
29979
29980 W is the window being exposed. FIRST_OVERLAPPING_ROW is the first
29981 row in W's current matrix that is exposed and overlaps other rows.
29982 LAST_OVERLAPPING_ROW is the last such row. */
29983
29984 static void
29985 expose_overlaps (struct window *w,
29986 struct glyph_row *first_overlapping_row,
29987 struct glyph_row *last_overlapping_row,
29988 XRectangle *r)
29989 {
29990 struct glyph_row *row;
29991
29992 for (row = first_overlapping_row; row <= last_overlapping_row; ++row)
29993 if (row->overlapping_p)
29994 {
29995 eassert (row->enabled_p && !row->mode_line_p);
29996
29997 row->clip = r;
29998 if (row->used[LEFT_MARGIN_AREA])
29999 x_fix_overlapping_area (w, row, LEFT_MARGIN_AREA, OVERLAPS_BOTH);
30000
30001 if (row->used[TEXT_AREA])
30002 x_fix_overlapping_area (w, row, TEXT_AREA, OVERLAPS_BOTH);
30003
30004 if (row->used[RIGHT_MARGIN_AREA])
30005 x_fix_overlapping_area (w, row, RIGHT_MARGIN_AREA, OVERLAPS_BOTH);
30006 row->clip = NULL;
30007 }
30008 }
30009
30010
30011 /* Return non-zero if W's cursor intersects rectangle R. */
30012
30013 static int
30014 phys_cursor_in_rect_p (struct window *w, XRectangle *r)
30015 {
30016 XRectangle cr, result;
30017 struct glyph *cursor_glyph;
30018 struct glyph_row *row;
30019
30020 if (w->phys_cursor.vpos >= 0
30021 && w->phys_cursor.vpos < w->current_matrix->nrows
30022 && (row = MATRIX_ROW (w->current_matrix, w->phys_cursor.vpos),
30023 row->enabled_p)
30024 && row->cursor_in_fringe_p)
30025 {
30026 /* Cursor is in the fringe. */
30027 cr.x = window_box_right_offset (w,
30028 (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
30029 ? RIGHT_MARGIN_AREA
30030 : TEXT_AREA));
30031 cr.y = row->y;
30032 cr.width = WINDOW_RIGHT_FRINGE_WIDTH (w);
30033 cr.height = row->height;
30034 return x_intersect_rectangles (&cr, r, &result);
30035 }
30036
30037 cursor_glyph = get_phys_cursor_glyph (w);
30038 if (cursor_glyph)
30039 {
30040 /* r is relative to W's box, but w->phys_cursor.x is relative
30041 to left edge of W's TEXT area. Adjust it. */
30042 cr.x = window_box_left_offset (w, TEXT_AREA) + w->phys_cursor.x;
30043 cr.y = w->phys_cursor.y;
30044 cr.width = cursor_glyph->pixel_width;
30045 cr.height = w->phys_cursor_height;
30046 /* ++KFS: W32 version used W32-specific IntersectRect here, but
30047 I assume the effect is the same -- and this is portable. */
30048 return x_intersect_rectangles (&cr, r, &result);
30049 }
30050 /* If we don't understand the format, pretend we're not in the hot-spot. */
30051 return 0;
30052 }
30053
30054
30055 /* EXPORT:
30056 Draw a vertical window border to the right of window W if W doesn't
30057 have vertical scroll bars. */
30058
30059 void
30060 x_draw_vertical_border (struct window *w)
30061 {
30062 struct frame *f = XFRAME (WINDOW_FRAME (w));
30063
30064 /* We could do better, if we knew what type of scroll-bar the adjacent
30065 windows (on either side) have... But we don't :-(
30066 However, I think this works ok. ++KFS 2003-04-25 */
30067
30068 /* Redraw borders between horizontally adjacent windows. Don't
30069 do it for frames with vertical scroll bars because either the
30070 right scroll bar of a window, or the left scroll bar of its
30071 neighbor will suffice as a border. */
30072 if (FRAME_HAS_VERTICAL_SCROLL_BARS (f) || FRAME_RIGHT_DIVIDER_WIDTH (f))
30073 return;
30074
30075 /* Note: It is necessary to redraw both the left and the right
30076 borders, for when only this single window W is being
30077 redisplayed. */
30078 if (!WINDOW_RIGHTMOST_P (w)
30079 && !WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_RIGHT (w))
30080 {
30081 int x0, x1, y0, y1;
30082
30083 window_box_edges (w, &x0, &y0, &x1, &y1);
30084 y1 -= 1;
30085
30086 if (WINDOW_LEFT_FRINGE_WIDTH (w) == 0)
30087 x1 -= 1;
30088
30089 FRAME_RIF (f)->draw_vertical_window_border (w, x1, y0, y1);
30090 }
30091
30092 if (!WINDOW_LEFTMOST_P (w)
30093 && !WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_LEFT (w))
30094 {
30095 int x0, x1, y0, y1;
30096
30097 window_box_edges (w, &x0, &y0, &x1, &y1);
30098 y1 -= 1;
30099
30100 if (WINDOW_LEFT_FRINGE_WIDTH (w) == 0)
30101 x0 -= 1;
30102
30103 FRAME_RIF (f)->draw_vertical_window_border (w, x0, y0, y1);
30104 }
30105 }
30106
30107
30108 /* Draw window dividers for window W. */
30109
30110 void
30111 x_draw_right_divider (struct window *w)
30112 {
30113 struct frame *f = WINDOW_XFRAME (w);
30114
30115 if (w->mini || w->pseudo_window_p)
30116 return;
30117 else if (WINDOW_RIGHT_DIVIDER_WIDTH (w))
30118 {
30119 int x0 = WINDOW_RIGHT_EDGE_X (w) - WINDOW_RIGHT_DIVIDER_WIDTH (w);
30120 int x1 = WINDOW_RIGHT_EDGE_X (w);
30121 int y0 = WINDOW_TOP_EDGE_Y (w);
30122 /* The bottom divider prevails. */
30123 int y1 = WINDOW_BOTTOM_EDGE_Y (w) - WINDOW_BOTTOM_DIVIDER_WIDTH (w);
30124
30125 FRAME_RIF (f)->draw_window_divider (w, x0, x1, y0, y1);
30126 }
30127 }
30128
30129 static void
30130 x_draw_bottom_divider (struct window *w)
30131 {
30132 struct frame *f = XFRAME (WINDOW_FRAME (w));
30133
30134 if (w->mini || w->pseudo_window_p)
30135 return;
30136 else if (WINDOW_BOTTOM_DIVIDER_WIDTH (w))
30137 {
30138 int x0 = WINDOW_LEFT_EDGE_X (w);
30139 int x1 = WINDOW_RIGHT_EDGE_X (w);
30140 int y0 = WINDOW_BOTTOM_EDGE_Y (w) - WINDOW_BOTTOM_DIVIDER_WIDTH (w);
30141 int y1 = WINDOW_BOTTOM_EDGE_Y (w);
30142
30143 FRAME_RIF (f)->draw_window_divider (w, x0, x1, y0, y1);
30144 }
30145 }
30146
30147 /* Redraw the part of window W intersection rectangle FR. Pixel
30148 coordinates in FR are frame-relative. Call this function with
30149 input blocked. Value is non-zero if the exposure overwrites
30150 mouse-face. */
30151
30152 static int
30153 expose_window (struct window *w, XRectangle *fr)
30154 {
30155 struct frame *f = XFRAME (w->frame);
30156 XRectangle wr, r;
30157 int mouse_face_overwritten_p = 0;
30158
30159 /* If window is not yet fully initialized, do nothing. This can
30160 happen when toolkit scroll bars are used and a window is split.
30161 Reconfiguring the scroll bar will generate an expose for a newly
30162 created window. */
30163 if (w->current_matrix == NULL)
30164 return 0;
30165
30166 /* When we're currently updating the window, display and current
30167 matrix usually don't agree. Arrange for a thorough display
30168 later. */
30169 if (w->must_be_updated_p)
30170 {
30171 SET_FRAME_GARBAGED (f);
30172 return 0;
30173 }
30174
30175 /* Frame-relative pixel rectangle of W. */
30176 wr.x = WINDOW_LEFT_EDGE_X (w);
30177 wr.y = WINDOW_TOP_EDGE_Y (w);
30178 wr.width = WINDOW_PIXEL_WIDTH (w);
30179 wr.height = WINDOW_PIXEL_HEIGHT (w);
30180
30181 if (x_intersect_rectangles (fr, &wr, &r))
30182 {
30183 int yb = window_text_bottom_y (w);
30184 struct glyph_row *row;
30185 int cursor_cleared_p, phys_cursor_on_p;
30186 struct glyph_row *first_overlapping_row, *last_overlapping_row;
30187
30188 TRACE ((stderr, "expose_window (%d, %d, %d, %d)\n",
30189 r.x, r.y, r.width, r.height));
30190
30191 /* Convert to window coordinates. */
30192 r.x -= WINDOW_LEFT_EDGE_X (w);
30193 r.y -= WINDOW_TOP_EDGE_Y (w);
30194
30195 /* Turn off the cursor. */
30196 if (!w->pseudo_window_p
30197 && phys_cursor_in_rect_p (w, &r))
30198 {
30199 x_clear_cursor (w);
30200 cursor_cleared_p = 1;
30201 }
30202 else
30203 cursor_cleared_p = 0;
30204
30205 /* If the row containing the cursor extends face to end of line,
30206 then expose_area might overwrite the cursor outside the
30207 rectangle and thus notice_overwritten_cursor might clear
30208 w->phys_cursor_on_p. We remember the original value and
30209 check later if it is changed. */
30210 phys_cursor_on_p = w->phys_cursor_on_p;
30211
30212 /* Update lines intersecting rectangle R. */
30213 first_overlapping_row = last_overlapping_row = NULL;
30214 for (row = w->current_matrix->rows;
30215 row->enabled_p;
30216 ++row)
30217 {
30218 int y0 = row->y;
30219 int y1 = MATRIX_ROW_BOTTOM_Y (row);
30220
30221 if ((y0 >= r.y && y0 < r.y + r.height)
30222 || (y1 > r.y && y1 < r.y + r.height)
30223 || (r.y >= y0 && r.y < y1)
30224 || (r.y + r.height > y0 && r.y + r.height < y1))
30225 {
30226 /* A header line may be overlapping, but there is no need
30227 to fix overlapping areas for them. KFS 2005-02-12 */
30228 if (row->overlapping_p && !row->mode_line_p)
30229 {
30230 if (first_overlapping_row == NULL)
30231 first_overlapping_row = row;
30232 last_overlapping_row = row;
30233 }
30234
30235 row->clip = fr;
30236 if (expose_line (w, row, &r))
30237 mouse_face_overwritten_p = 1;
30238 row->clip = NULL;
30239 }
30240 else if (row->overlapping_p)
30241 {
30242 /* We must redraw a row overlapping the exposed area. */
30243 if (y0 < r.y
30244 ? y0 + row->phys_height > r.y
30245 : y0 + row->ascent - row->phys_ascent < r.y +r.height)
30246 {
30247 if (first_overlapping_row == NULL)
30248 first_overlapping_row = row;
30249 last_overlapping_row = row;
30250 }
30251 }
30252
30253 if (y1 >= yb)
30254 break;
30255 }
30256
30257 /* Display the mode line if there is one. */
30258 if (WINDOW_WANTS_MODELINE_P (w)
30259 && (row = MATRIX_MODE_LINE_ROW (w->current_matrix),
30260 row->enabled_p)
30261 && row->y < r.y + r.height)
30262 {
30263 if (expose_line (w, row, &r))
30264 mouse_face_overwritten_p = 1;
30265 }
30266
30267 if (!w->pseudo_window_p)
30268 {
30269 /* Fix the display of overlapping rows. */
30270 if (first_overlapping_row)
30271 expose_overlaps (w, first_overlapping_row, last_overlapping_row,
30272 fr);
30273
30274 /* Draw border between windows. */
30275 if (WINDOW_RIGHT_DIVIDER_WIDTH (w))
30276 x_draw_right_divider (w);
30277 else
30278 x_draw_vertical_border (w);
30279
30280 if (WINDOW_BOTTOM_DIVIDER_WIDTH (w))
30281 x_draw_bottom_divider (w);
30282
30283 /* Turn the cursor on again. */
30284 if (cursor_cleared_p
30285 || (phys_cursor_on_p && !w->phys_cursor_on_p))
30286 update_window_cursor (w, 1);
30287 }
30288 }
30289
30290 return mouse_face_overwritten_p;
30291 }
30292
30293
30294
30295 /* Redraw (parts) of all windows in the window tree rooted at W that
30296 intersect R. R contains frame pixel coordinates. Value is
30297 non-zero if the exposure overwrites mouse-face. */
30298
30299 static int
30300 expose_window_tree (struct window *w, XRectangle *r)
30301 {
30302 struct frame *f = XFRAME (w->frame);
30303 int mouse_face_overwritten_p = 0;
30304
30305 while (w && !FRAME_GARBAGED_P (f))
30306 {
30307 if (WINDOWP (w->contents))
30308 mouse_face_overwritten_p
30309 |= expose_window_tree (XWINDOW (w->contents), r);
30310 else
30311 mouse_face_overwritten_p |= expose_window (w, r);
30312
30313 w = NILP (w->next) ? NULL : XWINDOW (w->next);
30314 }
30315
30316 return mouse_face_overwritten_p;
30317 }
30318
30319
30320 /* EXPORT:
30321 Redisplay an exposed area of frame F. X and Y are the upper-left
30322 corner of the exposed rectangle. W and H are width and height of
30323 the exposed area. All are pixel values. W or H zero means redraw
30324 the entire frame. */
30325
30326 void
30327 expose_frame (struct frame *f, int x, int y, int w, int h)
30328 {
30329 XRectangle r;
30330 int mouse_face_overwritten_p = 0;
30331
30332 TRACE ((stderr, "expose_frame "));
30333
30334 /* No need to redraw if frame will be redrawn soon. */
30335 if (FRAME_GARBAGED_P (f))
30336 {
30337 TRACE ((stderr, " garbaged\n"));
30338 return;
30339 }
30340
30341 /* If basic faces haven't been realized yet, there is no point in
30342 trying to redraw anything. This can happen when we get an expose
30343 event while Emacs is starting, e.g. by moving another window. */
30344 if (FRAME_FACE_CACHE (f) == NULL
30345 || FRAME_FACE_CACHE (f)->used < BASIC_FACE_ID_SENTINEL)
30346 {
30347 TRACE ((stderr, " no faces\n"));
30348 return;
30349 }
30350
30351 if (w == 0 || h == 0)
30352 {
30353 r.x = r.y = 0;
30354 r.width = FRAME_TEXT_WIDTH (f);
30355 r.height = FRAME_TEXT_HEIGHT (f);
30356 }
30357 else
30358 {
30359 r.x = x;
30360 r.y = y;
30361 r.width = w;
30362 r.height = h;
30363 }
30364
30365 TRACE ((stderr, "(%d, %d, %d, %d)\n", r.x, r.y, r.width, r.height));
30366 mouse_face_overwritten_p = expose_window_tree (XWINDOW (f->root_window), &r);
30367
30368 #if ! defined (USE_GTK) && ! defined (HAVE_NS)
30369 if (WINDOWP (f->tool_bar_window))
30370 mouse_face_overwritten_p
30371 |= expose_window (XWINDOW (f->tool_bar_window), &r);
30372 #endif
30373
30374 #ifdef HAVE_X_WINDOWS
30375 #ifndef MSDOS
30376 #if ! defined (USE_X_TOOLKIT) && ! defined (USE_GTK)
30377 if (WINDOWP (f->menu_bar_window))
30378 mouse_face_overwritten_p
30379 |= expose_window (XWINDOW (f->menu_bar_window), &r);
30380 #endif /* not USE_X_TOOLKIT and not USE_GTK */
30381 #endif
30382 #endif
30383
30384 /* Some window managers support a focus-follows-mouse style with
30385 delayed raising of frames. Imagine a partially obscured frame,
30386 and moving the mouse into partially obscured mouse-face on that
30387 frame. The visible part of the mouse-face will be highlighted,
30388 then the WM raises the obscured frame. With at least one WM, KDE
30389 2.1, Emacs is not getting any event for the raising of the frame
30390 (even tried with SubstructureRedirectMask), only Expose events.
30391 These expose events will draw text normally, i.e. not
30392 highlighted. Which means we must redo the highlight here.
30393 Subsume it under ``we love X''. --gerd 2001-08-15 */
30394 /* Included in Windows version because Windows most likely does not
30395 do the right thing if any third party tool offers
30396 focus-follows-mouse with delayed raise. --jason 2001-10-12 */
30397 if (mouse_face_overwritten_p && !FRAME_GARBAGED_P (f))
30398 {
30399 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
30400 if (f == hlinfo->mouse_face_mouse_frame)
30401 {
30402 int mouse_x = hlinfo->mouse_face_mouse_x;
30403 int mouse_y = hlinfo->mouse_face_mouse_y;
30404 clear_mouse_face (hlinfo);
30405 note_mouse_highlight (f, mouse_x, mouse_y);
30406 }
30407 }
30408 }
30409
30410
30411 /* EXPORT:
30412 Determine the intersection of two rectangles R1 and R2. Return
30413 the intersection in *RESULT. Value is non-zero if RESULT is not
30414 empty. */
30415
30416 int
30417 x_intersect_rectangles (XRectangle *r1, XRectangle *r2, XRectangle *result)
30418 {
30419 XRectangle *left, *right;
30420 XRectangle *upper, *lower;
30421 int intersection_p = 0;
30422
30423 /* Rearrange so that R1 is the left-most rectangle. */
30424 if (r1->x < r2->x)
30425 left = r1, right = r2;
30426 else
30427 left = r2, right = r1;
30428
30429 /* X0 of the intersection is right.x0, if this is inside R1,
30430 otherwise there is no intersection. */
30431 if (right->x <= left->x + left->width)
30432 {
30433 result->x = right->x;
30434
30435 /* The right end of the intersection is the minimum of
30436 the right ends of left and right. */
30437 result->width = (min (left->x + left->width, right->x + right->width)
30438 - result->x);
30439
30440 /* Same game for Y. */
30441 if (r1->y < r2->y)
30442 upper = r1, lower = r2;
30443 else
30444 upper = r2, lower = r1;
30445
30446 /* The upper end of the intersection is lower.y0, if this is inside
30447 of upper. Otherwise, there is no intersection. */
30448 if (lower->y <= upper->y + upper->height)
30449 {
30450 result->y = lower->y;
30451
30452 /* The lower end of the intersection is the minimum of the lower
30453 ends of upper and lower. */
30454 result->height = (min (lower->y + lower->height,
30455 upper->y + upper->height)
30456 - result->y);
30457 intersection_p = 1;
30458 }
30459 }
30460
30461 return intersection_p;
30462 }
30463
30464 #endif /* HAVE_WINDOW_SYSTEM */
30465
30466 \f
30467 /***********************************************************************
30468 Initialization
30469 ***********************************************************************/
30470
30471 void
30472 syms_of_xdisp (void)
30473 {
30474 Vwith_echo_area_save_vector = Qnil;
30475 staticpro (&Vwith_echo_area_save_vector);
30476
30477 Vmessage_stack = Qnil;
30478 staticpro (&Vmessage_stack);
30479
30480 /* Non-nil means don't actually do any redisplay. */
30481 DEFSYM (Qinhibit_redisplay, "inhibit-redisplay");
30482
30483 DEFSYM (Qredisplay_internal, "redisplay_internal (C function)");
30484
30485 message_dolog_marker1 = Fmake_marker ();
30486 staticpro (&message_dolog_marker1);
30487 message_dolog_marker2 = Fmake_marker ();
30488 staticpro (&message_dolog_marker2);
30489 message_dolog_marker3 = Fmake_marker ();
30490 staticpro (&message_dolog_marker3);
30491
30492 #ifdef GLYPH_DEBUG
30493 defsubr (&Sdump_frame_glyph_matrix);
30494 defsubr (&Sdump_glyph_matrix);
30495 defsubr (&Sdump_glyph_row);
30496 defsubr (&Sdump_tool_bar_row);
30497 defsubr (&Strace_redisplay);
30498 defsubr (&Strace_to_stderr);
30499 #endif
30500 #ifdef HAVE_WINDOW_SYSTEM
30501 defsubr (&Stool_bar_height);
30502 defsubr (&Slookup_image_map);
30503 #endif
30504 defsubr (&Sline_pixel_height);
30505 defsubr (&Sformat_mode_line);
30506 defsubr (&Sinvisible_p);
30507 defsubr (&Scurrent_bidi_paragraph_direction);
30508 defsubr (&Swindow_text_pixel_size);
30509 defsubr (&Smove_point_visually);
30510 defsubr (&Sbidi_find_overridden_directionality);
30511
30512 DEFSYM (Qmenu_bar_update_hook, "menu-bar-update-hook");
30513 DEFSYM (Qoverriding_terminal_local_map, "overriding-terminal-local-map");
30514 DEFSYM (Qoverriding_local_map, "overriding-local-map");
30515 DEFSYM (Qwindow_scroll_functions, "window-scroll-functions");
30516 DEFSYM (Qwindow_text_change_functions, "window-text-change-functions");
30517 DEFSYM (Qredisplay_end_trigger_functions, "redisplay-end-trigger-functions");
30518 DEFSYM (Qinhibit_point_motion_hooks, "inhibit-point-motion-hooks");
30519 DEFSYM (Qeval, "eval");
30520 DEFSYM (QCdata, ":data");
30521
30522 /* Names of text properties relevant for redisplay. */
30523 DEFSYM (Qdisplay, "display");
30524 DEFSYM (Qspace_width, "space-width");
30525 DEFSYM (Qraise, "raise");
30526 DEFSYM (Qslice, "slice");
30527 DEFSYM (Qspace, "space");
30528 DEFSYM (Qmargin, "margin");
30529 DEFSYM (Qpointer, "pointer");
30530 DEFSYM (Qleft_margin, "left-margin");
30531 DEFSYM (Qright_margin, "right-margin");
30532 DEFSYM (Qcenter, "center");
30533 DEFSYM (Qline_height, "line-height");
30534 DEFSYM (QCalign_to, ":align-to");
30535 DEFSYM (QCrelative_width, ":relative-width");
30536 DEFSYM (QCrelative_height, ":relative-height");
30537 DEFSYM (QCeval, ":eval");
30538 DEFSYM (QCpropertize, ":propertize");
30539 DEFSYM (QCfile, ":file");
30540 DEFSYM (Qfontified, "fontified");
30541 DEFSYM (Qfontification_functions, "fontification-functions");
30542
30543 /* Name of the face used to highlight trailing whitespace. */
30544 DEFSYM (Qtrailing_whitespace, "trailing-whitespace");
30545
30546 /* Name and number of the face used to highlight escape glyphs. */
30547 DEFSYM (Qescape_glyph, "escape-glyph");
30548
30549 /* Name and number of the face used to highlight non-breaking spaces. */
30550 DEFSYM (Qnobreak_space, "nobreak-space");
30551
30552 /* The symbol 'image' which is the car of the lists used to represent
30553 images in Lisp. Also a tool bar style. */
30554 DEFSYM (Qimage, "image");
30555
30556 /* Tool bar styles. */
30557 DEFSYM (Qtext, "text");
30558 DEFSYM (Qboth, "both");
30559 DEFSYM (Qboth_horiz, "both-horiz");
30560 DEFSYM (Qtext_image_horiz, "text-image-horiz");
30561
30562 /* The image map types. */
30563 DEFSYM (QCmap, ":map");
30564 DEFSYM (QCpointer, ":pointer");
30565 DEFSYM (Qrect, "rect");
30566 DEFSYM (Qcircle, "circle");
30567 DEFSYM (Qpoly, "poly");
30568
30569 /* The symbol `inhibit-menubar-update' and its DEFVAR_BOOL variable. */
30570 DEFSYM (Qinhibit_menubar_update, "inhibit-menubar-update");
30571 DEFSYM (Qmessage_truncate_lines, "message-truncate-lines");
30572
30573 DEFSYM (Qgrow_only, "grow-only");
30574 DEFSYM (Qinhibit_eval_during_redisplay, "inhibit-eval-during-redisplay");
30575 DEFSYM (Qposition, "position");
30576 DEFSYM (Qbuffer_position, "buffer-position");
30577 DEFSYM (Qobject, "object");
30578
30579 /* Cursor shapes. */
30580 DEFSYM (Qbar, "bar");
30581 DEFSYM (Qhbar, "hbar");
30582 DEFSYM (Qbox, "box");
30583 DEFSYM (Qhollow, "hollow");
30584
30585 /* Pointer shapes. */
30586 DEFSYM (Qhand, "hand");
30587 DEFSYM (Qarrow, "arrow");
30588 /* also Qtext */
30589
30590 DEFSYM (Qinhibit_free_realized_faces, "inhibit-free-realized-faces");
30591
30592 list_of_error = list1 (list2 (intern_c_string ("error"),
30593 intern_c_string ("void-variable")));
30594 staticpro (&list_of_error);
30595
30596 /* Values of those variables at last redisplay are stored as
30597 properties on 'overlay-arrow-position' symbol. However, if
30598 Voverlay_arrow_position is a marker, last-arrow-position is its
30599 numerical position. */
30600 DEFSYM (Qlast_arrow_position, "last-arrow-position");
30601 DEFSYM (Qlast_arrow_string, "last-arrow-string");
30602
30603 /* Alternative overlay-arrow-string and overlay-arrow-bitmap
30604 properties on a symbol in overlay-arrow-variable-list. */
30605 DEFSYM (Qoverlay_arrow_string, "overlay-arrow-string");
30606 DEFSYM (Qoverlay_arrow_bitmap, "overlay-arrow-bitmap");
30607
30608 echo_buffer[0] = echo_buffer[1] = Qnil;
30609 staticpro (&echo_buffer[0]);
30610 staticpro (&echo_buffer[1]);
30611
30612 echo_area_buffer[0] = echo_area_buffer[1] = Qnil;
30613 staticpro (&echo_area_buffer[0]);
30614 staticpro (&echo_area_buffer[1]);
30615
30616 Vmessages_buffer_name = build_pure_c_string ("*Messages*");
30617 staticpro (&Vmessages_buffer_name);
30618
30619 mode_line_proptrans_alist = Qnil;
30620 staticpro (&mode_line_proptrans_alist);
30621 mode_line_string_list = Qnil;
30622 staticpro (&mode_line_string_list);
30623 mode_line_string_face = Qnil;
30624 staticpro (&mode_line_string_face);
30625 mode_line_string_face_prop = Qnil;
30626 staticpro (&mode_line_string_face_prop);
30627 Vmode_line_unwind_vector = Qnil;
30628 staticpro (&Vmode_line_unwind_vector);
30629
30630 DEFSYM (Qmode_line_default_help_echo, "mode-line-default-help-echo");
30631
30632 help_echo_string = Qnil;
30633 staticpro (&help_echo_string);
30634 help_echo_object = Qnil;
30635 staticpro (&help_echo_object);
30636 help_echo_window = Qnil;
30637 staticpro (&help_echo_window);
30638 previous_help_echo_string = Qnil;
30639 staticpro (&previous_help_echo_string);
30640 help_echo_pos = -1;
30641
30642 DEFSYM (Qright_to_left, "right-to-left");
30643 DEFSYM (Qleft_to_right, "left-to-right");
30644 defsubr (&Sbidi_resolved_levels);
30645
30646 #ifdef HAVE_WINDOW_SYSTEM
30647 DEFVAR_BOOL ("x-stretch-cursor", x_stretch_cursor_p,
30648 doc: /* Non-nil means draw block cursor as wide as the glyph under it.
30649 For example, if a block cursor is over a tab, it will be drawn as
30650 wide as that tab on the display. */);
30651 x_stretch_cursor_p = 0;
30652 #endif
30653
30654 DEFVAR_LISP ("show-trailing-whitespace", Vshow_trailing_whitespace,
30655 doc: /* Non-nil means highlight trailing whitespace.
30656 The face used for trailing whitespace is `trailing-whitespace'. */);
30657 Vshow_trailing_whitespace = Qnil;
30658
30659 DEFVAR_LISP ("nobreak-char-display", Vnobreak_char_display,
30660 doc: /* Control highlighting of non-ASCII space and hyphen chars.
30661 If the value is t, Emacs highlights non-ASCII chars which have the
30662 same appearance as an ASCII space or hyphen, using the `nobreak-space'
30663 or `escape-glyph' face respectively.
30664
30665 U+00A0 (no-break space), U+00AD (soft hyphen), U+2010 (hyphen), and
30666 U+2011 (non-breaking hyphen) are affected.
30667
30668 Any other non-nil value means to display these characters as a escape
30669 glyph followed by an ordinary space or hyphen.
30670
30671 A value of nil means no special handling of these characters. */);
30672 Vnobreak_char_display = Qt;
30673
30674 DEFVAR_LISP ("void-text-area-pointer", Vvoid_text_area_pointer,
30675 doc: /* The pointer shape to show in void text areas.
30676 A value of nil means to show the text pointer. Other options are
30677 `arrow', `text', `hand', `vdrag', `hdrag', `nhdrag', `modeline', and
30678 `hourglass'. */);
30679 Vvoid_text_area_pointer = Qarrow;
30680
30681 DEFVAR_LISP ("inhibit-redisplay", Vinhibit_redisplay,
30682 doc: /* Non-nil means don't actually do any redisplay.
30683 This is used for internal purposes. */);
30684 Vinhibit_redisplay = Qnil;
30685
30686 DEFVAR_LISP ("global-mode-string", Vglobal_mode_string,
30687 doc: /* String (or mode line construct) included (normally) in `mode-line-format'. */);
30688 Vglobal_mode_string = Qnil;
30689
30690 DEFVAR_LISP ("overlay-arrow-position", Voverlay_arrow_position,
30691 doc: /* Marker for where to display an arrow on top of the buffer text.
30692 This must be the beginning of a line in order to work.
30693 See also `overlay-arrow-string'. */);
30694 Voverlay_arrow_position = Qnil;
30695
30696 DEFVAR_LISP ("overlay-arrow-string", Voverlay_arrow_string,
30697 doc: /* String to display as an arrow in non-window frames.
30698 See also `overlay-arrow-position'. */);
30699 Voverlay_arrow_string = build_pure_c_string ("=>");
30700
30701 DEFVAR_LISP ("overlay-arrow-variable-list", Voverlay_arrow_variable_list,
30702 doc: /* List of variables (symbols) which hold markers for overlay arrows.
30703 The symbols on this list are examined during redisplay to determine
30704 where to display overlay arrows. */);
30705 Voverlay_arrow_variable_list
30706 = list1 (intern_c_string ("overlay-arrow-position"));
30707
30708 DEFVAR_INT ("scroll-step", emacs_scroll_step,
30709 doc: /* The number of lines to try scrolling a window by when point moves out.
30710 If that fails to bring point back on frame, point is centered instead.
30711 If this is zero, point is always centered after it moves off frame.
30712 If you want scrolling to always be a line at a time, you should set
30713 `scroll-conservatively' to a large value rather than set this to 1. */);
30714
30715 DEFVAR_INT ("scroll-conservatively", scroll_conservatively,
30716 doc: /* Scroll up to this many lines, to bring point back on screen.
30717 If point moves off-screen, redisplay will scroll by up to
30718 `scroll-conservatively' lines in order to bring point just barely
30719 onto the screen again. If that cannot be done, then redisplay
30720 recenters point as usual.
30721
30722 If the value is greater than 100, redisplay will never recenter point,
30723 but will always scroll just enough text to bring point into view, even
30724 if you move far away.
30725
30726 A value of zero means always recenter point if it moves off screen. */);
30727 scroll_conservatively = 0;
30728
30729 DEFVAR_INT ("scroll-margin", scroll_margin,
30730 doc: /* Number of lines of margin at the top and bottom of a window.
30731 Recenter the window whenever point gets within this many lines
30732 of the top or bottom of the window. */);
30733 scroll_margin = 0;
30734
30735 DEFVAR_LISP ("display-pixels-per-inch", Vdisplay_pixels_per_inch,
30736 doc: /* Pixels per inch value for non-window system displays.
30737 Value is a number or a cons (WIDTH-DPI . HEIGHT-DPI). */);
30738 Vdisplay_pixels_per_inch = make_float (72.0);
30739
30740 #ifdef GLYPH_DEBUG
30741 DEFVAR_INT ("debug-end-pos", debug_end_pos, doc: /* Don't ask. */);
30742 #endif
30743
30744 DEFVAR_LISP ("truncate-partial-width-windows",
30745 Vtruncate_partial_width_windows,
30746 doc: /* Non-nil means truncate lines in windows narrower than the frame.
30747 For an integer value, truncate lines in each window narrower than the
30748 full frame width, provided the window width is less than that integer;
30749 otherwise, respect the value of `truncate-lines'.
30750
30751 For any other non-nil value, truncate lines in all windows that do
30752 not span the full frame width.
30753
30754 A value of nil means to respect the value of `truncate-lines'.
30755
30756 If `word-wrap' is enabled, you might want to reduce this. */);
30757 Vtruncate_partial_width_windows = make_number (50);
30758
30759 DEFVAR_LISP ("line-number-display-limit", Vline_number_display_limit,
30760 doc: /* Maximum buffer size for which line number should be displayed.
30761 If the buffer is bigger than this, the line number does not appear
30762 in the mode line. A value of nil means no limit. */);
30763 Vline_number_display_limit = Qnil;
30764
30765 DEFVAR_INT ("line-number-display-limit-width",
30766 line_number_display_limit_width,
30767 doc: /* Maximum line width (in characters) for line number display.
30768 If the average length of the lines near point is bigger than this, then the
30769 line number may be omitted from the mode line. */);
30770 line_number_display_limit_width = 200;
30771
30772 DEFVAR_BOOL ("highlight-nonselected-windows", highlight_nonselected_windows,
30773 doc: /* Non-nil means highlight region even in nonselected windows. */);
30774 highlight_nonselected_windows = 0;
30775
30776 DEFVAR_BOOL ("multiple-frames", multiple_frames,
30777 doc: /* Non-nil if more than one frame is visible on this display.
30778 Minibuffer-only frames don't count, but iconified frames do.
30779 This variable is not guaranteed to be accurate except while processing
30780 `frame-title-format' and `icon-title-format'. */);
30781
30782 DEFVAR_LISP ("frame-title-format", Vframe_title_format,
30783 doc: /* Template for displaying the title bar of visible frames.
30784 \(Assuming the window manager supports this feature.)
30785
30786 This variable has the same structure as `mode-line-format', except that
30787 the %c and %l constructs are ignored. It is used only on frames for
30788 which no explicit name has been set \(see `modify-frame-parameters'). */);
30789
30790 DEFVAR_LISP ("icon-title-format", Vicon_title_format,
30791 doc: /* Template for displaying the title bar of an iconified frame.
30792 \(Assuming the window manager supports this feature.)
30793 This variable has the same structure as `mode-line-format' (which see),
30794 and is used only on frames for which no explicit name has been set
30795 \(see `modify-frame-parameters'). */);
30796 Vicon_title_format
30797 = Vframe_title_format
30798 = listn (CONSTYPE_PURE, 3,
30799 intern_c_string ("multiple-frames"),
30800 build_pure_c_string ("%b"),
30801 listn (CONSTYPE_PURE, 4,
30802 empty_unibyte_string,
30803 intern_c_string ("invocation-name"),
30804 build_pure_c_string ("@"),
30805 intern_c_string ("system-name")));
30806
30807 DEFVAR_LISP ("message-log-max", Vmessage_log_max,
30808 doc: /* Maximum number of lines to keep in the message log buffer.
30809 If nil, disable message logging. If t, log messages but don't truncate
30810 the buffer when it becomes large. */);
30811 Vmessage_log_max = make_number (1000);
30812
30813 DEFVAR_LISP ("window-size-change-functions", Vwindow_size_change_functions,
30814 doc: /* Functions called before redisplay, if window sizes have changed.
30815 The value should be a list of functions that take one argument.
30816 Just before redisplay, for each frame, if any of its windows have changed
30817 size since the last redisplay, or have been split or deleted,
30818 all the functions in the list are called, with the frame as argument. */);
30819 Vwindow_size_change_functions = Qnil;
30820
30821 DEFVAR_LISP ("window-scroll-functions", Vwindow_scroll_functions,
30822 doc: /* List of functions to call before redisplaying a window with scrolling.
30823 Each function is called with two arguments, the window and its new
30824 display-start position.
30825 These functions are called whenever the `window-start' marker is modified,
30826 either to point into another buffer (e.g. via `set-window-buffer') or another
30827 place in the same buffer.
30828 Note that the value of `window-end' is not valid when these functions are
30829 called.
30830
30831 Warning: Do not use this feature to alter the way the window
30832 is scrolled. It is not designed for that, and such use probably won't
30833 work. */);
30834 Vwindow_scroll_functions = Qnil;
30835
30836 DEFVAR_LISP ("window-text-change-functions",
30837 Vwindow_text_change_functions,
30838 doc: /* Functions to call in redisplay when text in the window might change. */);
30839 Vwindow_text_change_functions = Qnil;
30840
30841 DEFVAR_LISP ("redisplay-end-trigger-functions", Vredisplay_end_trigger_functions,
30842 doc: /* Functions called when redisplay of a window reaches the end trigger.
30843 Each function is called with two arguments, the window and the end trigger value.
30844 See `set-window-redisplay-end-trigger'. */);
30845 Vredisplay_end_trigger_functions = Qnil;
30846
30847 DEFVAR_LISP ("mouse-autoselect-window", Vmouse_autoselect_window,
30848 doc: /* Non-nil means autoselect window with mouse pointer.
30849 If nil, do not autoselect windows.
30850 A positive number means delay autoselection by that many seconds: a
30851 window is autoselected only after the mouse has remained in that
30852 window for the duration of the delay.
30853 A negative number has a similar effect, but causes windows to be
30854 autoselected only after the mouse has stopped moving. \(Because of
30855 the way Emacs compares mouse events, you will occasionally wait twice
30856 that time before the window gets selected.\)
30857 Any other value means to autoselect window instantaneously when the
30858 mouse pointer enters it.
30859
30860 Autoselection selects the minibuffer only if it is active, and never
30861 unselects the minibuffer if it is active.
30862
30863 When customizing this variable make sure that the actual value of
30864 `focus-follows-mouse' matches the behavior of your window manager. */);
30865 Vmouse_autoselect_window = Qnil;
30866
30867 DEFVAR_LISP ("auto-resize-tool-bars", Vauto_resize_tool_bars,
30868 doc: /* Non-nil means automatically resize tool-bars.
30869 This dynamically changes the tool-bar's height to the minimum height
30870 that is needed to make all tool-bar items visible.
30871 If value is `grow-only', the tool-bar's height is only increased
30872 automatically; to decrease the tool-bar height, use \\[recenter]. */);
30873 Vauto_resize_tool_bars = Qt;
30874
30875 DEFVAR_BOOL ("auto-raise-tool-bar-buttons", auto_raise_tool_bar_buttons_p,
30876 doc: /* Non-nil means raise tool-bar buttons when the mouse moves over them. */);
30877 auto_raise_tool_bar_buttons_p = 1;
30878
30879 DEFVAR_BOOL ("make-cursor-line-fully-visible", make_cursor_line_fully_visible_p,
30880 doc: /* Non-nil means to scroll (recenter) cursor line if it is not fully visible. */);
30881 make_cursor_line_fully_visible_p = 1;
30882
30883 DEFVAR_LISP ("tool-bar-border", Vtool_bar_border,
30884 doc: /* Border below tool-bar in pixels.
30885 If an integer, use it as the height of the border.
30886 If it is one of `internal-border-width' or `border-width', use the
30887 value of the corresponding frame parameter.
30888 Otherwise, no border is added below the tool-bar. */);
30889 Vtool_bar_border = Qinternal_border_width;
30890
30891 DEFVAR_LISP ("tool-bar-button-margin", Vtool_bar_button_margin,
30892 doc: /* Margin around tool-bar buttons in pixels.
30893 If an integer, use that for both horizontal and vertical margins.
30894 Otherwise, value should be a pair of integers `(HORZ . VERT)' with
30895 HORZ specifying the horizontal margin, and VERT specifying the
30896 vertical margin. */);
30897 Vtool_bar_button_margin = make_number (DEFAULT_TOOL_BAR_BUTTON_MARGIN);
30898
30899 DEFVAR_INT ("tool-bar-button-relief", tool_bar_button_relief,
30900 doc: /* Relief thickness of tool-bar buttons. */);
30901 tool_bar_button_relief = DEFAULT_TOOL_BAR_BUTTON_RELIEF;
30902
30903 DEFVAR_LISP ("tool-bar-style", Vtool_bar_style,
30904 doc: /* Tool bar style to use.
30905 It can be one of
30906 image - show images only
30907 text - show text only
30908 both - show both, text below image
30909 both-horiz - show text to the right of the image
30910 text-image-horiz - show text to the left of the image
30911 any other - use system default or image if no system default.
30912
30913 This variable only affects the GTK+ toolkit version of Emacs. */);
30914 Vtool_bar_style = Qnil;
30915
30916 DEFVAR_INT ("tool-bar-max-label-size", tool_bar_max_label_size,
30917 doc: /* Maximum number of characters a label can have to be shown.
30918 The tool bar style must also show labels for this to have any effect, see
30919 `tool-bar-style'. */);
30920 tool_bar_max_label_size = DEFAULT_TOOL_BAR_LABEL_SIZE;
30921
30922 DEFVAR_LISP ("fontification-functions", Vfontification_functions,
30923 doc: /* List of functions to call to fontify regions of text.
30924 Each function is called with one argument POS. Functions must
30925 fontify a region starting at POS in the current buffer, and give
30926 fontified regions the property `fontified'. */);
30927 Vfontification_functions = Qnil;
30928 Fmake_variable_buffer_local (Qfontification_functions);
30929
30930 DEFVAR_BOOL ("unibyte-display-via-language-environment",
30931 unibyte_display_via_language_environment,
30932 doc: /* Non-nil means display unibyte text according to language environment.
30933 Specifically, this means that raw bytes in the range 160-255 decimal
30934 are displayed by converting them to the equivalent multibyte characters
30935 according to the current language environment. As a result, they are
30936 displayed according to the current fontset.
30937
30938 Note that this variable affects only how these bytes are displayed,
30939 but does not change the fact they are interpreted as raw bytes. */);
30940 unibyte_display_via_language_environment = 0;
30941
30942 DEFVAR_LISP ("max-mini-window-height", Vmax_mini_window_height,
30943 doc: /* Maximum height for resizing mini-windows (the minibuffer and the echo area).
30944 If a float, it specifies a fraction of the mini-window frame's height.
30945 If an integer, it specifies a number of lines. */);
30946 Vmax_mini_window_height = make_float (0.25);
30947
30948 DEFVAR_LISP ("resize-mini-windows", Vresize_mini_windows,
30949 doc: /* How to resize mini-windows (the minibuffer and the echo area).
30950 A value of nil means don't automatically resize mini-windows.
30951 A value of t means resize them to fit the text displayed in them.
30952 A value of `grow-only', the default, means let mini-windows grow only;
30953 they return to their normal size when the minibuffer is closed, or the
30954 echo area becomes empty. */);
30955 Vresize_mini_windows = Qgrow_only;
30956
30957 DEFVAR_LISP ("blink-cursor-alist", Vblink_cursor_alist,
30958 doc: /* Alist specifying how to blink the cursor off.
30959 Each element has the form (ON-STATE . OFF-STATE). Whenever the
30960 `cursor-type' frame-parameter or variable equals ON-STATE,
30961 comparing using `equal', Emacs uses OFF-STATE to specify
30962 how to blink it off. ON-STATE and OFF-STATE are values for
30963 the `cursor-type' frame parameter.
30964
30965 If a frame's ON-STATE has no entry in this list,
30966 the frame's other specifications determine how to blink the cursor off. */);
30967 Vblink_cursor_alist = Qnil;
30968
30969 DEFVAR_BOOL ("auto-hscroll-mode", automatic_hscrolling_p,
30970 doc: /* Allow or disallow automatic horizontal scrolling of windows.
30971 If non-nil, windows are automatically scrolled horizontally to make
30972 point visible. */);
30973 automatic_hscrolling_p = 1;
30974 DEFSYM (Qauto_hscroll_mode, "auto-hscroll-mode");
30975
30976 DEFVAR_INT ("hscroll-margin", hscroll_margin,
30977 doc: /* How many columns away from the window edge point is allowed to get
30978 before automatic hscrolling will horizontally scroll the window. */);
30979 hscroll_margin = 5;
30980
30981 DEFVAR_LISP ("hscroll-step", Vhscroll_step,
30982 doc: /* How many columns to scroll the window when point gets too close to the edge.
30983 When point is less than `hscroll-margin' columns from the window
30984 edge, automatic hscrolling will scroll the window by the amount of columns
30985 determined by this variable. If its value is a positive integer, scroll that
30986 many columns. If it's a positive floating-point number, it specifies the
30987 fraction of the window's width to scroll. If it's nil or zero, point will be
30988 centered horizontally after the scroll. Any other value, including negative
30989 numbers, are treated as if the value were zero.
30990
30991 Automatic hscrolling always moves point outside the scroll margin, so if
30992 point was more than scroll step columns inside the margin, the window will
30993 scroll more than the value given by the scroll step.
30994
30995 Note that the lower bound for automatic hscrolling specified by `scroll-left'
30996 and `scroll-right' overrides this variable's effect. */);
30997 Vhscroll_step = make_number (0);
30998
30999 DEFVAR_BOOL ("message-truncate-lines", message_truncate_lines,
31000 doc: /* If non-nil, messages are truncated instead of resizing the echo area.
31001 Bind this around calls to `message' to let it take effect. */);
31002 message_truncate_lines = 0;
31003
31004 DEFVAR_LISP ("menu-bar-update-hook", Vmenu_bar_update_hook,
31005 doc: /* Normal hook run to update the menu bar definitions.
31006 Redisplay runs this hook before it redisplays the menu bar.
31007 This is used to update menus such as Buffers, whose contents depend on
31008 various data. */);
31009 Vmenu_bar_update_hook = Qnil;
31010
31011 DEFVAR_LISP ("menu-updating-frame", Vmenu_updating_frame,
31012 doc: /* Frame for which we are updating a menu.
31013 The enable predicate for a menu binding should check this variable. */);
31014 Vmenu_updating_frame = Qnil;
31015
31016 DEFVAR_BOOL ("inhibit-menubar-update", inhibit_menubar_update,
31017 doc: /* Non-nil means don't update menu bars. Internal use only. */);
31018 inhibit_menubar_update = 0;
31019
31020 DEFVAR_LISP ("wrap-prefix", Vwrap_prefix,
31021 doc: /* Prefix prepended to all continuation lines at display time.
31022 The value may be a string, an image, or a stretch-glyph; it is
31023 interpreted in the same way as the value of a `display' text property.
31024
31025 This variable is overridden by any `wrap-prefix' text or overlay
31026 property.
31027
31028 To add a prefix to non-continuation lines, use `line-prefix'. */);
31029 Vwrap_prefix = Qnil;
31030 DEFSYM (Qwrap_prefix, "wrap-prefix");
31031 Fmake_variable_buffer_local (Qwrap_prefix);
31032
31033 DEFVAR_LISP ("line-prefix", Vline_prefix,
31034 doc: /* Prefix prepended to all non-continuation lines at display time.
31035 The value may be a string, an image, or a stretch-glyph; it is
31036 interpreted in the same way as the value of a `display' text property.
31037
31038 This variable is overridden by any `line-prefix' text or overlay
31039 property.
31040
31041 To add a prefix to continuation lines, use `wrap-prefix'. */);
31042 Vline_prefix = Qnil;
31043 DEFSYM (Qline_prefix, "line-prefix");
31044 Fmake_variable_buffer_local (Qline_prefix);
31045
31046 DEFVAR_BOOL ("inhibit-eval-during-redisplay", inhibit_eval_during_redisplay,
31047 doc: /* Non-nil means don't eval Lisp during redisplay. */);
31048 inhibit_eval_during_redisplay = 0;
31049
31050 DEFVAR_BOOL ("inhibit-free-realized-faces", inhibit_free_realized_faces,
31051 doc: /* Non-nil means don't free realized faces. Internal use only. */);
31052 inhibit_free_realized_faces = 0;
31053
31054 DEFVAR_BOOL ("inhibit-bidi-mirroring", inhibit_bidi_mirroring,
31055 doc: /* Non-nil means don't mirror characters even when bidi context requires that.
31056 Intended for use during debugging and for testing bidi display;
31057 see biditest.el in the test suite. */);
31058 inhibit_bidi_mirroring = 0;
31059
31060 #ifdef GLYPH_DEBUG
31061 DEFVAR_BOOL ("inhibit-try-window-id", inhibit_try_window_id,
31062 doc: /* Inhibit try_window_id display optimization. */);
31063 inhibit_try_window_id = 0;
31064
31065 DEFVAR_BOOL ("inhibit-try-window-reusing", inhibit_try_window_reusing,
31066 doc: /* Inhibit try_window_reusing display optimization. */);
31067 inhibit_try_window_reusing = 0;
31068
31069 DEFVAR_BOOL ("inhibit-try-cursor-movement", inhibit_try_cursor_movement,
31070 doc: /* Inhibit try_cursor_movement display optimization. */);
31071 inhibit_try_cursor_movement = 0;
31072 #endif /* GLYPH_DEBUG */
31073
31074 DEFVAR_INT ("overline-margin", overline_margin,
31075 doc: /* Space between overline and text, in pixels.
31076 The default value is 2: the height of the overline (1 pixel) plus 1 pixel
31077 margin to the character height. */);
31078 overline_margin = 2;
31079
31080 DEFVAR_INT ("underline-minimum-offset",
31081 underline_minimum_offset,
31082 doc: /* Minimum distance between baseline and underline.
31083 This can improve legibility of underlined text at small font sizes,
31084 particularly when using variable `x-use-underline-position-properties'
31085 with fonts that specify an UNDERLINE_POSITION relatively close to the
31086 baseline. The default value is 1. */);
31087 underline_minimum_offset = 1;
31088
31089 DEFVAR_BOOL ("display-hourglass", display_hourglass_p,
31090 doc: /* Non-nil means show an hourglass pointer, when Emacs is busy.
31091 This feature only works when on a window system that can change
31092 cursor shapes. */);
31093 display_hourglass_p = 1;
31094
31095 DEFVAR_LISP ("hourglass-delay", Vhourglass_delay,
31096 doc: /* Seconds to wait before displaying an hourglass pointer when Emacs is busy. */);
31097 Vhourglass_delay = make_number (DEFAULT_HOURGLASS_DELAY);
31098
31099 #ifdef HAVE_WINDOW_SYSTEM
31100 hourglass_atimer = NULL;
31101 hourglass_shown_p = 0;
31102 #endif /* HAVE_WINDOW_SYSTEM */
31103
31104 /* Name of the face used to display glyphless characters. */
31105 DEFSYM (Qglyphless_char, "glyphless-char");
31106
31107 /* Method symbols for Vglyphless_char_display. */
31108 DEFSYM (Qhex_code, "hex-code");
31109 DEFSYM (Qempty_box, "empty-box");
31110 DEFSYM (Qthin_space, "thin-space");
31111 DEFSYM (Qzero_width, "zero-width");
31112
31113 DEFVAR_LISP ("pre-redisplay-function", Vpre_redisplay_function,
31114 doc: /* Function run just before redisplay.
31115 It is called with one argument, which is the set of windows that are to
31116 be redisplayed. This set can be nil (meaning, only the selected window),
31117 or t (meaning all windows). */);
31118 Vpre_redisplay_function = intern ("ignore");
31119
31120 /* Symbol for the purpose of Vglyphless_char_display. */
31121 DEFSYM (Qglyphless_char_display, "glyphless-char-display");
31122 Fput (Qglyphless_char_display, Qchar_table_extra_slots, make_number (1));
31123
31124 DEFVAR_LISP ("glyphless-char-display", Vglyphless_char_display,
31125 doc: /* Char-table defining glyphless characters.
31126 Each element, if non-nil, should be one of the following:
31127 an ASCII acronym string: display this string in a box
31128 `hex-code': display the hexadecimal code of a character in a box
31129 `empty-box': display as an empty box
31130 `thin-space': display as 1-pixel width space
31131 `zero-width': don't display
31132 An element may also be a cons cell (GRAPHICAL . TEXT), which specifies the
31133 display method for graphical terminals and text terminals respectively.
31134 GRAPHICAL and TEXT should each have one of the values listed above.
31135
31136 The char-table has one extra slot to control the display of a character for
31137 which no font is found. This slot only takes effect on graphical terminals.
31138 Its value should be an ASCII acronym string, `hex-code', `empty-box', or
31139 `thin-space'. The default is `empty-box'.
31140
31141 If a character has a non-nil entry in an active display table, the
31142 display table takes effect; in this case, Emacs does not consult
31143 `glyphless-char-display' at all. */);
31144 Vglyphless_char_display = Fmake_char_table (Qglyphless_char_display, Qnil);
31145 Fset_char_table_extra_slot (Vglyphless_char_display, make_number (0),
31146 Qempty_box);
31147
31148 DEFVAR_LISP ("debug-on-message", Vdebug_on_message,
31149 doc: /* If non-nil, debug if a message matching this regexp is displayed. */);
31150 Vdebug_on_message = Qnil;
31151
31152 DEFVAR_LISP ("redisplay--all-windows-cause", Vredisplay__all_windows_cause,
31153 doc: /* */);
31154 Vredisplay__all_windows_cause
31155 = Fmake_vector (make_number (100), make_number (0));
31156
31157 DEFVAR_LISP ("redisplay--mode-lines-cause", Vredisplay__mode_lines_cause,
31158 doc: /* */);
31159 Vredisplay__mode_lines_cause
31160 = Fmake_vector (make_number (100), make_number (0));
31161 }
31162
31163
31164 /* Initialize this module when Emacs starts. */
31165
31166 void
31167 init_xdisp (void)
31168 {
31169 CHARPOS (this_line_start_pos) = 0;
31170
31171 if (!noninteractive)
31172 {
31173 struct window *m = XWINDOW (minibuf_window);
31174 Lisp_Object frame = m->frame;
31175 struct frame *f = XFRAME (frame);
31176 Lisp_Object root = FRAME_ROOT_WINDOW (f);
31177 struct window *r = XWINDOW (root);
31178 int i;
31179
31180 echo_area_window = minibuf_window;
31181
31182 r->top_line = FRAME_TOP_MARGIN (f);
31183 r->pixel_top = r->top_line * FRAME_LINE_HEIGHT (f);
31184 r->total_cols = FRAME_COLS (f);
31185 r->pixel_width = r->total_cols * FRAME_COLUMN_WIDTH (f);
31186 r->total_lines = FRAME_TOTAL_LINES (f) - 1 - FRAME_TOP_MARGIN (f);
31187 r->pixel_height = r->total_lines * FRAME_LINE_HEIGHT (f);
31188
31189 m->top_line = FRAME_TOTAL_LINES (f) - 1;
31190 m->pixel_top = m->top_line * FRAME_LINE_HEIGHT (f);
31191 m->total_cols = FRAME_COLS (f);
31192 m->pixel_width = m->total_cols * FRAME_COLUMN_WIDTH (f);
31193 m->total_lines = 1;
31194 m->pixel_height = m->total_lines * FRAME_LINE_HEIGHT (f);
31195
31196 scratch_glyph_row.glyphs[TEXT_AREA] = scratch_glyphs;
31197 scratch_glyph_row.glyphs[TEXT_AREA + 1]
31198 = scratch_glyphs + MAX_SCRATCH_GLYPHS;
31199
31200 /* The default ellipsis glyphs `...'. */
31201 for (i = 0; i < 3; ++i)
31202 default_invis_vector[i] = make_number ('.');
31203 }
31204
31205 {
31206 /* Allocate the buffer for frame titles.
31207 Also used for `format-mode-line'. */
31208 int size = 100;
31209 mode_line_noprop_buf = xmalloc (size);
31210 mode_line_noprop_buf_end = mode_line_noprop_buf + size;
31211 mode_line_noprop_ptr = mode_line_noprop_buf;
31212 mode_line_target = MODE_LINE_DISPLAY;
31213 }
31214
31215 help_echo_showing_p = 0;
31216 }
31217
31218 #ifdef HAVE_WINDOW_SYSTEM
31219
31220 /* Platform-independent portion of hourglass implementation. */
31221
31222 /* Timer function of hourglass_atimer. */
31223
31224 static void
31225 show_hourglass (struct atimer *timer)
31226 {
31227 /* The timer implementation will cancel this timer automatically
31228 after this function has run. Set hourglass_atimer to null
31229 so that we know the timer doesn't have to be canceled. */
31230 hourglass_atimer = NULL;
31231
31232 if (!hourglass_shown_p)
31233 {
31234 Lisp_Object tail, frame;
31235
31236 block_input ();
31237
31238 FOR_EACH_FRAME (tail, frame)
31239 {
31240 struct frame *f = XFRAME (frame);
31241
31242 if (FRAME_LIVE_P (f) && FRAME_WINDOW_P (f)
31243 && FRAME_RIF (f)->show_hourglass)
31244 FRAME_RIF (f)->show_hourglass (f);
31245 }
31246
31247 hourglass_shown_p = 1;
31248 unblock_input ();
31249 }
31250 }
31251
31252 /* Cancel a currently active hourglass timer, and start a new one. */
31253
31254 void
31255 start_hourglass (void)
31256 {
31257 struct timespec delay;
31258
31259 cancel_hourglass ();
31260
31261 if (INTEGERP (Vhourglass_delay)
31262 && XINT (Vhourglass_delay) > 0)
31263 delay = make_timespec (min (XINT (Vhourglass_delay),
31264 TYPE_MAXIMUM (time_t)),
31265 0);
31266 else if (FLOATP (Vhourglass_delay)
31267 && XFLOAT_DATA (Vhourglass_delay) > 0)
31268 delay = dtotimespec (XFLOAT_DATA (Vhourglass_delay));
31269 else
31270 delay = make_timespec (DEFAULT_HOURGLASS_DELAY, 0);
31271
31272 hourglass_atimer = start_atimer (ATIMER_RELATIVE, delay,
31273 show_hourglass, NULL);
31274 }
31275
31276 /* Cancel the hourglass cursor timer if active, hide a busy cursor if
31277 shown. */
31278
31279 void
31280 cancel_hourglass (void)
31281 {
31282 if (hourglass_atimer)
31283 {
31284 cancel_atimer (hourglass_atimer);
31285 hourglass_atimer = NULL;
31286 }
31287
31288 if (hourglass_shown_p)
31289 {
31290 Lisp_Object tail, frame;
31291
31292 block_input ();
31293
31294 FOR_EACH_FRAME (tail, frame)
31295 {
31296 struct frame *f = XFRAME (frame);
31297
31298 if (FRAME_LIVE_P (f) && FRAME_WINDOW_P (f)
31299 && FRAME_RIF (f)->hide_hourglass)
31300 FRAME_RIF (f)->hide_hourglass (f);
31301 #ifdef HAVE_NTGUI
31302 /* No cursors on non GUI frames - restore to stock arrow cursor. */
31303 else if (!FRAME_W32_P (f))
31304 w32_arrow_cursor ();
31305 #endif
31306 }
31307
31308 hourglass_shown_p = 0;
31309 unblock_input ();
31310 }
31311 }
31312
31313 #endif /* HAVE_WINDOW_SYSTEM */