*** empty log message ***
[emacs/old-mirror.git] / src / xdisp.c
blob28ff03b3dea25126ab943aa74c294bc6684badea
1 /* Display generation from window structure and buffer text.
2 Copyright (C) 1985, 86, 87, 88, 93, 94, 95, 97, 98, 99, 2000, 2001, 2002
3 Free Software Foundation, Inc.
5 This file is part of GNU Emacs.
7 GNU Emacs is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
12 GNU Emacs is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNU Emacs; see the file COPYING. If not, write to
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
22 /* New redisplay written by Gerd Moellmann <gerd@gnu.org>.
24 Redisplay.
26 Emacs separates the task of updating the display from code
27 modifying global state, e.g. buffer text. This way functions
28 operating on buffers don't also have to be concerned with updating
29 the display.
31 Updating the display is triggered by the Lisp interpreter when it
32 decides it's time to do it. This is done either automatically for
33 you as part of the interpreter's command loop or as the result of
34 calling Lisp functions like `sit-for'. The C function `redisplay'
35 in xdisp.c is the only entry into the inner redisplay code. (Or,
36 let's say almost---see the description of direct update
37 operations, below.)
39 The following diagram shows how redisplay code is invoked. As you
40 can see, Lisp calls redisplay and vice versa. Under window systems
41 like X, some portions of the redisplay code are also called
42 asynchronously during mouse movement or expose events. It is very
43 important that these code parts do NOT use the C library (malloc,
44 free) because many C libraries under Unix are not reentrant. They
45 may also NOT call functions of the Lisp interpreter which could
46 change the interpreter's state. If you don't follow these rules,
47 you will encounter bugs which are very hard to explain.
49 (Direct functions, see below)
50 direct_output_for_insert,
51 direct_forward_char (dispnew.c)
52 +---------------------------------+
53 | |
54 | V
55 +--------------+ redisplay +----------------+
56 | Lisp machine |---------------->| Redisplay code |<--+
57 +--------------+ (xdisp.c) +----------------+ |
58 ^ | |
59 +----------------------------------+ |
60 Don't use this path when called |
61 asynchronously! |
63 expose_window (asynchronous) |
65 X expose events -----+
67 What does redisplay do? Obviously, it has to figure out somehow what
68 has been changed since the last time the display has been updated,
69 and to make these changes visible. Preferably it would do that in
70 a moderately intelligent way, i.e. fast.
72 Changes in buffer text can be deduced from window and buffer
73 structures, and from some global variables like `beg_unchanged' and
74 `end_unchanged'. The contents of the display are additionally
75 recorded in a `glyph matrix', a two-dimensional matrix of glyph
76 structures. Each row in such a matrix corresponds to a line on the
77 display, and each glyph in a row corresponds to a column displaying
78 a character, an image, or what else. This matrix is called the
79 `current glyph matrix' or `current matrix' in redisplay
80 terminology.
82 For buffer parts that have been changed since the last update, a
83 second glyph matrix is constructed, the so called `desired glyph
84 matrix' or short `desired matrix'. Current and desired matrix are
85 then compared to find a cheap way to update the display, e.g. by
86 reusing part of the display by scrolling lines.
89 Direct operations.
91 You will find a lot of redisplay optimizations when you start
92 looking at the innards of redisplay. The overall goal of all these
93 optimizations is to make redisplay fast because it is done
94 frequently.
96 Two optimizations are not found in xdisp.c. These are the direct
97 operations mentioned above. As the name suggests they follow a
98 different principle than the rest of redisplay. Instead of
99 building a desired matrix and then comparing it with the current
100 display, they perform their actions directly on the display and on
101 the current matrix.
103 One direct operation updates the display after one character has
104 been entered. The other one moves the cursor by one position
105 forward or backward. You find these functions under the names
106 `direct_output_for_insert' and `direct_output_forward_char' in
107 dispnew.c.
110 Desired matrices.
112 Desired matrices are always built per Emacs window. The function
113 `display_line' is the central function to look at if you are
114 interested. It constructs one row in a desired matrix given an
115 iterator structure containing both a buffer position and a
116 description of the environment in which the text is to be
117 displayed. But this is too early, read on.
119 Characters and pixmaps displayed for a range of buffer text depend
120 on various settings of buffers and windows, on overlays and text
121 properties, on display tables, on selective display. The good news
122 is that all this hairy stuff is hidden behind a small set of
123 interface functions taking an iterator structure (struct it)
124 argument.
126 Iteration over things to be displayed is then simple. It is
127 started by initializing an iterator with a call to init_iterator.
128 Calls to get_next_display_element fill the iterator structure with
129 relevant information about the next thing to display. Calls to
130 set_iterator_to_next move the iterator to the next thing.
132 Besides this, an iterator also contains information about the
133 display environment in which glyphs for display elements are to be
134 produced. It has fields for the width and height of the display,
135 the information whether long lines are truncated or continued, a
136 current X and Y position, and lots of other stuff you can better
137 see in dispextern.h.
139 Glyphs in a desired matrix are normally constructed in a loop
140 calling get_next_display_element and then produce_glyphs. The call
141 to produce_glyphs will fill the iterator structure with pixel
142 information about the element being displayed and at the same time
143 produce glyphs for it. If the display element fits on the line
144 being displayed, set_iterator_to_next is called next, otherwise the
145 glyphs produced are discarded.
148 Frame matrices.
150 That just couldn't be all, could it? What about terminal types not
151 supporting operations on sub-windows of the screen? To update the
152 display on such a terminal, window-based glyph matrices are not
153 well suited. To be able to reuse part of the display (scrolling
154 lines up and down), we must instead have a view of the whole
155 screen. This is what `frame matrices' are for. They are a trick.
157 Frames on terminals like above have a glyph pool. Windows on such
158 a frame sub-allocate their glyph memory from their frame's glyph
159 pool. The frame itself is given its own glyph matrices. By
160 coincidence---or maybe something else---rows in window glyph
161 matrices are slices of corresponding rows in frame matrices. Thus
162 writing to window matrices implicitly updates a frame matrix which
163 provides us with the view of the whole screen that we originally
164 wanted to have without having to move many bytes around. To be
165 honest, there is a little bit more done, but not much more. If you
166 plan to extend that code, take a look at dispnew.c. The function
167 build_frame_matrix is a good starting point. */
169 #include <config.h>
170 #include <stdio.h>
172 #include "lisp.h"
173 #include "keyboard.h"
174 #include "frame.h"
175 #include "window.h"
176 #include "termchar.h"
177 #include "dispextern.h"
178 #include "buffer.h"
179 #include "charset.h"
180 #include "indent.h"
181 #include "commands.h"
182 #include "macros.h"
183 #include "disptab.h"
184 #include "termhooks.h"
185 #include "intervals.h"
186 #include "coding.h"
187 #include "process.h"
188 #include "region-cache.h"
189 #include "fontset.h"
191 #ifdef HAVE_X_WINDOWS
192 #include "xterm.h"
193 #endif
194 #ifdef WINDOWSNT
195 #include "w32term.h"
196 #endif
197 #ifdef MAC_OS
198 #include "macterm.h"
199 #endif
201 #define INFINITY 10000000
203 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) || defined (MAC_OS)
204 extern void set_frame_menubar P_ ((struct frame *f, int, int));
205 extern int pending_menu_activation;
206 #endif
208 extern int interrupt_input;
209 extern int command_loop_level;
211 extern int minibuffer_auto_raise;
213 extern Lisp_Object Qface;
214 extern Lisp_Object Qmode_line, Qmode_line_inactive, Qheader_line;
216 extern Lisp_Object Voverriding_local_map;
217 extern Lisp_Object Voverriding_local_map_menu_flag;
218 extern Lisp_Object Qmenu_item;
220 Lisp_Object Qoverriding_local_map, Qoverriding_terminal_local_map;
221 Lisp_Object Qwindow_scroll_functions, Vwindow_scroll_functions;
222 Lisp_Object Qredisplay_end_trigger_functions;
223 Lisp_Object Qinhibit_point_motion_hooks;
224 Lisp_Object QCeval, Qwhen, QCfile, QCdata, QCpropertize;
225 Lisp_Object Qfontified;
226 Lisp_Object Qgrow_only;
227 Lisp_Object Qinhibit_eval_during_redisplay;
228 Lisp_Object Qbuffer_position, Qposition, Qobject;
230 /* Cursor shapes */
231 Lisp_Object Qbar, Qhbar, Qbox, Qhollow;
233 Lisp_Object Qrisky_local_variable;
235 /* Holds the list (error). */
236 Lisp_Object list_of_error;
238 /* Functions called to fontify regions of text. */
240 Lisp_Object Vfontification_functions;
241 Lisp_Object Qfontification_functions;
243 /* Non-zero means draw tool bar buttons raised when the mouse moves
244 over them. */
246 int auto_raise_tool_bar_buttons_p;
248 /* Margin around tool bar buttons in pixels. */
250 Lisp_Object Vtool_bar_button_margin;
252 /* Thickness of shadow to draw around tool bar buttons. */
254 EMACS_INT tool_bar_button_relief;
256 /* Non-zero means automatically resize tool-bars so that all tool-bar
257 items are visible, and no blank lines remain. */
259 int auto_resize_tool_bars_p;
261 /* Non-nil means don't actually do any redisplay. */
263 Lisp_Object Vinhibit_redisplay, Qinhibit_redisplay;
265 /* Non-zero means Lisp evaluation during redisplay is inhibited. */
267 int inhibit_eval_during_redisplay;
269 /* Names of text properties relevant for redisplay. */
271 Lisp_Object Qdisplay, Qrelative_width, Qalign_to;
272 extern Lisp_Object Qface, Qinvisible, Qwidth;
274 /* Symbols used in text property values. */
276 Lisp_Object Qspace, QCalign_to, QCrelative_width, QCrelative_height;
277 Lisp_Object Qleft_margin, Qright_margin, Qspace_width, Qraise;
278 Lisp_Object Qmargin;
279 extern Lisp_Object Qheight;
281 /* Non-nil means highlight trailing whitespace. */
283 Lisp_Object Vshow_trailing_whitespace;
285 /* Name of the face used to highlight trailing whitespace. */
287 Lisp_Object Qtrailing_whitespace;
289 /* The symbol `image' which is the car of the lists used to represent
290 images in Lisp. */
292 Lisp_Object Qimage;
294 /* Non-zero means print newline to stdout before next mini-buffer
295 message. */
297 int noninteractive_need_newline;
299 /* Non-zero means print newline to message log before next message. */
301 static int message_log_need_newline;
303 /* Three markers that message_dolog uses.
304 It could allocate them itself, but that causes trouble
305 in handling memory-full errors. */
306 static Lisp_Object message_dolog_marker1;
307 static Lisp_Object message_dolog_marker2;
308 static Lisp_Object message_dolog_marker3;
310 /* The buffer position of the first character appearing entirely or
311 partially on the line of the selected window which contains the
312 cursor; <= 0 if not known. Set by set_cursor_from_row, used for
313 redisplay optimization in redisplay_internal. */
315 static struct text_pos this_line_start_pos;
317 /* Number of characters past the end of the line above, including the
318 terminating newline. */
320 static struct text_pos this_line_end_pos;
322 /* The vertical positions and the height of this line. */
324 static int this_line_vpos;
325 static int this_line_y;
326 static int this_line_pixel_height;
328 /* X position at which this display line starts. Usually zero;
329 negative if first character is partially visible. */
331 static int this_line_start_x;
333 /* Buffer that this_line_.* variables are referring to. */
335 static struct buffer *this_line_buffer;
337 /* Nonzero means truncate lines in all windows less wide than the
338 frame. */
340 int truncate_partial_width_windows;
342 /* A flag to control how to display unibyte 8-bit character. */
344 int unibyte_display_via_language_environment;
346 /* Nonzero means we have more than one non-mini-buffer-only frame.
347 Not guaranteed to be accurate except while parsing
348 frame-title-format. */
350 int multiple_frames;
352 Lisp_Object Vglobal_mode_string;
354 /* Marker for where to display an arrow on top of the buffer text. */
356 Lisp_Object Voverlay_arrow_position;
358 /* String to display for the arrow. Only used on terminal frames. */
360 Lisp_Object Voverlay_arrow_string;
362 /* Values of those variables at last redisplay. However, if
363 Voverlay_arrow_position is a marker, last_arrow_position is its
364 numerical position. */
366 static Lisp_Object last_arrow_position, last_arrow_string;
368 /* Like mode-line-format, but for the title bar on a visible frame. */
370 Lisp_Object Vframe_title_format;
372 /* Like mode-line-format, but for the title bar on an iconified frame. */
374 Lisp_Object Vicon_title_format;
376 /* List of functions to call when a window's size changes. These
377 functions get one arg, a frame on which one or more windows' sizes
378 have changed. */
380 static Lisp_Object Vwindow_size_change_functions;
382 Lisp_Object Qmenu_bar_update_hook, Vmenu_bar_update_hook;
384 /* Nonzero if overlay arrow has been displayed once in this window. */
386 static int overlay_arrow_seen;
388 /* Nonzero means highlight the region even in nonselected windows. */
390 int highlight_nonselected_windows;
392 /* If cursor motion alone moves point off frame, try scrolling this
393 many lines up or down if that will bring it back. */
395 static EMACS_INT scroll_step;
397 /* Nonzero means scroll just far enough to bring point back on the
398 screen, when appropriate. */
400 static EMACS_INT scroll_conservatively;
402 /* Recenter the window whenever point gets within this many lines of
403 the top or bottom of the window. This value is translated into a
404 pixel value by multiplying it with CANON_Y_UNIT, which means that
405 there is really a fixed pixel height scroll margin. */
407 EMACS_INT scroll_margin;
409 /* Number of windows showing the buffer of the selected window (or
410 another buffer with the same base buffer). keyboard.c refers to
411 this. */
413 int buffer_shared;
415 /* Vector containing glyphs for an ellipsis `...'. */
417 static Lisp_Object default_invis_vector[3];
419 /* Zero means display the mode-line/header-line/menu-bar in the default face
420 (this slightly odd definition is for compatibility with previous versions
421 of emacs), non-zero means display them using their respective faces.
423 This variable is deprecated. */
425 int mode_line_inverse_video;
427 /* Prompt to display in front of the mini-buffer contents. */
429 Lisp_Object minibuf_prompt;
431 /* Width of current mini-buffer prompt. Only set after display_line
432 of the line that contains the prompt. */
434 int minibuf_prompt_width;
436 /* This is the window where the echo area message was displayed. It
437 is always a mini-buffer window, but it may not be the same window
438 currently active as a mini-buffer. */
440 Lisp_Object echo_area_window;
442 /* List of pairs (MESSAGE . MULTIBYTE). The function save_message
443 pushes the current message and the value of
444 message_enable_multibyte on the stack, the function restore_message
445 pops the stack and displays MESSAGE again. */
447 Lisp_Object Vmessage_stack;
449 /* Nonzero means multibyte characters were enabled when the echo area
450 message was specified. */
452 int message_enable_multibyte;
454 /* Nonzero if we should redraw the mode lines on the next redisplay. */
456 int update_mode_lines;
458 /* Nonzero if window sizes or contents have changed since last
459 redisplay that finished. */
461 int windows_or_buffers_changed;
463 /* Nonzero means a frame's cursor type has been changed. */
465 int cursor_type_changed;
467 /* Nonzero after display_mode_line if %l was used and it displayed a
468 line number. */
470 int line_number_displayed;
472 /* Maximum buffer size for which to display line numbers. */
474 Lisp_Object Vline_number_display_limit;
476 /* Line width to consider when repositioning for line number display. */
478 static EMACS_INT line_number_display_limit_width;
480 /* Number of lines to keep in the message log buffer. t means
481 infinite. nil means don't log at all. */
483 Lisp_Object Vmessage_log_max;
485 /* The name of the *Messages* buffer, a string. */
487 static Lisp_Object Vmessages_buffer_name;
489 /* Current, index 0, and last displayed echo area message. Either
490 buffers from echo_buffers, or nil to indicate no message. */
492 Lisp_Object echo_area_buffer[2];
494 /* The buffers referenced from echo_area_buffer. */
496 static Lisp_Object echo_buffer[2];
498 /* A vector saved used in with_area_buffer to reduce consing. */
500 static Lisp_Object Vwith_echo_area_save_vector;
502 /* Non-zero means display_echo_area should display the last echo area
503 message again. Set by redisplay_preserve_echo_area. */
505 static int display_last_displayed_message_p;
507 /* Nonzero if echo area is being used by print; zero if being used by
508 message. */
510 int message_buf_print;
512 /* The symbol `inhibit-menubar-update' and its DEFVAR_BOOL variable. */
514 Lisp_Object Qinhibit_menubar_update;
515 int inhibit_menubar_update;
517 /* Maximum height for resizing mini-windows. Either a float
518 specifying a fraction of the available height, or an integer
519 specifying a number of lines. */
521 Lisp_Object Vmax_mini_window_height;
523 /* Non-zero means messages should be displayed with truncated
524 lines instead of being continued. */
526 int message_truncate_lines;
527 Lisp_Object Qmessage_truncate_lines;
529 /* Set to 1 in clear_message to make redisplay_internal aware
530 of an emptied echo area. */
532 static int message_cleared_p;
534 /* Non-zero means we want a hollow cursor in windows that are not
535 selected. Zero means there's no cursor in such windows. */
537 Lisp_Object Vcursor_in_non_selected_windows;
538 Lisp_Object Qcursor_in_non_selected_windows;
540 /* How to blink the default frame cursor off. */
541 Lisp_Object Vblink_cursor_alist;
543 /* A scratch glyph row with contents used for generating truncation
544 glyphs. Also used in direct_output_for_insert. */
546 #define MAX_SCRATCH_GLYPHS 100
547 struct glyph_row scratch_glyph_row;
548 static struct glyph scratch_glyphs[MAX_SCRATCH_GLYPHS];
550 /* Ascent and height of the last line processed by move_it_to. */
552 static int last_max_ascent, last_height;
554 /* Non-zero if there's a help-echo in the echo area. */
556 int help_echo_showing_p;
558 /* If >= 0, computed, exact values of mode-line and header-line height
559 to use in the macros CURRENT_MODE_LINE_HEIGHT and
560 CURRENT_HEADER_LINE_HEIGHT. */
562 int current_mode_line_height, current_header_line_height;
564 /* The maximum distance to look ahead for text properties. Values
565 that are too small let us call compute_char_face and similar
566 functions too often which is expensive. Values that are too large
567 let us call compute_char_face and alike too often because we
568 might not be interested in text properties that far away. */
570 #define TEXT_PROP_DISTANCE_LIMIT 100
572 #if GLYPH_DEBUG
574 /* Variables to turn off display optimizations from Lisp. */
576 int inhibit_try_window_id, inhibit_try_window_reusing;
577 int inhibit_try_cursor_movement;
579 /* Non-zero means print traces of redisplay if compiled with
580 GLYPH_DEBUG != 0. */
582 int trace_redisplay_p;
584 #endif /* GLYPH_DEBUG */
586 #ifdef DEBUG_TRACE_MOVE
587 /* Non-zero means trace with TRACE_MOVE to stderr. */
588 int trace_move;
590 #define TRACE_MOVE(x) if (trace_move) fprintf x; else (void) 0
591 #else
592 #define TRACE_MOVE(x) (void) 0
593 #endif
595 /* Non-zero means automatically scroll windows horizontally to make
596 point visible. */
598 int automatic_hscrolling_p;
600 /* How close to the margin can point get before the window is scrolled
601 horizontally. */
602 EMACS_INT hscroll_margin;
604 /* How much to scroll horizontally when point is inside the above margin. */
605 Lisp_Object Vhscroll_step;
607 /* A list of symbols, one for each supported image type. */
609 Lisp_Object Vimage_types;
611 /* The variable `resize-mini-windows'. If nil, don't resize
612 mini-windows. If t, always resize them to fit the text they
613 display. If `grow-only', let mini-windows grow only until they
614 become empty. */
616 Lisp_Object Vresize_mini_windows;
618 /* Buffer being redisplayed -- for redisplay_window_error. */
620 struct buffer *displayed_buffer;
622 /* Value returned from text property handlers (see below). */
624 enum prop_handled
626 HANDLED_NORMALLY,
627 HANDLED_RECOMPUTE_PROPS,
628 HANDLED_OVERLAY_STRING_CONSUMED,
629 HANDLED_RETURN
632 /* A description of text properties that redisplay is interested
633 in. */
635 struct props
637 /* The name of the property. */
638 Lisp_Object *name;
640 /* A unique index for the property. */
641 enum prop_idx idx;
643 /* A handler function called to set up iterator IT from the property
644 at IT's current position. Value is used to steer handle_stop. */
645 enum prop_handled (*handler) P_ ((struct it *it));
648 static enum prop_handled handle_face_prop P_ ((struct it *));
649 static enum prop_handled handle_invisible_prop P_ ((struct it *));
650 static enum prop_handled handle_display_prop P_ ((struct it *));
651 static enum prop_handled handle_composition_prop P_ ((struct it *));
652 static enum prop_handled handle_overlay_change P_ ((struct it *));
653 static enum prop_handled handle_fontified_prop P_ ((struct it *));
655 /* Properties handled by iterators. */
657 static struct props it_props[] =
659 {&Qfontified, FONTIFIED_PROP_IDX, handle_fontified_prop},
660 /* Handle `face' before `display' because some sub-properties of
661 `display' need to know the face. */
662 {&Qface, FACE_PROP_IDX, handle_face_prop},
663 {&Qdisplay, DISPLAY_PROP_IDX, handle_display_prop},
664 {&Qinvisible, INVISIBLE_PROP_IDX, handle_invisible_prop},
665 {&Qcomposition, COMPOSITION_PROP_IDX, handle_composition_prop},
666 {NULL, 0, NULL}
669 /* Value is the position described by X. If X is a marker, value is
670 the marker_position of X. Otherwise, value is X. */
672 #define COERCE_MARKER(X) (MARKERP ((X)) ? Fmarker_position (X) : (X))
674 /* Enumeration returned by some move_it_.* functions internally. */
676 enum move_it_result
678 /* Not used. Undefined value. */
679 MOVE_UNDEFINED,
681 /* Move ended at the requested buffer position or ZV. */
682 MOVE_POS_MATCH_OR_ZV,
684 /* Move ended at the requested X pixel position. */
685 MOVE_X_REACHED,
687 /* Move within a line ended at the end of a line that must be
688 continued. */
689 MOVE_LINE_CONTINUED,
691 /* Move within a line ended at the end of a line that would
692 be displayed truncated. */
693 MOVE_LINE_TRUNCATED,
695 /* Move within a line ended at a line end. */
696 MOVE_NEWLINE_OR_CR
699 /* This counter is used to clear the face cache every once in a while
700 in redisplay_internal. It is incremented for each redisplay.
701 Every CLEAR_FACE_CACHE_COUNT full redisplays, the face cache is
702 cleared. */
704 #define CLEAR_FACE_CACHE_COUNT 500
705 static int clear_face_cache_count;
707 /* Record the previous terminal frame we displayed. */
709 static struct frame *previous_terminal_frame;
711 /* Non-zero while redisplay_internal is in progress. */
713 int redisplaying_p;
715 /* Non-zero means don't free realized faces. Bound while freeing
716 realized faces is dangerous because glyph matrices might still
717 reference them. */
719 int inhibit_free_realized_faces;
720 Lisp_Object Qinhibit_free_realized_faces;
723 /* Function prototypes. */
725 static void setup_for_ellipsis P_ ((struct it *));
726 static void mark_window_display_accurate_1 P_ ((struct window *, int));
727 static int single_display_prop_string_p P_ ((Lisp_Object, Lisp_Object));
728 static int display_prop_string_p P_ ((Lisp_Object, Lisp_Object));
729 static int cursor_row_p P_ ((struct window *, struct glyph_row *));
730 static int redisplay_mode_lines P_ ((Lisp_Object, int));
731 static char *decode_mode_spec_coding P_ ((Lisp_Object, char *, int));
733 #if 0
734 static int invisible_text_between_p P_ ((struct it *, int, int));
735 #endif
737 static int next_element_from_ellipsis P_ ((struct it *));
738 static void pint2str P_ ((char *, int, int));
739 static struct text_pos run_window_scroll_functions P_ ((Lisp_Object,
740 struct text_pos));
741 static void reconsider_clip_changes P_ ((struct window *, struct buffer *));
742 static int text_outside_line_unchanged_p P_ ((struct window *, int, int));
743 static void store_frame_title_char P_ ((char));
744 static int store_frame_title P_ ((const unsigned char *, int, int));
745 static void x_consider_frame_title P_ ((Lisp_Object));
746 static void handle_stop P_ ((struct it *));
747 static int tool_bar_lines_needed P_ ((struct frame *));
748 static int single_display_prop_intangible_p P_ ((Lisp_Object));
749 static void ensure_echo_area_buffers P_ ((void));
750 static Lisp_Object unwind_with_echo_area_buffer P_ ((Lisp_Object));
751 static Lisp_Object with_echo_area_buffer_unwind_data P_ ((struct window *));
752 static int with_echo_area_buffer P_ ((struct window *, int,
753 int (*) (EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT),
754 EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
755 static void clear_garbaged_frames P_ ((void));
756 static int current_message_1 P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
757 static int truncate_message_1 P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
758 static int set_message_1 P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
759 static int display_echo_area P_ ((struct window *));
760 static int display_echo_area_1 P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
761 static int resize_mini_window_1 P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
762 static Lisp_Object unwind_redisplay P_ ((Lisp_Object));
763 static int string_char_and_length P_ ((const unsigned char *, int, int *));
764 static struct text_pos display_prop_end P_ ((struct it *, Lisp_Object,
765 struct text_pos));
766 static int compute_window_start_on_continuation_line P_ ((struct window *));
767 static Lisp_Object safe_eval_handler P_ ((Lisp_Object));
768 static void insert_left_trunc_glyphs P_ ((struct it *));
769 static struct glyph_row *get_overlay_arrow_glyph_row P_ ((struct window *));
770 static void extend_face_to_end_of_line P_ ((struct it *));
771 static int append_space P_ ((struct it *, int));
772 static int make_cursor_line_fully_visible P_ ((struct window *));
773 static int try_scrolling P_ ((Lisp_Object, int, EMACS_INT, EMACS_INT, int));
774 static int try_cursor_movement P_ ((Lisp_Object, struct text_pos, int *));
775 static int trailing_whitespace_p P_ ((int));
776 static int message_log_check_duplicate P_ ((int, int, int, int));
777 static void push_it P_ ((struct it *));
778 static void pop_it P_ ((struct it *));
779 static void sync_frame_with_window_matrix_rows P_ ((struct window *));
780 static void redisplay_internal P_ ((int));
781 static int echo_area_display P_ ((int));
782 static void redisplay_windows P_ ((Lisp_Object));
783 static void redisplay_window P_ ((Lisp_Object, int));
784 static Lisp_Object redisplay_window_error ();
785 static Lisp_Object redisplay_window_0 P_ ((Lisp_Object));
786 static Lisp_Object redisplay_window_1 P_ ((Lisp_Object));
787 static void update_menu_bar P_ ((struct frame *, int));
788 static int try_window_reusing_current_matrix P_ ((struct window *));
789 static int try_window_id P_ ((struct window *));
790 static int display_line P_ ((struct it *));
791 static int display_mode_lines P_ ((struct window *));
792 static int display_mode_line P_ ((struct window *, enum face_id, Lisp_Object));
793 static int display_mode_element P_ ((struct it *, int, int, int, Lisp_Object, Lisp_Object, int));
794 static int store_mode_line_string P_ ((char *, Lisp_Object, int, int, int, Lisp_Object));
795 static char *decode_mode_spec P_ ((struct window *, int, int, int, int *));
796 static void display_menu_bar P_ ((struct window *));
797 static int display_count_lines P_ ((int, int, int, int, int *));
798 static int display_string P_ ((unsigned char *, Lisp_Object, Lisp_Object,
799 int, int, struct it *, int, int, int, int));
800 static void compute_line_metrics P_ ((struct it *));
801 static void run_redisplay_end_trigger_hook P_ ((struct it *));
802 static int get_overlay_strings P_ ((struct it *, int));
803 static void next_overlay_string P_ ((struct it *));
804 static void reseat P_ ((struct it *, struct text_pos, int));
805 static void reseat_1 P_ ((struct it *, struct text_pos, int));
806 static void back_to_previous_visible_line_start P_ ((struct it *));
807 static void reseat_at_previous_visible_line_start P_ ((struct it *));
808 static void reseat_at_next_visible_line_start P_ ((struct it *, int));
809 static int next_element_from_display_vector P_ ((struct it *));
810 static int next_element_from_string P_ ((struct it *));
811 static int next_element_from_c_string P_ ((struct it *));
812 static int next_element_from_buffer P_ ((struct it *));
813 static int next_element_from_composition P_ ((struct it *));
814 static int next_element_from_image P_ ((struct it *));
815 static int next_element_from_stretch P_ ((struct it *));
816 static void load_overlay_strings P_ ((struct it *, int));
817 static int init_from_display_pos P_ ((struct it *, struct window *,
818 struct display_pos *));
819 static void reseat_to_string P_ ((struct it *, unsigned char *,
820 Lisp_Object, int, int, int, int));
821 static enum move_it_result move_it_in_display_line_to P_ ((struct it *,
822 int, int, int));
823 void move_it_vertically_backward P_ ((struct it *, int));
824 static void init_to_row_start P_ ((struct it *, struct window *,
825 struct glyph_row *));
826 static int init_to_row_end P_ ((struct it *, struct window *,
827 struct glyph_row *));
828 static void back_to_previous_line_start P_ ((struct it *));
829 static int forward_to_next_line_start P_ ((struct it *, int *));
830 static struct text_pos string_pos_nchars_ahead P_ ((struct text_pos,
831 Lisp_Object, int));
832 static struct text_pos string_pos P_ ((int, Lisp_Object));
833 static struct text_pos c_string_pos P_ ((int, unsigned char *, int));
834 static int number_of_chars P_ ((unsigned char *, int));
835 static void compute_stop_pos P_ ((struct it *));
836 static void compute_string_pos P_ ((struct text_pos *, struct text_pos,
837 Lisp_Object));
838 static int face_before_or_after_it_pos P_ ((struct it *, int));
839 static int next_overlay_change P_ ((int));
840 static int handle_single_display_prop P_ ((struct it *, Lisp_Object,
841 Lisp_Object, struct text_pos *,
842 int));
843 static int underlying_face_id P_ ((struct it *));
844 static int in_ellipses_for_invisible_text_p P_ ((struct display_pos *,
845 struct window *));
847 #define face_before_it_pos(IT) face_before_or_after_it_pos ((IT), 1)
848 #define face_after_it_pos(IT) face_before_or_after_it_pos ((IT), 0)
850 #ifdef HAVE_WINDOW_SYSTEM
852 static void update_tool_bar P_ ((struct frame *, int));
853 static void build_desired_tool_bar_string P_ ((struct frame *f));
854 static int redisplay_tool_bar P_ ((struct frame *));
855 static void display_tool_bar_line P_ ((struct it *));
857 #endif /* HAVE_WINDOW_SYSTEM */
860 /***********************************************************************
861 Window display dimensions
862 ***********************************************************************/
864 /* Return the window-relative maximum y + 1 for glyph rows displaying
865 text in window W. This is the height of W minus the height of a
866 mode line, if any. */
868 INLINE int
869 window_text_bottom_y (w)
870 struct window *w;
872 struct frame *f = XFRAME (w->frame);
873 int height = XFASTINT (w->height) * CANON_Y_UNIT (f);
875 if (WINDOW_WANTS_MODELINE_P (w))
876 height -= CURRENT_MODE_LINE_HEIGHT (w);
877 return height;
881 /* Return the pixel width of display area AREA of window W. AREA < 0
882 means return the total width of W, not including fringes to
883 the left and right of the window. */
885 INLINE int
886 window_box_width (w, area)
887 struct window *w;
888 int area;
890 struct frame *f = XFRAME (w->frame);
891 int width = XFASTINT (w->width);
893 if (!w->pseudo_window_p)
895 width -= FRAME_SCROLL_BAR_WIDTH (f) + FRAME_FRINGE_COLS (f);
897 if (area == TEXT_AREA)
899 if (INTEGERP (w->left_margin_width))
900 width -= XFASTINT (w->left_margin_width);
901 if (INTEGERP (w->right_margin_width))
902 width -= XFASTINT (w->right_margin_width);
904 else if (area == LEFT_MARGIN_AREA)
905 width = (INTEGERP (w->left_margin_width)
906 ? XFASTINT (w->left_margin_width) : 0);
907 else if (area == RIGHT_MARGIN_AREA)
908 width = (INTEGERP (w->right_margin_width)
909 ? XFASTINT (w->right_margin_width) : 0);
912 return width * CANON_X_UNIT (f);
916 /* Return the pixel height of the display area of window W, not
917 including mode lines of W, if any. */
919 INLINE int
920 window_box_height (w)
921 struct window *w;
923 struct frame *f = XFRAME (w->frame);
924 int height = XFASTINT (w->height) * CANON_Y_UNIT (f);
926 xassert (height >= 0);
928 /* Note: the code below that determines the mode-line/header-line
929 height is essentially the same as that contained in the macro
930 CURRENT_{MODE,HEADER}_LINE_HEIGHT, except that it checks whether
931 the appropriate glyph row has its `mode_line_p' flag set,
932 and if it doesn't, uses estimate_mode_line_height instead. */
934 if (WINDOW_WANTS_MODELINE_P (w))
936 struct glyph_row *ml_row
937 = (w->current_matrix && w->current_matrix->rows
938 ? MATRIX_MODE_LINE_ROW (w->current_matrix)
939 : 0);
940 if (ml_row && ml_row->mode_line_p)
941 height -= ml_row->height;
942 else
943 height -= estimate_mode_line_height (f, CURRENT_MODE_LINE_FACE_ID (w));
946 if (WINDOW_WANTS_HEADER_LINE_P (w))
948 struct glyph_row *hl_row
949 = (w->current_matrix && w->current_matrix->rows
950 ? MATRIX_HEADER_LINE_ROW (w->current_matrix)
951 : 0);
952 if (hl_row && hl_row->mode_line_p)
953 height -= hl_row->height;
954 else
955 height -= estimate_mode_line_height (f, HEADER_LINE_FACE_ID);
958 /* With a very small font and a mode-line that's taller than
959 default, we might end up with a negative height. */
960 return max (0, height);
964 /* Return the frame-relative coordinate of the left edge of display
965 area AREA of window W. AREA < 0 means return the left edge of the
966 whole window, to the right of the left fringe of W. */
968 INLINE int
969 window_box_left (w, area)
970 struct window *w;
971 int area;
973 struct frame *f = XFRAME (w->frame);
974 int x = FRAME_INTERNAL_BORDER_WIDTH_SAFE (f);
976 if (!w->pseudo_window_p)
978 x += (WINDOW_LEFT_MARGIN (w) * CANON_X_UNIT (f)
979 + FRAME_LEFT_FRINGE_WIDTH (f));
981 if (area == TEXT_AREA)
982 x += window_box_width (w, LEFT_MARGIN_AREA);
983 else if (area == RIGHT_MARGIN_AREA)
984 x += (window_box_width (w, LEFT_MARGIN_AREA)
985 + window_box_width (w, TEXT_AREA));
988 return x;
992 /* Return the frame-relative coordinate of the right edge of display
993 area AREA of window W. AREA < 0 means return the left edge of the
994 whole window, to the left of the right fringe of W. */
996 INLINE int
997 window_box_right (w, area)
998 struct window *w;
999 int area;
1001 return window_box_left (w, area) + window_box_width (w, area);
1005 /* Get the bounding box of the display area AREA of window W, without
1006 mode lines, in frame-relative coordinates. AREA < 0 means the
1007 whole window, not including the left and right fringes of
1008 the window. Return in *BOX_X and *BOX_Y the frame-relative pixel
1009 coordinates of the upper-left corner of the box. Return in
1010 *BOX_WIDTH, and *BOX_HEIGHT the pixel width and height of the box. */
1012 INLINE void
1013 window_box (w, area, box_x, box_y, box_width, box_height)
1014 struct window *w;
1015 int area;
1016 int *box_x, *box_y, *box_width, *box_height;
1018 struct frame *f = XFRAME (w->frame);
1020 *box_width = window_box_width (w, area);
1021 *box_height = window_box_height (w);
1022 *box_x = window_box_left (w, area);
1023 *box_y = (FRAME_INTERNAL_BORDER_WIDTH_SAFE (f)
1024 + XFASTINT (w->top) * CANON_Y_UNIT (f));
1025 if (WINDOW_WANTS_HEADER_LINE_P (w))
1026 *box_y += CURRENT_HEADER_LINE_HEIGHT (w);
1030 /* Get the bounding box of the display area AREA of window W, without
1031 mode lines. AREA < 0 means the whole window, not including the
1032 left and right fringe of the window. Return in *TOP_LEFT_X
1033 and TOP_LEFT_Y the frame-relative pixel coordinates of the
1034 upper-left corner of the box. Return in *BOTTOM_RIGHT_X, and
1035 *BOTTOM_RIGHT_Y the coordinates of the bottom-right corner of the
1036 box. */
1038 INLINE void
1039 window_box_edges (w, area, top_left_x, top_left_y,
1040 bottom_right_x, bottom_right_y)
1041 struct window *w;
1042 int area;
1043 int *top_left_x, *top_left_y, *bottom_right_x, *bottom_right_y;
1045 window_box (w, area, top_left_x, top_left_y, bottom_right_x,
1046 bottom_right_y);
1047 *bottom_right_x += *top_left_x;
1048 *bottom_right_y += *top_left_y;
1053 /***********************************************************************
1054 Utilities
1055 ***********************************************************************/
1057 /* Return the bottom y-position of the line the iterator IT is in.
1058 This can modify IT's settings. */
1061 line_bottom_y (it)
1062 struct it *it;
1064 int line_height = it->max_ascent + it->max_descent;
1065 int line_top_y = it->current_y;
1067 if (line_height == 0)
1069 if (last_height)
1070 line_height = last_height;
1071 else if (IT_CHARPOS (*it) < ZV)
1073 move_it_by_lines (it, 1, 1);
1074 line_height = (it->max_ascent || it->max_descent
1075 ? it->max_ascent + it->max_descent
1076 : last_height);
1078 else
1080 struct glyph_row *row = it->glyph_row;
1082 /* Use the default character height. */
1083 it->glyph_row = NULL;
1084 it->what = IT_CHARACTER;
1085 it->c = ' ';
1086 it->len = 1;
1087 PRODUCE_GLYPHS (it);
1088 line_height = it->ascent + it->descent;
1089 it->glyph_row = row;
1093 return line_top_y + line_height;
1097 /* Return 1 if position CHARPOS is visible in window W. Set *FULLY to
1098 1 if POS is visible and the line containing POS is fully visible.
1099 EXACT_MODE_LINE_HEIGHTS_P non-zero means compute exact mode-line
1100 and header-lines heights. */
1103 pos_visible_p (w, charpos, fully, exact_mode_line_heights_p)
1104 struct window *w;
1105 int charpos, *fully, exact_mode_line_heights_p;
1107 struct it it;
1108 struct text_pos top;
1109 int visible_p;
1110 struct buffer *old_buffer = NULL;
1112 if (XBUFFER (w->buffer) != current_buffer)
1114 old_buffer = current_buffer;
1115 set_buffer_internal_1 (XBUFFER (w->buffer));
1118 *fully = visible_p = 0;
1119 SET_TEXT_POS_FROM_MARKER (top, w->start);
1121 /* Compute exact mode line heights, if requested. */
1122 if (exact_mode_line_heights_p)
1124 if (WINDOW_WANTS_MODELINE_P (w))
1125 current_mode_line_height
1126 = display_mode_line (w, CURRENT_MODE_LINE_FACE_ID (w),
1127 current_buffer->mode_line_format);
1129 if (WINDOW_WANTS_HEADER_LINE_P (w))
1130 current_header_line_height
1131 = display_mode_line (w, HEADER_LINE_FACE_ID,
1132 current_buffer->header_line_format);
1135 start_display (&it, w, top);
1136 move_it_to (&it, charpos, 0, it.last_visible_y, -1,
1137 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
1139 /* Note that we may overshoot because of invisible text. */
1140 if (IT_CHARPOS (it) >= charpos)
1142 int top_y = it.current_y;
1143 int bottom_y = line_bottom_y (&it);
1144 int window_top_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w);
1146 if (top_y < window_top_y)
1147 visible_p = bottom_y > window_top_y;
1148 else if (top_y < it.last_visible_y)
1150 visible_p = 1;
1151 *fully = bottom_y <= it.last_visible_y;
1154 else if (it.current_y + it.max_ascent + it.max_descent > it.last_visible_y)
1156 move_it_by_lines (&it, 1, 0);
1157 if (charpos < IT_CHARPOS (it))
1159 visible_p = 1;
1160 *fully = 0;
1164 if (old_buffer)
1165 set_buffer_internal_1 (old_buffer);
1167 current_header_line_height = current_mode_line_height = -1;
1168 return visible_p;
1172 /* Return the next character from STR which is MAXLEN bytes long.
1173 Return in *LEN the length of the character. This is like
1174 STRING_CHAR_AND_LENGTH but never returns an invalid character. If
1175 we find one, we return a `?', but with the length of the invalid
1176 character. */
1178 static INLINE int
1179 string_char_and_length (str, maxlen, len)
1180 const unsigned char *str;
1181 int maxlen, *len;
1183 int c;
1185 c = STRING_CHAR_AND_LENGTH (str, maxlen, *len);
1186 if (!CHAR_VALID_P (c, 1))
1187 /* We may not change the length here because other places in Emacs
1188 don't use this function, i.e. they silently accept invalid
1189 characters. */
1190 c = '?';
1192 return c;
1197 /* Given a position POS containing a valid character and byte position
1198 in STRING, return the position NCHARS ahead (NCHARS >= 0). */
1200 static struct text_pos
1201 string_pos_nchars_ahead (pos, string, nchars)
1202 struct text_pos pos;
1203 Lisp_Object string;
1204 int nchars;
1206 xassert (STRINGP (string) && nchars >= 0);
1208 if (STRING_MULTIBYTE (string))
1210 int rest = SBYTES (string) - BYTEPOS (pos);
1211 const unsigned char *p = SDATA (string) + BYTEPOS (pos);
1212 int len;
1214 while (nchars--)
1216 string_char_and_length (p, rest, &len);
1217 p += len, rest -= len;
1218 xassert (rest >= 0);
1219 CHARPOS (pos) += 1;
1220 BYTEPOS (pos) += len;
1223 else
1224 SET_TEXT_POS (pos, CHARPOS (pos) + nchars, BYTEPOS (pos) + nchars);
1226 return pos;
1230 /* Value is the text position, i.e. character and byte position,
1231 for character position CHARPOS in STRING. */
1233 static INLINE struct text_pos
1234 string_pos (charpos, string)
1235 int charpos;
1236 Lisp_Object string;
1238 struct text_pos pos;
1239 xassert (STRINGP (string));
1240 xassert (charpos >= 0);
1241 SET_TEXT_POS (pos, charpos, string_char_to_byte (string, charpos));
1242 return pos;
1246 /* Value is a text position, i.e. character and byte position, for
1247 character position CHARPOS in C string S. MULTIBYTE_P non-zero
1248 means recognize multibyte characters. */
1250 static struct text_pos
1251 c_string_pos (charpos, s, multibyte_p)
1252 int charpos;
1253 unsigned char *s;
1254 int multibyte_p;
1256 struct text_pos pos;
1258 xassert (s != NULL);
1259 xassert (charpos >= 0);
1261 if (multibyte_p)
1263 int rest = strlen (s), len;
1265 SET_TEXT_POS (pos, 0, 0);
1266 while (charpos--)
1268 string_char_and_length (s, rest, &len);
1269 s += len, rest -= len;
1270 xassert (rest >= 0);
1271 CHARPOS (pos) += 1;
1272 BYTEPOS (pos) += len;
1275 else
1276 SET_TEXT_POS (pos, charpos, charpos);
1278 return pos;
1282 /* Value is the number of characters in C string S. MULTIBYTE_P
1283 non-zero means recognize multibyte characters. */
1285 static int
1286 number_of_chars (s, multibyte_p)
1287 unsigned char *s;
1288 int multibyte_p;
1290 int nchars;
1292 if (multibyte_p)
1294 int rest = strlen (s), len;
1295 unsigned char *p = (unsigned char *) s;
1297 for (nchars = 0; rest > 0; ++nchars)
1299 string_char_and_length (p, rest, &len);
1300 rest -= len, p += len;
1303 else
1304 nchars = strlen (s);
1306 return nchars;
1310 /* Compute byte position NEWPOS->bytepos corresponding to
1311 NEWPOS->charpos. POS is a known position in string STRING.
1312 NEWPOS->charpos must be >= POS.charpos. */
1314 static void
1315 compute_string_pos (newpos, pos, string)
1316 struct text_pos *newpos, pos;
1317 Lisp_Object string;
1319 xassert (STRINGP (string));
1320 xassert (CHARPOS (*newpos) >= CHARPOS (pos));
1322 if (STRING_MULTIBYTE (string))
1323 *newpos = string_pos_nchars_ahead (pos, string,
1324 CHARPOS (*newpos) - CHARPOS (pos));
1325 else
1326 BYTEPOS (*newpos) = CHARPOS (*newpos);
1331 /***********************************************************************
1332 Lisp form evaluation
1333 ***********************************************************************/
1335 /* Error handler for safe_eval and safe_call. */
1337 static Lisp_Object
1338 safe_eval_handler (arg)
1339 Lisp_Object arg;
1341 add_to_log ("Error during redisplay: %s", arg, Qnil);
1342 return Qnil;
1346 /* Evaluate SEXPR and return the result, or nil if something went
1347 wrong. Prevent redisplay during the evaluation. */
1349 Lisp_Object
1350 safe_eval (sexpr)
1351 Lisp_Object sexpr;
1353 Lisp_Object val;
1355 if (inhibit_eval_during_redisplay)
1356 val = Qnil;
1357 else
1359 int count = SPECPDL_INDEX ();
1360 struct gcpro gcpro1;
1362 GCPRO1 (sexpr);
1363 specbind (Qinhibit_redisplay, Qt);
1364 /* Use Qt to ensure debugger does not run,
1365 so there is no possibility of wanting to redisplay. */
1366 val = internal_condition_case_1 (Feval, sexpr, Qt,
1367 safe_eval_handler);
1368 UNGCPRO;
1369 val = unbind_to (count, val);
1372 return val;
1376 /* Call function ARGS[0] with arguments ARGS[1] to ARGS[NARGS - 1].
1377 Return the result, or nil if something went wrong. Prevent
1378 redisplay during the evaluation. */
1380 Lisp_Object
1381 safe_call (nargs, args)
1382 int nargs;
1383 Lisp_Object *args;
1385 Lisp_Object val;
1387 if (inhibit_eval_during_redisplay)
1388 val = Qnil;
1389 else
1391 int count = SPECPDL_INDEX ();
1392 struct gcpro gcpro1;
1394 GCPRO1 (args[0]);
1395 gcpro1.nvars = nargs;
1396 specbind (Qinhibit_redisplay, Qt);
1397 /* Use Qt to ensure debugger does not run,
1398 so there is no possibility of wanting to redisplay. */
1399 val = internal_condition_case_2 (Ffuncall, nargs, args, Qt,
1400 safe_eval_handler);
1401 UNGCPRO;
1402 val = unbind_to (count, val);
1405 return val;
1409 /* Call function FN with one argument ARG.
1410 Return the result, or nil if something went wrong. */
1412 Lisp_Object
1413 safe_call1 (fn, arg)
1414 Lisp_Object fn, arg;
1416 Lisp_Object args[2];
1417 args[0] = fn;
1418 args[1] = arg;
1419 return safe_call (2, args);
1424 /***********************************************************************
1425 Debugging
1426 ***********************************************************************/
1428 #if 0
1430 /* Define CHECK_IT to perform sanity checks on iterators.
1431 This is for debugging. It is too slow to do unconditionally. */
1433 static void
1434 check_it (it)
1435 struct it *it;
1437 if (it->method == next_element_from_string)
1439 xassert (STRINGP (it->string));
1440 xassert (IT_STRING_CHARPOS (*it) >= 0);
1442 else if (it->method == next_element_from_buffer)
1444 /* Check that character and byte positions agree. */
1445 xassert (IT_CHARPOS (*it) == BYTE_TO_CHAR (IT_BYTEPOS (*it)));
1448 if (it->dpvec)
1449 xassert (it->current.dpvec_index >= 0);
1450 else
1451 xassert (it->current.dpvec_index < 0);
1454 #define CHECK_IT(IT) check_it ((IT))
1456 #else /* not 0 */
1458 #define CHECK_IT(IT) (void) 0
1460 #endif /* not 0 */
1463 #if GLYPH_DEBUG
1465 /* Check that the window end of window W is what we expect it
1466 to be---the last row in the current matrix displaying text. */
1468 static void
1469 check_window_end (w)
1470 struct window *w;
1472 if (!MINI_WINDOW_P (w)
1473 && !NILP (w->window_end_valid))
1475 struct glyph_row *row;
1476 xassert ((row = MATRIX_ROW (w->current_matrix,
1477 XFASTINT (w->window_end_vpos)),
1478 !row->enabled_p
1479 || MATRIX_ROW_DISPLAYS_TEXT_P (row)
1480 || MATRIX_ROW_VPOS (row, w->current_matrix) == 0));
1484 #define CHECK_WINDOW_END(W) check_window_end ((W))
1486 #else /* not GLYPH_DEBUG */
1488 #define CHECK_WINDOW_END(W) (void) 0
1490 #endif /* not GLYPH_DEBUG */
1494 /***********************************************************************
1495 Iterator initialization
1496 ***********************************************************************/
1498 /* Initialize IT for displaying current_buffer in window W, starting
1499 at character position CHARPOS. CHARPOS < 0 means that no buffer
1500 position is specified which is useful when the iterator is assigned
1501 a position later. BYTEPOS is the byte position corresponding to
1502 CHARPOS. BYTEPOS < 0 means compute it from CHARPOS.
1504 If ROW is not null, calls to produce_glyphs with IT as parameter
1505 will produce glyphs in that row.
1507 BASE_FACE_ID is the id of a base face to use. It must be one of
1508 DEFAULT_FACE_ID for normal text, MODE_LINE_FACE_ID,
1509 MODE_LINE_INACTIVE_FACE_ID, or HEADER_LINE_FACE_ID for displaying
1510 mode lines, or TOOL_BAR_FACE_ID for displaying the tool-bar.
1512 If ROW is null and BASE_FACE_ID is equal to MODE_LINE_FACE_ID,
1513 MODE_LINE_INACTIVE_FACE_ID, or HEADER_LINE_FACE_ID, the iterator
1514 will be initialized to use the corresponding mode line glyph row of
1515 the desired matrix of W. */
1517 void
1518 init_iterator (it, w, charpos, bytepos, row, base_face_id)
1519 struct it *it;
1520 struct window *w;
1521 int charpos, bytepos;
1522 struct glyph_row *row;
1523 enum face_id base_face_id;
1525 int highlight_region_p;
1527 /* Some precondition checks. */
1528 xassert (w != NULL && it != NULL);
1529 xassert (charpos < 0 || (charpos >= BUF_BEG (current_buffer)
1530 && charpos <= ZV));
1532 /* If face attributes have been changed since the last redisplay,
1533 free realized faces now because they depend on face definitions
1534 that might have changed. Don't free faces while there might be
1535 desired matrices pending which reference these faces. */
1536 if (face_change_count && !inhibit_free_realized_faces)
1538 face_change_count = 0;
1539 free_all_realized_faces (Qnil);
1542 /* Use one of the mode line rows of W's desired matrix if
1543 appropriate. */
1544 if (row == NULL)
1546 if (base_face_id == MODE_LINE_FACE_ID
1547 || base_face_id == MODE_LINE_INACTIVE_FACE_ID)
1548 row = MATRIX_MODE_LINE_ROW (w->desired_matrix);
1549 else if (base_face_id == HEADER_LINE_FACE_ID)
1550 row = MATRIX_HEADER_LINE_ROW (w->desired_matrix);
1553 /* Clear IT. */
1554 bzero (it, sizeof *it);
1555 it->current.overlay_string_index = -1;
1556 it->current.dpvec_index = -1;
1557 it->base_face_id = base_face_id;
1559 /* The window in which we iterate over current_buffer: */
1560 XSETWINDOW (it->window, w);
1561 it->w = w;
1562 it->f = XFRAME (w->frame);
1564 /* Extra space between lines (on window systems only). */
1565 if (base_face_id == DEFAULT_FACE_ID
1566 && FRAME_WINDOW_P (it->f))
1568 if (NATNUMP (current_buffer->extra_line_spacing))
1569 it->extra_line_spacing = XFASTINT (current_buffer->extra_line_spacing);
1570 else if (it->f->extra_line_spacing > 0)
1571 it->extra_line_spacing = it->f->extra_line_spacing;
1574 /* If realized faces have been removed, e.g. because of face
1575 attribute changes of named faces, recompute them. When running
1576 in batch mode, the face cache of Vterminal_frame is null. If
1577 we happen to get called, make a dummy face cache. */
1578 if (
1579 #ifndef WINDOWSNT
1580 noninteractive &&
1581 #endif
1582 FRAME_FACE_CACHE (it->f) == NULL)
1583 init_frame_faces (it->f);
1584 if (FRAME_FACE_CACHE (it->f)->used == 0)
1585 recompute_basic_faces (it->f);
1587 /* Current value of the `space-width', and 'height' properties. */
1588 it->space_width = Qnil;
1589 it->font_height = Qnil;
1591 /* Are control characters displayed as `^C'? */
1592 it->ctl_arrow_p = !NILP (current_buffer->ctl_arrow);
1594 /* -1 means everything between a CR and the following line end
1595 is invisible. >0 means lines indented more than this value are
1596 invisible. */
1597 it->selective = (INTEGERP (current_buffer->selective_display)
1598 ? XFASTINT (current_buffer->selective_display)
1599 : (!NILP (current_buffer->selective_display)
1600 ? -1 : 0));
1601 it->selective_display_ellipsis_p
1602 = !NILP (current_buffer->selective_display_ellipses);
1604 /* Display table to use. */
1605 it->dp = window_display_table (w);
1607 /* Are multibyte characters enabled in current_buffer? */
1608 it->multibyte_p = !NILP (current_buffer->enable_multibyte_characters);
1610 /* Non-zero if we should highlight the region. */
1611 highlight_region_p
1612 = (!NILP (Vtransient_mark_mode)
1613 && !NILP (current_buffer->mark_active)
1614 && XMARKER (current_buffer->mark)->buffer != 0);
1616 /* Set IT->region_beg_charpos and IT->region_end_charpos to the
1617 start and end of a visible region in window IT->w. Set both to
1618 -1 to indicate no region. */
1619 if (highlight_region_p
1620 /* Maybe highlight only in selected window. */
1621 && (/* Either show region everywhere. */
1622 highlight_nonselected_windows
1623 /* Or show region in the selected window. */
1624 || w == XWINDOW (selected_window)
1625 /* Or show the region if we are in the mini-buffer and W is
1626 the window the mini-buffer refers to. */
1627 || (MINI_WINDOW_P (XWINDOW (selected_window))
1628 && WINDOWP (minibuf_selected_window)
1629 && w == XWINDOW (minibuf_selected_window))))
1631 int charpos = marker_position (current_buffer->mark);
1632 it->region_beg_charpos = min (PT, charpos);
1633 it->region_end_charpos = max (PT, charpos);
1635 else
1636 it->region_beg_charpos = it->region_end_charpos = -1;
1638 /* Get the position at which the redisplay_end_trigger hook should
1639 be run, if it is to be run at all. */
1640 if (MARKERP (w->redisplay_end_trigger)
1641 && XMARKER (w->redisplay_end_trigger)->buffer != 0)
1642 it->redisplay_end_trigger_charpos
1643 = marker_position (w->redisplay_end_trigger);
1644 else if (INTEGERP (w->redisplay_end_trigger))
1645 it->redisplay_end_trigger_charpos = XINT (w->redisplay_end_trigger);
1647 /* Correct bogus values of tab_width. */
1648 it->tab_width = XINT (current_buffer->tab_width);
1649 if (it->tab_width <= 0 || it->tab_width > 1000)
1650 it->tab_width = 8;
1652 /* Are lines in the display truncated? */
1653 it->truncate_lines_p
1654 = (base_face_id != DEFAULT_FACE_ID
1655 || XINT (it->w->hscroll)
1656 || (truncate_partial_width_windows
1657 && !WINDOW_FULL_WIDTH_P (it->w))
1658 || !NILP (current_buffer->truncate_lines));
1660 /* Get dimensions of truncation and continuation glyphs. These are
1661 displayed as fringe bitmaps under X, so we don't need them for such
1662 frames. */
1663 if (!FRAME_WINDOW_P (it->f))
1665 if (it->truncate_lines_p)
1667 /* We will need the truncation glyph. */
1668 xassert (it->glyph_row == NULL);
1669 produce_special_glyphs (it, IT_TRUNCATION);
1670 it->truncation_pixel_width = it->pixel_width;
1672 else
1674 /* We will need the continuation glyph. */
1675 xassert (it->glyph_row == NULL);
1676 produce_special_glyphs (it, IT_CONTINUATION);
1677 it->continuation_pixel_width = it->pixel_width;
1680 /* Reset these values to zero because the produce_special_glyphs
1681 above has changed them. */
1682 it->pixel_width = it->ascent = it->descent = 0;
1683 it->phys_ascent = it->phys_descent = 0;
1686 /* Set this after getting the dimensions of truncation and
1687 continuation glyphs, so that we don't produce glyphs when calling
1688 produce_special_glyphs, above. */
1689 it->glyph_row = row;
1690 it->area = TEXT_AREA;
1692 /* Get the dimensions of the display area. The display area
1693 consists of the visible window area plus a horizontally scrolled
1694 part to the left of the window. All x-values are relative to the
1695 start of this total display area. */
1696 if (base_face_id != DEFAULT_FACE_ID)
1698 /* Mode lines, menu bar in terminal frames. */
1699 it->first_visible_x = 0;
1700 it->last_visible_x = XFASTINT (w->width) * CANON_X_UNIT (it->f);
1702 else
1704 it->first_visible_x
1705 = XFASTINT (it->w->hscroll) * CANON_X_UNIT (it->f);
1706 it->last_visible_x = (it->first_visible_x
1707 + window_box_width (w, TEXT_AREA));
1709 /* If we truncate lines, leave room for the truncator glyph(s) at
1710 the right margin. Otherwise, leave room for the continuation
1711 glyph(s). Truncation and continuation glyphs are not inserted
1712 for window-based redisplay. */
1713 if (!FRAME_WINDOW_P (it->f))
1715 if (it->truncate_lines_p)
1716 it->last_visible_x -= it->truncation_pixel_width;
1717 else
1718 it->last_visible_x -= it->continuation_pixel_width;
1721 it->header_line_p = WINDOW_WANTS_HEADER_LINE_P (w);
1722 it->current_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w) + w->vscroll;
1725 /* Leave room for a border glyph. */
1726 if (!FRAME_WINDOW_P (it->f)
1727 && !WINDOW_RIGHTMOST_P (it->w))
1728 it->last_visible_x -= 1;
1730 it->last_visible_y = window_text_bottom_y (w);
1732 /* For mode lines and alike, arrange for the first glyph having a
1733 left box line if the face specifies a box. */
1734 if (base_face_id != DEFAULT_FACE_ID)
1736 struct face *face;
1738 it->face_id = base_face_id;
1740 /* If we have a boxed mode line, make the first character appear
1741 with a left box line. */
1742 face = FACE_FROM_ID (it->f, base_face_id);
1743 if (face->box != FACE_NO_BOX)
1744 it->start_of_box_run_p = 1;
1747 /* If a buffer position was specified, set the iterator there,
1748 getting overlays and face properties from that position. */
1749 if (charpos >= BUF_BEG (current_buffer))
1751 it->end_charpos = ZV;
1752 it->face_id = -1;
1753 IT_CHARPOS (*it) = charpos;
1755 /* Compute byte position if not specified. */
1756 if (bytepos < charpos)
1757 IT_BYTEPOS (*it) = CHAR_TO_BYTE (charpos);
1758 else
1759 IT_BYTEPOS (*it) = bytepos;
1761 /* Compute faces etc. */
1762 reseat (it, it->current.pos, 1);
1765 CHECK_IT (it);
1769 /* Initialize IT for the display of window W with window start POS. */
1771 void
1772 start_display (it, w, pos)
1773 struct it *it;
1774 struct window *w;
1775 struct text_pos pos;
1777 struct glyph_row *row;
1778 int first_vpos = WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0;
1780 row = w->desired_matrix->rows + first_vpos;
1781 init_iterator (it, w, CHARPOS (pos), BYTEPOS (pos), row, DEFAULT_FACE_ID);
1783 if (!it->truncate_lines_p)
1785 int start_at_line_beg_p;
1786 int first_y = it->current_y;
1788 /* If window start is not at a line start, skip forward to POS to
1789 get the correct continuation lines width. */
1790 start_at_line_beg_p = (CHARPOS (pos) == BEGV
1791 || FETCH_BYTE (BYTEPOS (pos) - 1) == '\n');
1792 if (!start_at_line_beg_p)
1794 reseat_at_previous_visible_line_start (it);
1795 move_it_to (it, CHARPOS (pos), -1, -1, -1, MOVE_TO_POS);
1797 /* If lines are continued, this line may end in the middle
1798 of a multi-glyph character (e.g. a control character
1799 displayed as \003, or in the middle of an overlay
1800 string). In this case move_it_to above will not have
1801 taken us to the start of the continuation line but to the
1802 end of the continued line. */
1803 if (it->current_x > 0)
1805 if (it->current.dpvec_index >= 0
1806 || it->current.overlay_string_index >= 0)
1808 set_iterator_to_next (it, 1);
1809 move_it_in_display_line_to (it, -1, -1, 0);
1812 it->continuation_lines_width += it->current_x;
1815 /* We're starting a new display line, not affected by the
1816 height of the continued line, so clear the appropriate
1817 fields in the iterator structure. */
1818 it->max_ascent = it->max_descent = 0;
1819 it->max_phys_ascent = it->max_phys_descent = 0;
1821 it->current_y = first_y;
1822 it->vpos = 0;
1823 it->current_x = it->hpos = 0;
1827 #if 0 /* Don't assert the following because start_display is sometimes
1828 called intentionally with a window start that is not at a
1829 line start. Please leave this code in as a comment. */
1831 /* Window start should be on a line start, now. */
1832 xassert (it->continuation_lines_width
1833 || IT_CHARPOS (it) == BEGV
1834 || FETCH_BYTE (IT_BYTEPOS (it) - 1) == '\n');
1835 #endif /* 0 */
1839 /* Return 1 if POS is a position in ellipses displayed for invisible
1840 text. W is the window we display, for text property lookup. */
1842 static int
1843 in_ellipses_for_invisible_text_p (pos, w)
1844 struct display_pos *pos;
1845 struct window *w;
1847 Lisp_Object prop, window;
1848 int ellipses_p = 0;
1849 int charpos = CHARPOS (pos->pos);
1851 /* If POS specifies a position in a display vector, this might
1852 be for an ellipsis displayed for invisible text. We won't
1853 get the iterator set up for delivering that ellipsis unless
1854 we make sure that it gets aware of the invisible text. */
1855 if (pos->dpvec_index >= 0
1856 && pos->overlay_string_index < 0
1857 && CHARPOS (pos->string_pos) < 0
1858 && charpos > BEGV
1859 && (XSETWINDOW (window, w),
1860 prop = Fget_char_property (make_number (charpos),
1861 Qinvisible, window),
1862 !TEXT_PROP_MEANS_INVISIBLE (prop)))
1864 prop = Fget_char_property (make_number (charpos - 1), Qinvisible,
1865 window);
1866 ellipses_p = 2 == TEXT_PROP_MEANS_INVISIBLE (prop);
1869 return ellipses_p;
1873 /* Initialize IT for stepping through current_buffer in window W,
1874 starting at position POS that includes overlay string and display
1875 vector/ control character translation position information. Value
1876 is zero if there are overlay strings with newlines at POS. */
1878 static int
1879 init_from_display_pos (it, w, pos)
1880 struct it *it;
1881 struct window *w;
1882 struct display_pos *pos;
1884 int charpos = CHARPOS (pos->pos), bytepos = BYTEPOS (pos->pos);
1885 int i, overlay_strings_with_newlines = 0;
1887 /* If POS specifies a position in a display vector, this might
1888 be for an ellipsis displayed for invisible text. We won't
1889 get the iterator set up for delivering that ellipsis unless
1890 we make sure that it gets aware of the invisible text. */
1891 if (in_ellipses_for_invisible_text_p (pos, w))
1893 --charpos;
1894 bytepos = 0;
1897 /* Keep in mind: the call to reseat in init_iterator skips invisible
1898 text, so we might end up at a position different from POS. This
1899 is only a problem when POS is a row start after a newline and an
1900 overlay starts there with an after-string, and the overlay has an
1901 invisible property. Since we don't skip invisible text in
1902 display_line and elsewhere immediately after consuming the
1903 newline before the row start, such a POS will not be in a string,
1904 but the call to init_iterator below will move us to the
1905 after-string. */
1906 init_iterator (it, w, charpos, bytepos, NULL, DEFAULT_FACE_ID);
1908 for (i = 0; i < it->n_overlay_strings; ++i)
1910 const char *s = SDATA (it->overlay_strings[i]);
1911 const char *e = s + SBYTES (it->overlay_strings[i]);
1913 while (s < e && *s != '\n')
1914 ++s;
1916 if (s < e)
1918 overlay_strings_with_newlines = 1;
1919 break;
1923 /* If position is within an overlay string, set up IT to the right
1924 overlay string. */
1925 if (pos->overlay_string_index >= 0)
1927 int relative_index;
1929 /* If the first overlay string happens to have a `display'
1930 property for an image, the iterator will be set up for that
1931 image, and we have to undo that setup first before we can
1932 correct the overlay string index. */
1933 if (it->method == next_element_from_image)
1934 pop_it (it);
1936 /* We already have the first chunk of overlay strings in
1937 IT->overlay_strings. Load more until the one for
1938 pos->overlay_string_index is in IT->overlay_strings. */
1939 if (pos->overlay_string_index >= OVERLAY_STRING_CHUNK_SIZE)
1941 int n = pos->overlay_string_index / OVERLAY_STRING_CHUNK_SIZE;
1942 it->current.overlay_string_index = 0;
1943 while (n--)
1945 load_overlay_strings (it, 0);
1946 it->current.overlay_string_index += OVERLAY_STRING_CHUNK_SIZE;
1950 it->current.overlay_string_index = pos->overlay_string_index;
1951 relative_index = (it->current.overlay_string_index
1952 % OVERLAY_STRING_CHUNK_SIZE);
1953 it->string = it->overlay_strings[relative_index];
1954 xassert (STRINGP (it->string));
1955 it->current.string_pos = pos->string_pos;
1956 it->method = next_element_from_string;
1959 #if 0 /* This is bogus because POS not having an overlay string
1960 position does not mean it's after the string. Example: A
1961 line starting with a before-string and initialization of IT
1962 to the previous row's end position. */
1963 else if (it->current.overlay_string_index >= 0)
1965 /* If POS says we're already after an overlay string ending at
1966 POS, make sure to pop the iterator because it will be in
1967 front of that overlay string. When POS is ZV, we've thereby
1968 also ``processed'' overlay strings at ZV. */
1969 while (it->sp)
1970 pop_it (it);
1971 it->current.overlay_string_index = -1;
1972 it->method = next_element_from_buffer;
1973 if (CHARPOS (pos->pos) == ZV)
1974 it->overlay_strings_at_end_processed_p = 1;
1976 #endif /* 0 */
1978 if (CHARPOS (pos->string_pos) >= 0)
1980 /* Recorded position is not in an overlay string, but in another
1981 string. This can only be a string from a `display' property.
1982 IT should already be filled with that string. */
1983 it->current.string_pos = pos->string_pos;
1984 xassert (STRINGP (it->string));
1987 /* Restore position in display vector translations, control
1988 character translations or ellipses. */
1989 if (pos->dpvec_index >= 0)
1991 if (it->dpvec == NULL)
1992 get_next_display_element (it);
1993 xassert (it->dpvec && it->current.dpvec_index == 0);
1994 it->current.dpvec_index = pos->dpvec_index;
1997 CHECK_IT (it);
1998 return !overlay_strings_with_newlines;
2002 /* Initialize IT for stepping through current_buffer in window W
2003 starting at ROW->start. */
2005 static void
2006 init_to_row_start (it, w, row)
2007 struct it *it;
2008 struct window *w;
2009 struct glyph_row *row;
2011 init_from_display_pos (it, w, &row->start);
2012 it->continuation_lines_width = row->continuation_lines_width;
2013 CHECK_IT (it);
2017 /* Initialize IT for stepping through current_buffer in window W
2018 starting in the line following ROW, i.e. starting at ROW->end.
2019 Value is zero if there are overlay strings with newlines at ROW's
2020 end position. */
2022 static int
2023 init_to_row_end (it, w, row)
2024 struct it *it;
2025 struct window *w;
2026 struct glyph_row *row;
2028 int success = 0;
2030 if (init_from_display_pos (it, w, &row->end))
2032 if (row->continued_p)
2033 it->continuation_lines_width
2034 = row->continuation_lines_width + row->pixel_width;
2035 CHECK_IT (it);
2036 success = 1;
2039 return success;
2045 /***********************************************************************
2046 Text properties
2047 ***********************************************************************/
2049 /* Called when IT reaches IT->stop_charpos. Handle text property and
2050 overlay changes. Set IT->stop_charpos to the next position where
2051 to stop. */
2053 static void
2054 handle_stop (it)
2055 struct it *it;
2057 enum prop_handled handled;
2058 int handle_overlay_change_p = 1;
2059 struct props *p;
2061 it->dpvec = NULL;
2062 it->current.dpvec_index = -1;
2066 handled = HANDLED_NORMALLY;
2068 /* Call text property handlers. */
2069 for (p = it_props; p->handler; ++p)
2071 handled = p->handler (it);
2073 if (handled == HANDLED_RECOMPUTE_PROPS)
2074 break;
2075 else if (handled == HANDLED_RETURN)
2076 return;
2077 else if (handled == HANDLED_OVERLAY_STRING_CONSUMED)
2078 handle_overlay_change_p = 0;
2081 if (handled != HANDLED_RECOMPUTE_PROPS)
2083 /* Don't check for overlay strings below when set to deliver
2084 characters from a display vector. */
2085 if (it->method == next_element_from_display_vector)
2086 handle_overlay_change_p = 0;
2088 /* Handle overlay changes. */
2089 if (handle_overlay_change_p)
2090 handled = handle_overlay_change (it);
2092 /* Determine where to stop next. */
2093 if (handled == HANDLED_NORMALLY)
2094 compute_stop_pos (it);
2097 while (handled == HANDLED_RECOMPUTE_PROPS);
2101 /* Compute IT->stop_charpos from text property and overlay change
2102 information for IT's current position. */
2104 static void
2105 compute_stop_pos (it)
2106 struct it *it;
2108 register INTERVAL iv, next_iv;
2109 Lisp_Object object, limit, position;
2111 /* If nowhere else, stop at the end. */
2112 it->stop_charpos = it->end_charpos;
2114 if (STRINGP (it->string))
2116 /* Strings are usually short, so don't limit the search for
2117 properties. */
2118 object = it->string;
2119 limit = Qnil;
2120 position = make_number (IT_STRING_CHARPOS (*it));
2122 else
2124 int charpos;
2126 /* If next overlay change is in front of the current stop pos
2127 (which is IT->end_charpos), stop there. Note: value of
2128 next_overlay_change is point-max if no overlay change
2129 follows. */
2130 charpos = next_overlay_change (IT_CHARPOS (*it));
2131 if (charpos < it->stop_charpos)
2132 it->stop_charpos = charpos;
2134 /* If showing the region, we have to stop at the region
2135 start or end because the face might change there. */
2136 if (it->region_beg_charpos > 0)
2138 if (IT_CHARPOS (*it) < it->region_beg_charpos)
2139 it->stop_charpos = min (it->stop_charpos, it->region_beg_charpos);
2140 else if (IT_CHARPOS (*it) < it->region_end_charpos)
2141 it->stop_charpos = min (it->stop_charpos, it->region_end_charpos);
2144 /* Set up variables for computing the stop position from text
2145 property changes. */
2146 XSETBUFFER (object, current_buffer);
2147 limit = make_number (IT_CHARPOS (*it) + TEXT_PROP_DISTANCE_LIMIT);
2148 position = make_number (IT_CHARPOS (*it));
2152 /* Get the interval containing IT's position. Value is a null
2153 interval if there isn't such an interval. */
2154 iv = validate_interval_range (object, &position, &position, 0);
2155 if (!NULL_INTERVAL_P (iv))
2157 Lisp_Object values_here[LAST_PROP_IDX];
2158 struct props *p;
2160 /* Get properties here. */
2161 for (p = it_props; p->handler; ++p)
2162 values_here[p->idx] = textget (iv->plist, *p->name);
2164 /* Look for an interval following iv that has different
2165 properties. */
2166 for (next_iv = next_interval (iv);
2167 (!NULL_INTERVAL_P (next_iv)
2168 && (NILP (limit)
2169 || XFASTINT (limit) > next_iv->position));
2170 next_iv = next_interval (next_iv))
2172 for (p = it_props; p->handler; ++p)
2174 Lisp_Object new_value;
2176 new_value = textget (next_iv->plist, *p->name);
2177 if (!EQ (values_here[p->idx], new_value))
2178 break;
2181 if (p->handler)
2182 break;
2185 if (!NULL_INTERVAL_P (next_iv))
2187 if (INTEGERP (limit)
2188 && next_iv->position >= XFASTINT (limit))
2189 /* No text property change up to limit. */
2190 it->stop_charpos = min (XFASTINT (limit), it->stop_charpos);
2191 else
2192 /* Text properties change in next_iv. */
2193 it->stop_charpos = min (it->stop_charpos, next_iv->position);
2197 xassert (STRINGP (it->string)
2198 || (it->stop_charpos >= BEGV
2199 && it->stop_charpos >= IT_CHARPOS (*it)));
2203 /* Return the position of the next overlay change after POS in
2204 current_buffer. Value is point-max if no overlay change
2205 follows. This is like `next-overlay-change' but doesn't use
2206 xmalloc. */
2208 static int
2209 next_overlay_change (pos)
2210 int pos;
2212 int noverlays;
2213 int endpos;
2214 Lisp_Object *overlays;
2215 int len;
2216 int i;
2218 /* Get all overlays at the given position. */
2219 len = 10;
2220 overlays = (Lisp_Object *) alloca (len * sizeof *overlays);
2221 noverlays = overlays_at (pos, 0, &overlays, &len, &endpos, NULL, 1);
2222 if (noverlays > len)
2224 len = noverlays;
2225 overlays = (Lisp_Object *) alloca (len * sizeof *overlays);
2226 noverlays = overlays_at (pos, 0, &overlays, &len, &endpos, NULL, 1);
2229 /* If any of these overlays ends before endpos,
2230 use its ending point instead. */
2231 for (i = 0; i < noverlays; ++i)
2233 Lisp_Object oend;
2234 int oendpos;
2236 oend = OVERLAY_END (overlays[i]);
2237 oendpos = OVERLAY_POSITION (oend);
2238 endpos = min (endpos, oendpos);
2241 return endpos;
2246 /***********************************************************************
2247 Fontification
2248 ***********************************************************************/
2250 /* Handle changes in the `fontified' property of the current buffer by
2251 calling hook functions from Qfontification_functions to fontify
2252 regions of text. */
2254 static enum prop_handled
2255 handle_fontified_prop (it)
2256 struct it *it;
2258 Lisp_Object prop, pos;
2259 enum prop_handled handled = HANDLED_NORMALLY;
2261 /* Get the value of the `fontified' property at IT's current buffer
2262 position. (The `fontified' property doesn't have a special
2263 meaning in strings.) If the value is nil, call functions from
2264 Qfontification_functions. */
2265 if (!STRINGP (it->string)
2266 && it->s == NULL
2267 && !NILP (Vfontification_functions)
2268 && !NILP (Vrun_hooks)
2269 && (pos = make_number (IT_CHARPOS (*it)),
2270 prop = Fget_char_property (pos, Qfontified, Qnil),
2271 NILP (prop)))
2273 int count = SPECPDL_INDEX ();
2274 Lisp_Object val;
2276 val = Vfontification_functions;
2277 specbind (Qfontification_functions, Qnil);
2279 if (!CONSP (val) || EQ (XCAR (val), Qlambda))
2280 safe_call1 (val, pos);
2281 else
2283 Lisp_Object globals, fn;
2284 struct gcpro gcpro1, gcpro2;
2286 globals = Qnil;
2287 GCPRO2 (val, globals);
2289 for (; CONSP (val); val = XCDR (val))
2291 fn = XCAR (val);
2293 if (EQ (fn, Qt))
2295 /* A value of t indicates this hook has a local
2296 binding; it means to run the global binding too.
2297 In a global value, t should not occur. If it
2298 does, we must ignore it to avoid an endless
2299 loop. */
2300 for (globals = Fdefault_value (Qfontification_functions);
2301 CONSP (globals);
2302 globals = XCDR (globals))
2304 fn = XCAR (globals);
2305 if (!EQ (fn, Qt))
2306 safe_call1 (fn, pos);
2309 else
2310 safe_call1 (fn, pos);
2313 UNGCPRO;
2316 unbind_to (count, Qnil);
2318 /* Return HANDLED_RECOMPUTE_PROPS only if function fontified
2319 something. This avoids an endless loop if they failed to
2320 fontify the text for which reason ever. */
2321 if (!NILP (Fget_char_property (pos, Qfontified, Qnil)))
2322 handled = HANDLED_RECOMPUTE_PROPS;
2325 return handled;
2330 /***********************************************************************
2331 Faces
2332 ***********************************************************************/
2334 /* Set up iterator IT from face properties at its current position.
2335 Called from handle_stop. */
2337 static enum prop_handled
2338 handle_face_prop (it)
2339 struct it *it;
2341 int new_face_id, next_stop;
2343 if (!STRINGP (it->string))
2345 new_face_id
2346 = face_at_buffer_position (it->w,
2347 IT_CHARPOS (*it),
2348 it->region_beg_charpos,
2349 it->region_end_charpos,
2350 &next_stop,
2351 (IT_CHARPOS (*it)
2352 + TEXT_PROP_DISTANCE_LIMIT),
2355 /* Is this a start of a run of characters with box face?
2356 Caveat: this can be called for a freshly initialized
2357 iterator; face_id is -1 in this case. We know that the new
2358 face will not change until limit, i.e. if the new face has a
2359 box, all characters up to limit will have one. But, as
2360 usual, we don't know whether limit is really the end. */
2361 if (new_face_id != it->face_id)
2363 struct face *new_face = FACE_FROM_ID (it->f, new_face_id);
2365 /* If new face has a box but old face has not, this is
2366 the start of a run of characters with box, i.e. it has
2367 a shadow on the left side. The value of face_id of the
2368 iterator will be -1 if this is the initial call that gets
2369 the face. In this case, we have to look in front of IT's
2370 position and see whether there is a face != new_face_id. */
2371 it->start_of_box_run_p
2372 = (new_face->box != FACE_NO_BOX
2373 && (it->face_id >= 0
2374 || IT_CHARPOS (*it) == BEG
2375 || new_face_id != face_before_it_pos (it)));
2376 it->face_box_p = new_face->box != FACE_NO_BOX;
2379 else
2381 int base_face_id, bufpos;
2383 if (it->current.overlay_string_index >= 0)
2384 bufpos = IT_CHARPOS (*it);
2385 else
2386 bufpos = 0;
2388 /* For strings from a buffer, i.e. overlay strings or strings
2389 from a `display' property, use the face at IT's current
2390 buffer position as the base face to merge with, so that
2391 overlay strings appear in the same face as surrounding
2392 text, unless they specify their own faces. */
2393 base_face_id = underlying_face_id (it);
2395 new_face_id = face_at_string_position (it->w,
2396 it->string,
2397 IT_STRING_CHARPOS (*it),
2398 bufpos,
2399 it->region_beg_charpos,
2400 it->region_end_charpos,
2401 &next_stop,
2402 base_face_id, 0);
2404 #if 0 /* This shouldn't be neccessary. Let's check it. */
2405 /* If IT is used to display a mode line we would really like to
2406 use the mode line face instead of the frame's default face. */
2407 if (it->glyph_row == MATRIX_MODE_LINE_ROW (it->w->desired_matrix)
2408 && new_face_id == DEFAULT_FACE_ID)
2409 new_face_id = CURRENT_MODE_LINE_FACE_ID (it->w);
2410 #endif
2412 /* Is this a start of a run of characters with box? Caveat:
2413 this can be called for a freshly allocated iterator; face_id
2414 is -1 is this case. We know that the new face will not
2415 change until the next check pos, i.e. if the new face has a
2416 box, all characters up to that position will have a
2417 box. But, as usual, we don't know whether that position
2418 is really the end. */
2419 if (new_face_id != it->face_id)
2421 struct face *new_face = FACE_FROM_ID (it->f, new_face_id);
2422 struct face *old_face = FACE_FROM_ID (it->f, it->face_id);
2424 /* If new face has a box but old face hasn't, this is the
2425 start of a run of characters with box, i.e. it has a
2426 shadow on the left side. */
2427 it->start_of_box_run_p
2428 = new_face->box && (old_face == NULL || !old_face->box);
2429 it->face_box_p = new_face->box != FACE_NO_BOX;
2433 it->face_id = new_face_id;
2434 return HANDLED_NORMALLY;
2438 /* Return the ID of the face ``underlying'' IT's current position,
2439 which is in a string. If the iterator is associated with a
2440 buffer, return the face at IT's current buffer position.
2441 Otherwise, use the iterator's base_face_id. */
2443 static int
2444 underlying_face_id (it)
2445 struct it *it;
2447 int face_id = it->base_face_id, i;
2449 xassert (STRINGP (it->string));
2451 for (i = it->sp - 1; i >= 0; --i)
2452 if (NILP (it->stack[i].string))
2453 face_id = it->stack[i].face_id;
2455 return face_id;
2459 /* Compute the face one character before or after the current position
2460 of IT. BEFORE_P non-zero means get the face in front of IT's
2461 position. Value is the id of the face. */
2463 static int
2464 face_before_or_after_it_pos (it, before_p)
2465 struct it *it;
2466 int before_p;
2468 int face_id, limit;
2469 int next_check_charpos;
2470 struct text_pos pos;
2472 xassert (it->s == NULL);
2474 if (STRINGP (it->string))
2476 int bufpos, base_face_id;
2478 /* No face change past the end of the string (for the case
2479 we are padding with spaces). No face change before the
2480 string start. */
2481 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string)
2482 || (IT_STRING_CHARPOS (*it) == 0 && before_p))
2483 return it->face_id;
2485 /* Set pos to the position before or after IT's current position. */
2486 if (before_p)
2487 pos = string_pos (IT_STRING_CHARPOS (*it) - 1, it->string);
2488 else
2489 /* For composition, we must check the character after the
2490 composition. */
2491 pos = (it->what == IT_COMPOSITION
2492 ? string_pos (IT_STRING_CHARPOS (*it) + it->cmp_len, it->string)
2493 : string_pos (IT_STRING_CHARPOS (*it) + 1, it->string));
2495 if (it->current.overlay_string_index >= 0)
2496 bufpos = IT_CHARPOS (*it);
2497 else
2498 bufpos = 0;
2500 base_face_id = underlying_face_id (it);
2502 /* Get the face for ASCII, or unibyte. */
2503 face_id = face_at_string_position (it->w,
2504 it->string,
2505 CHARPOS (pos),
2506 bufpos,
2507 it->region_beg_charpos,
2508 it->region_end_charpos,
2509 &next_check_charpos,
2510 base_face_id, 0);
2512 /* Correct the face for charsets different from ASCII. Do it
2513 for the multibyte case only. The face returned above is
2514 suitable for unibyte text if IT->string is unibyte. */
2515 if (STRING_MULTIBYTE (it->string))
2517 const unsigned char *p = SDATA (it->string) + BYTEPOS (pos);
2518 int rest = SBYTES (it->string) - BYTEPOS (pos);
2519 int c, len;
2520 struct face *face = FACE_FROM_ID (it->f, face_id);
2522 c = string_char_and_length (p, rest, &len);
2523 face_id = FACE_FOR_CHAR (it->f, face, c);
2526 else
2528 if ((IT_CHARPOS (*it) >= ZV && !before_p)
2529 || (IT_CHARPOS (*it) <= BEGV && before_p))
2530 return it->face_id;
2532 limit = IT_CHARPOS (*it) + TEXT_PROP_DISTANCE_LIMIT;
2533 pos = it->current.pos;
2535 if (before_p)
2536 DEC_TEXT_POS (pos, it->multibyte_p);
2537 else
2539 if (it->what == IT_COMPOSITION)
2540 /* For composition, we must check the position after the
2541 composition. */
2542 pos.charpos += it->cmp_len, pos.bytepos += it->len;
2543 else
2544 INC_TEXT_POS (pos, it->multibyte_p);
2547 /* Determine face for CHARSET_ASCII, or unibyte. */
2548 face_id = face_at_buffer_position (it->w,
2549 CHARPOS (pos),
2550 it->region_beg_charpos,
2551 it->region_end_charpos,
2552 &next_check_charpos,
2553 limit, 0);
2555 /* Correct the face for charsets different from ASCII. Do it
2556 for the multibyte case only. The face returned above is
2557 suitable for unibyte text if current_buffer is unibyte. */
2558 if (it->multibyte_p)
2560 int c = FETCH_MULTIBYTE_CHAR (BYTEPOS (pos));
2561 struct face *face = FACE_FROM_ID (it->f, face_id);
2562 face_id = FACE_FOR_CHAR (it->f, face, c);
2566 return face_id;
2571 /***********************************************************************
2572 Invisible text
2573 ***********************************************************************/
2575 /* Set up iterator IT from invisible properties at its current
2576 position. Called from handle_stop. */
2578 static enum prop_handled
2579 handle_invisible_prop (it)
2580 struct it *it;
2582 enum prop_handled handled = HANDLED_NORMALLY;
2584 if (STRINGP (it->string))
2586 extern Lisp_Object Qinvisible;
2587 Lisp_Object prop, end_charpos, limit, charpos;
2589 /* Get the value of the invisible text property at the
2590 current position. Value will be nil if there is no such
2591 property. */
2592 charpos = make_number (IT_STRING_CHARPOS (*it));
2593 prop = Fget_text_property (charpos, Qinvisible, it->string);
2595 if (!NILP (prop)
2596 && IT_STRING_CHARPOS (*it) < it->end_charpos)
2598 handled = HANDLED_RECOMPUTE_PROPS;
2600 /* Get the position at which the next change of the
2601 invisible text property can be found in IT->string.
2602 Value will be nil if the property value is the same for
2603 all the rest of IT->string. */
2604 XSETINT (limit, SCHARS (it->string));
2605 end_charpos = Fnext_single_property_change (charpos, Qinvisible,
2606 it->string, limit);
2608 /* Text at current position is invisible. The next
2609 change in the property is at position end_charpos.
2610 Move IT's current position to that position. */
2611 if (INTEGERP (end_charpos)
2612 && XFASTINT (end_charpos) < XFASTINT (limit))
2614 struct text_pos old;
2615 old = it->current.string_pos;
2616 IT_STRING_CHARPOS (*it) = XFASTINT (end_charpos);
2617 compute_string_pos (&it->current.string_pos, old, it->string);
2619 else
2621 /* The rest of the string is invisible. If this is an
2622 overlay string, proceed with the next overlay string
2623 or whatever comes and return a character from there. */
2624 if (it->current.overlay_string_index >= 0)
2626 next_overlay_string (it);
2627 /* Don't check for overlay strings when we just
2628 finished processing them. */
2629 handled = HANDLED_OVERLAY_STRING_CONSUMED;
2631 else
2633 IT_STRING_CHARPOS (*it) = SCHARS (it->string);
2634 IT_STRING_BYTEPOS (*it) = SBYTES (it->string);
2639 else
2641 int invis_p, newpos, next_stop, start_charpos;
2642 Lisp_Object pos, prop, overlay;
2644 /* First of all, is there invisible text at this position? */
2645 start_charpos = IT_CHARPOS (*it);
2646 pos = make_number (IT_CHARPOS (*it));
2647 prop = get_char_property_and_overlay (pos, Qinvisible, it->window,
2648 &overlay);
2649 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
2651 /* If we are on invisible text, skip over it. */
2652 if (invis_p && IT_CHARPOS (*it) < it->end_charpos)
2654 /* Record whether we have to display an ellipsis for the
2655 invisible text. */
2656 int display_ellipsis_p = invis_p == 2;
2658 handled = HANDLED_RECOMPUTE_PROPS;
2660 /* Loop skipping over invisible text. The loop is left at
2661 ZV or with IT on the first char being visible again. */
2664 /* Try to skip some invisible text. Return value is the
2665 position reached which can be equal to IT's position
2666 if there is nothing invisible here. This skips both
2667 over invisible text properties and overlays with
2668 invisible property. */
2669 newpos = skip_invisible (IT_CHARPOS (*it),
2670 &next_stop, ZV, it->window);
2672 /* If we skipped nothing at all we weren't at invisible
2673 text in the first place. If everything to the end of
2674 the buffer was skipped, end the loop. */
2675 if (newpos == IT_CHARPOS (*it) || newpos >= ZV)
2676 invis_p = 0;
2677 else
2679 /* We skipped some characters but not necessarily
2680 all there are. Check if we ended up on visible
2681 text. Fget_char_property returns the property of
2682 the char before the given position, i.e. if we
2683 get invis_p = 0, this means that the char at
2684 newpos is visible. */
2685 pos = make_number (newpos);
2686 prop = Fget_char_property (pos, Qinvisible, it->window);
2687 invis_p = TEXT_PROP_MEANS_INVISIBLE (prop);
2690 /* If we ended up on invisible text, proceed to
2691 skip starting with next_stop. */
2692 if (invis_p)
2693 IT_CHARPOS (*it) = next_stop;
2695 while (invis_p);
2697 /* The position newpos is now either ZV or on visible text. */
2698 IT_CHARPOS (*it) = newpos;
2699 IT_BYTEPOS (*it) = CHAR_TO_BYTE (newpos);
2701 /* If there are before-strings at the start of invisible
2702 text, and the text is invisible because of a text
2703 property, arrange to show before-strings because 20.x did
2704 it that way. (If the text is invisible because of an
2705 overlay property instead of a text property, this is
2706 already handled in the overlay code.) */
2707 if (NILP (overlay)
2708 && get_overlay_strings (it, start_charpos))
2710 handled = HANDLED_RECOMPUTE_PROPS;
2711 it->stack[it->sp - 1].display_ellipsis_p = display_ellipsis_p;
2713 else if (display_ellipsis_p)
2714 setup_for_ellipsis (it);
2718 return handled;
2722 /* Make iterator IT return `...' next. */
2724 static void
2725 setup_for_ellipsis (it)
2726 struct it *it;
2728 if (it->dp
2729 && VECTORP (DISP_INVIS_VECTOR (it->dp)))
2731 struct Lisp_Vector *v = XVECTOR (DISP_INVIS_VECTOR (it->dp));
2732 it->dpvec = v->contents;
2733 it->dpend = v->contents + v->size;
2735 else
2737 /* Default `...'. */
2738 it->dpvec = default_invis_vector;
2739 it->dpend = default_invis_vector + 3;
2742 /* The ellipsis display does not replace the display of the
2743 character at the new position. Indicate this by setting
2744 IT->dpvec_char_len to zero. */
2745 it->dpvec_char_len = 0;
2747 it->current.dpvec_index = 0;
2748 it->method = next_element_from_display_vector;
2753 /***********************************************************************
2754 'display' property
2755 ***********************************************************************/
2757 /* Set up iterator IT from `display' property at its current position.
2758 Called from handle_stop. */
2760 static enum prop_handled
2761 handle_display_prop (it)
2762 struct it *it;
2764 Lisp_Object prop, object;
2765 struct text_pos *position;
2766 int display_replaced_p = 0;
2768 if (STRINGP (it->string))
2770 object = it->string;
2771 position = &it->current.string_pos;
2773 else
2775 object = it->w->buffer;
2776 position = &it->current.pos;
2779 /* Reset those iterator values set from display property values. */
2780 it->font_height = Qnil;
2781 it->space_width = Qnil;
2782 it->voffset = 0;
2784 /* We don't support recursive `display' properties, i.e. string
2785 values that have a string `display' property, that have a string
2786 `display' property etc. */
2787 if (!it->string_from_display_prop_p)
2788 it->area = TEXT_AREA;
2790 prop = Fget_char_property (make_number (position->charpos),
2791 Qdisplay, object);
2792 if (NILP (prop))
2793 return HANDLED_NORMALLY;
2795 if (CONSP (prop)
2796 /* Simple properties. */
2797 && !EQ (XCAR (prop), Qimage)
2798 && !EQ (XCAR (prop), Qspace)
2799 && !EQ (XCAR (prop), Qwhen)
2800 && !EQ (XCAR (prop), Qspace_width)
2801 && !EQ (XCAR (prop), Qheight)
2802 && !EQ (XCAR (prop), Qraise)
2803 /* Marginal area specifications. */
2804 && !(CONSP (XCAR (prop)) && EQ (XCAR (XCAR (prop)), Qmargin))
2805 && !NILP (XCAR (prop)))
2807 for (; CONSP (prop); prop = XCDR (prop))
2809 if (handle_single_display_prop (it, XCAR (prop), object,
2810 position, display_replaced_p))
2811 display_replaced_p = 1;
2814 else if (VECTORP (prop))
2816 int i;
2817 for (i = 0; i < ASIZE (prop); ++i)
2818 if (handle_single_display_prop (it, AREF (prop, i), object,
2819 position, display_replaced_p))
2820 display_replaced_p = 1;
2822 else
2824 if (handle_single_display_prop (it, prop, object, position, 0))
2825 display_replaced_p = 1;
2828 return display_replaced_p ? HANDLED_RETURN : HANDLED_NORMALLY;
2832 /* Value is the position of the end of the `display' property starting
2833 at START_POS in OBJECT. */
2835 static struct text_pos
2836 display_prop_end (it, object, start_pos)
2837 struct it *it;
2838 Lisp_Object object;
2839 struct text_pos start_pos;
2841 Lisp_Object end;
2842 struct text_pos end_pos;
2844 end = Fnext_single_char_property_change (make_number (CHARPOS (start_pos)),
2845 Qdisplay, object, Qnil);
2846 CHARPOS (end_pos) = XFASTINT (end);
2847 if (STRINGP (object))
2848 compute_string_pos (&end_pos, start_pos, it->string);
2849 else
2850 BYTEPOS (end_pos) = CHAR_TO_BYTE (XFASTINT (end));
2852 return end_pos;
2856 /* Set up IT from a single `display' sub-property value PROP. OBJECT
2857 is the object in which the `display' property was found. *POSITION
2858 is the position at which it was found. DISPLAY_REPLACED_P non-zero
2859 means that we previously saw a display sub-property which already
2860 replaced text display with something else, for example an image;
2861 ignore such properties after the first one has been processed.
2863 If PROP is a `space' or `image' sub-property, set *POSITION to the
2864 end position of the `display' property.
2866 Value is non-zero if something was found which replaces the display
2867 of buffer or string text. */
2869 static int
2870 handle_single_display_prop (it, prop, object, position,
2871 display_replaced_before_p)
2872 struct it *it;
2873 Lisp_Object prop;
2874 Lisp_Object object;
2875 struct text_pos *position;
2876 int display_replaced_before_p;
2878 Lisp_Object value;
2879 int replaces_text_display_p = 0;
2880 Lisp_Object form;
2882 /* If PROP is a list of the form `(when FORM . VALUE)', FORM is
2883 evaluated. If the result is nil, VALUE is ignored. */
2884 form = Qt;
2885 if (CONSP (prop) && EQ (XCAR (prop), Qwhen))
2887 prop = XCDR (prop);
2888 if (!CONSP (prop))
2889 return 0;
2890 form = XCAR (prop);
2891 prop = XCDR (prop);
2894 if (!NILP (form) && !EQ (form, Qt))
2896 int count = SPECPDL_INDEX ();
2897 struct gcpro gcpro1;
2899 /* Bind `object' to the object having the `display' property, a
2900 buffer or string. Bind `position' to the position in the
2901 object where the property was found, and `buffer-position'
2902 to the current position in the buffer. */
2903 specbind (Qobject, object);
2904 specbind (Qposition, make_number (CHARPOS (*position)));
2905 specbind (Qbuffer_position,
2906 make_number (STRINGP (object)
2907 ? IT_CHARPOS (*it) : CHARPOS (*position)));
2908 GCPRO1 (form);
2909 form = safe_eval (form);
2910 UNGCPRO;
2911 unbind_to (count, Qnil);
2914 if (NILP (form))
2915 return 0;
2917 if (CONSP (prop)
2918 && EQ (XCAR (prop), Qheight)
2919 && CONSP (XCDR (prop)))
2921 if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
2922 return 0;
2924 /* `(height HEIGHT)'. */
2925 it->font_height = XCAR (XCDR (prop));
2926 if (!NILP (it->font_height))
2928 struct face *face = FACE_FROM_ID (it->f, it->face_id);
2929 int new_height = -1;
2931 if (CONSP (it->font_height)
2932 && (EQ (XCAR (it->font_height), Qplus)
2933 || EQ (XCAR (it->font_height), Qminus))
2934 && CONSP (XCDR (it->font_height))
2935 && INTEGERP (XCAR (XCDR (it->font_height))))
2937 /* `(+ N)' or `(- N)' where N is an integer. */
2938 int steps = XINT (XCAR (XCDR (it->font_height)));
2939 if (EQ (XCAR (it->font_height), Qplus))
2940 steps = - steps;
2941 it->face_id = smaller_face (it->f, it->face_id, steps);
2943 else if (FUNCTIONP (it->font_height))
2945 /* Call function with current height as argument.
2946 Value is the new height. */
2947 Lisp_Object height;
2948 height = safe_call1 (it->font_height,
2949 face->lface[LFACE_HEIGHT_INDEX]);
2950 if (NUMBERP (height))
2951 new_height = XFLOATINT (height);
2953 else if (NUMBERP (it->font_height))
2955 /* Value is a multiple of the canonical char height. */
2956 struct face *face;
2958 face = FACE_FROM_ID (it->f, DEFAULT_FACE_ID);
2959 new_height = (XFLOATINT (it->font_height)
2960 * XINT (face->lface[LFACE_HEIGHT_INDEX]));
2962 else
2964 /* Evaluate IT->font_height with `height' bound to the
2965 current specified height to get the new height. */
2966 Lisp_Object value;
2967 int count = SPECPDL_INDEX ();
2969 specbind (Qheight, face->lface[LFACE_HEIGHT_INDEX]);
2970 value = safe_eval (it->font_height);
2971 unbind_to (count, Qnil);
2973 if (NUMBERP (value))
2974 new_height = XFLOATINT (value);
2977 if (new_height > 0)
2978 it->face_id = face_with_height (it->f, it->face_id, new_height);
2981 else if (CONSP (prop)
2982 && EQ (XCAR (prop), Qspace_width)
2983 && CONSP (XCDR (prop)))
2985 /* `(space_width WIDTH)'. */
2986 if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
2987 return 0;
2989 value = XCAR (XCDR (prop));
2990 if (NUMBERP (value) && XFLOATINT (value) > 0)
2991 it->space_width = value;
2993 else if (CONSP (prop)
2994 && EQ (XCAR (prop), Qraise)
2995 && CONSP (XCDR (prop)))
2997 /* `(raise FACTOR)'. */
2998 if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
2999 return 0;
3001 #ifdef HAVE_WINDOW_SYSTEM
3002 value = XCAR (XCDR (prop));
3003 if (NUMBERP (value))
3005 struct face *face = FACE_FROM_ID (it->f, it->face_id);
3006 it->voffset = - (XFLOATINT (value)
3007 * (FONT_HEIGHT (face->font)));
3009 #endif /* HAVE_WINDOW_SYSTEM */
3011 else if (!it->string_from_display_prop_p)
3013 /* `((margin left-margin) VALUE)' or `((margin right-margin)
3014 VALUE) or `((margin nil) VALUE)' or VALUE. */
3015 Lisp_Object location, value;
3016 struct text_pos start_pos;
3017 int valid_p;
3019 /* Characters having this form of property are not displayed, so
3020 we have to find the end of the property. */
3021 start_pos = *position;
3022 *position = display_prop_end (it, object, start_pos);
3023 value = Qnil;
3025 /* Let's stop at the new position and assume that all
3026 text properties change there. */
3027 it->stop_charpos = position->charpos;
3029 location = Qunbound;
3030 if (CONSP (prop) && CONSP (XCAR (prop)))
3032 Lisp_Object tem;
3034 value = XCDR (prop);
3035 if (CONSP (value))
3036 value = XCAR (value);
3038 tem = XCAR (prop);
3039 if (EQ (XCAR (tem), Qmargin)
3040 && (tem = XCDR (tem),
3041 tem = CONSP (tem) ? XCAR (tem) : Qnil,
3042 (NILP (tem)
3043 || EQ (tem, Qleft_margin)
3044 || EQ (tem, Qright_margin))))
3045 location = tem;
3048 if (EQ (location, Qunbound))
3050 location = Qnil;
3051 value = prop;
3054 #ifdef HAVE_WINDOW_SYSTEM
3055 if (FRAME_TERMCAP_P (it->f))
3056 valid_p = STRINGP (value);
3057 else
3058 valid_p = (STRINGP (value)
3059 || (CONSP (value) && EQ (XCAR (value), Qspace))
3060 || valid_image_p (value));
3061 #else /* not HAVE_WINDOW_SYSTEM */
3062 valid_p = STRINGP (value);
3063 #endif /* not HAVE_WINDOW_SYSTEM */
3065 if ((EQ (location, Qleft_margin)
3066 || EQ (location, Qright_margin)
3067 || NILP (location))
3068 && valid_p
3069 && !display_replaced_before_p)
3071 replaces_text_display_p = 1;
3073 /* Save current settings of IT so that we can restore them
3074 when we are finished with the glyph property value. */
3075 push_it (it);
3077 if (NILP (location))
3078 it->area = TEXT_AREA;
3079 else if (EQ (location, Qleft_margin))
3080 it->area = LEFT_MARGIN_AREA;
3081 else
3082 it->area = RIGHT_MARGIN_AREA;
3084 if (STRINGP (value))
3086 it->string = value;
3087 it->multibyte_p = STRING_MULTIBYTE (it->string);
3088 it->current.overlay_string_index = -1;
3089 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = 0;
3090 it->end_charpos = it->string_nchars = SCHARS (it->string);
3091 it->method = next_element_from_string;
3092 it->stop_charpos = 0;
3093 it->string_from_display_prop_p = 1;
3094 /* Say that we haven't consumed the characters with
3095 `display' property yet. The call to pop_it in
3096 set_iterator_to_next will clean this up. */
3097 *position = start_pos;
3099 else if (CONSP (value) && EQ (XCAR (value), Qspace))
3101 it->method = next_element_from_stretch;
3102 it->object = value;
3103 it->current.pos = it->position = start_pos;
3105 #ifdef HAVE_WINDOW_SYSTEM
3106 else
3108 it->what = IT_IMAGE;
3109 it->image_id = lookup_image (it->f, value);
3110 it->position = start_pos;
3111 it->object = NILP (object) ? it->w->buffer : object;
3112 it->method = next_element_from_image;
3114 /* Say that we haven't consumed the characters with
3115 `display' property yet. The call to pop_it in
3116 set_iterator_to_next will clean this up. */
3117 *position = start_pos;
3119 #endif /* HAVE_WINDOW_SYSTEM */
3121 else
3122 /* Invalid property or property not supported. Restore
3123 the position to what it was before. */
3124 *position = start_pos;
3127 return replaces_text_display_p;
3131 /* Check if PROP is a display sub-property value whose text should be
3132 treated as intangible. */
3134 static int
3135 single_display_prop_intangible_p (prop)
3136 Lisp_Object prop;
3138 /* Skip over `when FORM'. */
3139 if (CONSP (prop) && EQ (XCAR (prop), Qwhen))
3141 prop = XCDR (prop);
3142 if (!CONSP (prop))
3143 return 0;
3144 prop = XCDR (prop);
3147 if (STRINGP (prop))
3148 return 1;
3150 if (!CONSP (prop))
3151 return 0;
3153 /* Skip over `margin LOCATION'. If LOCATION is in the margins,
3154 we don't need to treat text as intangible. */
3155 if (EQ (XCAR (prop), Qmargin))
3157 prop = XCDR (prop);
3158 if (!CONSP (prop))
3159 return 0;
3161 prop = XCDR (prop);
3162 if (!CONSP (prop)
3163 || EQ (XCAR (prop), Qleft_margin)
3164 || EQ (XCAR (prop), Qright_margin))
3165 return 0;
3168 return CONSP (prop) && EQ (XCAR (prop), Qimage);
3172 /* Check if PROP is a display property value whose text should be
3173 treated as intangible. */
3176 display_prop_intangible_p (prop)
3177 Lisp_Object prop;
3179 if (CONSP (prop)
3180 && CONSP (XCAR (prop))
3181 && !EQ (Qmargin, XCAR (XCAR (prop))))
3183 /* A list of sub-properties. */
3184 while (CONSP (prop))
3186 if (single_display_prop_intangible_p (XCAR (prop)))
3187 return 1;
3188 prop = XCDR (prop);
3191 else if (VECTORP (prop))
3193 /* A vector of sub-properties. */
3194 int i;
3195 for (i = 0; i < ASIZE (prop); ++i)
3196 if (single_display_prop_intangible_p (AREF (prop, i)))
3197 return 1;
3199 else
3200 return single_display_prop_intangible_p (prop);
3202 return 0;
3206 /* Return 1 if PROP is a display sub-property value containing STRING. */
3208 static int
3209 single_display_prop_string_p (prop, string)
3210 Lisp_Object prop, string;
3212 if (EQ (string, prop))
3213 return 1;
3215 /* Skip over `when FORM'. */
3216 if (CONSP (prop) && EQ (XCAR (prop), Qwhen))
3218 prop = XCDR (prop);
3219 if (!CONSP (prop))
3220 return 0;
3221 prop = XCDR (prop);
3224 if (CONSP (prop))
3225 /* Skip over `margin LOCATION'. */
3226 if (EQ (XCAR (prop), Qmargin))
3228 prop = XCDR (prop);
3229 if (!CONSP (prop))
3230 return 0;
3232 prop = XCDR (prop);
3233 if (!CONSP (prop))
3234 return 0;
3237 return CONSP (prop) && EQ (XCAR (prop), string);
3241 /* Return 1 if STRING appears in the `display' property PROP. */
3243 static int
3244 display_prop_string_p (prop, string)
3245 Lisp_Object prop, string;
3247 if (CONSP (prop)
3248 && CONSP (XCAR (prop))
3249 && !EQ (Qmargin, XCAR (XCAR (prop))))
3251 /* A list of sub-properties. */
3252 while (CONSP (prop))
3254 if (single_display_prop_string_p (XCAR (prop), string))
3255 return 1;
3256 prop = XCDR (prop);
3259 else if (VECTORP (prop))
3261 /* A vector of sub-properties. */
3262 int i;
3263 for (i = 0; i < ASIZE (prop); ++i)
3264 if (single_display_prop_string_p (AREF (prop, i), string))
3265 return 1;
3267 else
3268 return single_display_prop_string_p (prop, string);
3270 return 0;
3274 /* Determine from which buffer position in W's buffer STRING comes
3275 from. AROUND_CHARPOS is an approximate position where it could
3276 be from. Value is the buffer position or 0 if it couldn't be
3277 determined.
3279 W's buffer must be current.
3281 This function is necessary because we don't record buffer positions
3282 in glyphs generated from strings (to keep struct glyph small).
3283 This function may only use code that doesn't eval because it is
3284 called asynchronously from note_mouse_highlight. */
3287 string_buffer_position (w, string, around_charpos)
3288 struct window *w;
3289 Lisp_Object string;
3290 int around_charpos;
3292 Lisp_Object limit, prop, pos;
3293 const int MAX_DISTANCE = 1000;
3294 int found = 0;
3296 pos = make_number (around_charpos);
3297 limit = make_number (min (XINT (pos) + MAX_DISTANCE, ZV));
3298 while (!found && !EQ (pos, limit))
3300 prop = Fget_char_property (pos, Qdisplay, Qnil);
3301 if (!NILP (prop) && display_prop_string_p (prop, string))
3302 found = 1;
3303 else
3304 pos = Fnext_single_char_property_change (pos, Qdisplay, Qnil, limit);
3307 if (!found)
3309 pos = make_number (around_charpos);
3310 limit = make_number (max (XINT (pos) - MAX_DISTANCE, BEGV));
3311 while (!found && !EQ (pos, limit))
3313 prop = Fget_char_property (pos, Qdisplay, Qnil);
3314 if (!NILP (prop) && display_prop_string_p (prop, string))
3315 found = 1;
3316 else
3317 pos = Fprevious_single_char_property_change (pos, Qdisplay, Qnil,
3318 limit);
3322 return found ? XINT (pos) : 0;
3327 /***********************************************************************
3328 `composition' property
3329 ***********************************************************************/
3331 /* Set up iterator IT from `composition' property at its current
3332 position. Called from handle_stop. */
3334 static enum prop_handled
3335 handle_composition_prop (it)
3336 struct it *it;
3338 Lisp_Object prop, string;
3339 int pos, pos_byte, end;
3340 enum prop_handled handled = HANDLED_NORMALLY;
3342 if (STRINGP (it->string))
3344 pos = IT_STRING_CHARPOS (*it);
3345 pos_byte = IT_STRING_BYTEPOS (*it);
3346 string = it->string;
3348 else
3350 pos = IT_CHARPOS (*it);
3351 pos_byte = IT_BYTEPOS (*it);
3352 string = Qnil;
3355 /* If there's a valid composition and point is not inside of the
3356 composition (in the case that the composition is from the current
3357 buffer), draw a glyph composed from the composition components. */
3358 if (find_composition (pos, -1, &pos, &end, &prop, string)
3359 && COMPOSITION_VALID_P (pos, end, prop)
3360 && (STRINGP (it->string) || (PT <= pos || PT >= end)))
3362 int id = get_composition_id (pos, pos_byte, end - pos, prop, string);
3364 if (id >= 0)
3366 it->method = next_element_from_composition;
3367 it->cmp_id = id;
3368 it->cmp_len = COMPOSITION_LENGTH (prop);
3369 /* For a terminal, draw only the first character of the
3370 components. */
3371 it->c = COMPOSITION_GLYPH (composition_table[id], 0);
3372 it->len = (STRINGP (it->string)
3373 ? string_char_to_byte (it->string, end)
3374 : CHAR_TO_BYTE (end)) - pos_byte;
3375 it->stop_charpos = end;
3376 handled = HANDLED_RETURN;
3380 return handled;
3385 /***********************************************************************
3386 Overlay strings
3387 ***********************************************************************/
3389 /* The following structure is used to record overlay strings for
3390 later sorting in load_overlay_strings. */
3392 struct overlay_entry
3394 Lisp_Object overlay;
3395 Lisp_Object string;
3396 int priority;
3397 int after_string_p;
3401 /* Set up iterator IT from overlay strings at its current position.
3402 Called from handle_stop. */
3404 static enum prop_handled
3405 handle_overlay_change (it)
3406 struct it *it;
3408 if (!STRINGP (it->string) && get_overlay_strings (it, 0))
3409 return HANDLED_RECOMPUTE_PROPS;
3410 else
3411 return HANDLED_NORMALLY;
3415 /* Set up the next overlay string for delivery by IT, if there is an
3416 overlay string to deliver. Called by set_iterator_to_next when the
3417 end of the current overlay string is reached. If there are more
3418 overlay strings to display, IT->string and
3419 IT->current.overlay_string_index are set appropriately here.
3420 Otherwise IT->string is set to nil. */
3422 static void
3423 next_overlay_string (it)
3424 struct it *it;
3426 ++it->current.overlay_string_index;
3427 if (it->current.overlay_string_index == it->n_overlay_strings)
3429 /* No more overlay strings. Restore IT's settings to what
3430 they were before overlay strings were processed, and
3431 continue to deliver from current_buffer. */
3432 int display_ellipsis_p = it->stack[it->sp - 1].display_ellipsis_p;
3434 pop_it (it);
3435 xassert (it->stop_charpos >= BEGV
3436 && it->stop_charpos <= it->end_charpos);
3437 it->string = Qnil;
3438 it->current.overlay_string_index = -1;
3439 SET_TEXT_POS (it->current.string_pos, -1, -1);
3440 it->n_overlay_strings = 0;
3441 it->method = next_element_from_buffer;
3443 /* If we're at the end of the buffer, record that we have
3444 processed the overlay strings there already, so that
3445 next_element_from_buffer doesn't try it again. */
3446 if (IT_CHARPOS (*it) >= it->end_charpos)
3447 it->overlay_strings_at_end_processed_p = 1;
3449 /* If we have to display `...' for invisible text, set
3450 the iterator up for that. */
3451 if (display_ellipsis_p)
3452 setup_for_ellipsis (it);
3454 else
3456 /* There are more overlay strings to process. If
3457 IT->current.overlay_string_index has advanced to a position
3458 where we must load IT->overlay_strings with more strings, do
3459 it. */
3460 int i = it->current.overlay_string_index % OVERLAY_STRING_CHUNK_SIZE;
3462 if (it->current.overlay_string_index && i == 0)
3463 load_overlay_strings (it, 0);
3465 /* Initialize IT to deliver display elements from the overlay
3466 string. */
3467 it->string = it->overlay_strings[i];
3468 it->multibyte_p = STRING_MULTIBYTE (it->string);
3469 SET_TEXT_POS (it->current.string_pos, 0, 0);
3470 it->method = next_element_from_string;
3471 it->stop_charpos = 0;
3474 CHECK_IT (it);
3478 /* Compare two overlay_entry structures E1 and E2. Used as a
3479 comparison function for qsort in load_overlay_strings. Overlay
3480 strings for the same position are sorted so that
3482 1. All after-strings come in front of before-strings, except
3483 when they come from the same overlay.
3485 2. Within after-strings, strings are sorted so that overlay strings
3486 from overlays with higher priorities come first.
3488 2. Within before-strings, strings are sorted so that overlay
3489 strings from overlays with higher priorities come last.
3491 Value is analogous to strcmp. */
3494 static int
3495 compare_overlay_entries (e1, e2)
3496 void *e1, *e2;
3498 struct overlay_entry *entry1 = (struct overlay_entry *) e1;
3499 struct overlay_entry *entry2 = (struct overlay_entry *) e2;
3500 int result;
3502 if (entry1->after_string_p != entry2->after_string_p)
3504 /* Let after-strings appear in front of before-strings if
3505 they come from different overlays. */
3506 if (EQ (entry1->overlay, entry2->overlay))
3507 result = entry1->after_string_p ? 1 : -1;
3508 else
3509 result = entry1->after_string_p ? -1 : 1;
3511 else if (entry1->after_string_p)
3512 /* After-strings sorted in order of decreasing priority. */
3513 result = entry2->priority - entry1->priority;
3514 else
3515 /* Before-strings sorted in order of increasing priority. */
3516 result = entry1->priority - entry2->priority;
3518 return result;
3522 /* Load the vector IT->overlay_strings with overlay strings from IT's
3523 current buffer position, or from CHARPOS if that is > 0. Set
3524 IT->n_overlays to the total number of overlay strings found.
3526 Overlay strings are processed OVERLAY_STRING_CHUNK_SIZE strings at
3527 a time. On entry into load_overlay_strings,
3528 IT->current.overlay_string_index gives the number of overlay
3529 strings that have already been loaded by previous calls to this
3530 function.
3532 IT->add_overlay_start contains an additional overlay start
3533 position to consider for taking overlay strings from, if non-zero.
3534 This position comes into play when the overlay has an `invisible'
3535 property, and both before and after-strings. When we've skipped to
3536 the end of the overlay, because of its `invisible' property, we
3537 nevertheless want its before-string to appear.
3538 IT->add_overlay_start will contain the overlay start position
3539 in this case.
3541 Overlay strings are sorted so that after-string strings come in
3542 front of before-string strings. Within before and after-strings,
3543 strings are sorted by overlay priority. See also function
3544 compare_overlay_entries. */
3546 static void
3547 load_overlay_strings (it, charpos)
3548 struct it *it;
3549 int charpos;
3551 extern Lisp_Object Qafter_string, Qbefore_string, Qwindow, Qpriority;
3552 Lisp_Object ov, overlay, window, str, invisible;
3553 int start, end;
3554 int size = 20;
3555 int n = 0, i, j, invis_p;
3556 struct overlay_entry *entries
3557 = (struct overlay_entry *) alloca (size * sizeof *entries);
3559 if (charpos <= 0)
3560 charpos = IT_CHARPOS (*it);
3562 /* Append the overlay string STRING of overlay OVERLAY to vector
3563 `entries' which has size `size' and currently contains `n'
3564 elements. AFTER_P non-zero means STRING is an after-string of
3565 OVERLAY. */
3566 #define RECORD_OVERLAY_STRING(OVERLAY, STRING, AFTER_P) \
3567 do \
3569 Lisp_Object priority; \
3571 if (n == size) \
3573 int new_size = 2 * size; \
3574 struct overlay_entry *old = entries; \
3575 entries = \
3576 (struct overlay_entry *) alloca (new_size \
3577 * sizeof *entries); \
3578 bcopy (old, entries, size * sizeof *entries); \
3579 size = new_size; \
3582 entries[n].string = (STRING); \
3583 entries[n].overlay = (OVERLAY); \
3584 priority = Foverlay_get ((OVERLAY), Qpriority); \
3585 entries[n].priority = INTEGERP (priority) ? XINT (priority) : 0; \
3586 entries[n].after_string_p = (AFTER_P); \
3587 ++n; \
3589 while (0)
3591 /* Process overlay before the overlay center. */
3592 for (ov = current_buffer->overlays_before; CONSP (ov); ov = XCDR (ov))
3594 overlay = XCAR (ov);
3595 xassert (OVERLAYP (overlay));
3596 start = OVERLAY_POSITION (OVERLAY_START (overlay));
3597 end = OVERLAY_POSITION (OVERLAY_END (overlay));
3599 if (end < charpos)
3600 break;
3602 /* Skip this overlay if it doesn't start or end at IT's current
3603 position. */
3604 if (end != charpos && start != charpos)
3605 continue;
3607 /* Skip this overlay if it doesn't apply to IT->w. */
3608 window = Foverlay_get (overlay, Qwindow);
3609 if (WINDOWP (window) && XWINDOW (window) != it->w)
3610 continue;
3612 /* If the text ``under'' the overlay is invisible, both before-
3613 and after-strings from this overlay are visible; start and
3614 end position are indistinguishable. */
3615 invisible = Foverlay_get (overlay, Qinvisible);
3616 invis_p = TEXT_PROP_MEANS_INVISIBLE (invisible);
3618 /* If overlay has a non-empty before-string, record it. */
3619 if ((start == charpos || (end == charpos && invis_p))
3620 && (str = Foverlay_get (overlay, Qbefore_string), STRINGP (str))
3621 && SCHARS (str))
3622 RECORD_OVERLAY_STRING (overlay, str, 0);
3624 /* If overlay has a non-empty after-string, record it. */
3625 if ((end == charpos || (start == charpos && invis_p))
3626 && (str = Foverlay_get (overlay, Qafter_string), STRINGP (str))
3627 && SCHARS (str))
3628 RECORD_OVERLAY_STRING (overlay, str, 1);
3631 /* Process overlays after the overlay center. */
3632 for (ov = current_buffer->overlays_after; CONSP (ov); ov = XCDR (ov))
3634 overlay = XCAR (ov);
3635 xassert (OVERLAYP (overlay));
3636 start = OVERLAY_POSITION (OVERLAY_START (overlay));
3637 end = OVERLAY_POSITION (OVERLAY_END (overlay));
3639 if (start > charpos)
3640 break;
3642 /* Skip this overlay if it doesn't start or end at IT's current
3643 position. */
3644 if (end != charpos && start != charpos)
3645 continue;
3647 /* Skip this overlay if it doesn't apply to IT->w. */
3648 window = Foverlay_get (overlay, Qwindow);
3649 if (WINDOWP (window) && XWINDOW (window) != it->w)
3650 continue;
3652 /* If the text ``under'' the overlay is invisible, it has a zero
3653 dimension, and both before- and after-strings apply. */
3654 invisible = Foverlay_get (overlay, Qinvisible);
3655 invis_p = TEXT_PROP_MEANS_INVISIBLE (invisible);
3657 /* If overlay has a non-empty before-string, record it. */
3658 if ((start == charpos || (end == charpos && invis_p))
3659 && (str = Foverlay_get (overlay, Qbefore_string), STRINGP (str))
3660 && SCHARS (str))
3661 RECORD_OVERLAY_STRING (overlay, str, 0);
3663 /* If overlay has a non-empty after-string, record it. */
3664 if ((end == charpos || (start == charpos && invis_p))
3665 && (str = Foverlay_get (overlay, Qafter_string), STRINGP (str))
3666 && SCHARS (str))
3667 RECORD_OVERLAY_STRING (overlay, str, 1);
3670 #undef RECORD_OVERLAY_STRING
3672 /* Sort entries. */
3673 if (n > 1)
3674 qsort (entries, n, sizeof *entries, compare_overlay_entries);
3676 /* Record the total number of strings to process. */
3677 it->n_overlay_strings = n;
3679 /* IT->current.overlay_string_index is the number of overlay strings
3680 that have already been consumed by IT. Copy some of the
3681 remaining overlay strings to IT->overlay_strings. */
3682 i = 0;
3683 j = it->current.overlay_string_index;
3684 while (i < OVERLAY_STRING_CHUNK_SIZE && j < n)
3685 it->overlay_strings[i++] = entries[j++].string;
3687 CHECK_IT (it);
3691 /* Get the first chunk of overlay strings at IT's current buffer
3692 position, or at CHARPOS if that is > 0. Value is non-zero if at
3693 least one overlay string was found. */
3695 static int
3696 get_overlay_strings (it, charpos)
3697 struct it *it;
3698 int charpos;
3700 /* Get the first OVERLAY_STRING_CHUNK_SIZE overlay strings to
3701 process. This fills IT->overlay_strings with strings, and sets
3702 IT->n_overlay_strings to the total number of strings to process.
3703 IT->pos.overlay_string_index has to be set temporarily to zero
3704 because load_overlay_strings needs this; it must be set to -1
3705 when no overlay strings are found because a zero value would
3706 indicate a position in the first overlay string. */
3707 it->current.overlay_string_index = 0;
3708 load_overlay_strings (it, charpos);
3710 /* If we found overlay strings, set up IT to deliver display
3711 elements from the first one. Otherwise set up IT to deliver
3712 from current_buffer. */
3713 if (it->n_overlay_strings)
3715 /* Make sure we know settings in current_buffer, so that we can
3716 restore meaningful values when we're done with the overlay
3717 strings. */
3718 compute_stop_pos (it);
3719 xassert (it->face_id >= 0);
3721 /* Save IT's settings. They are restored after all overlay
3722 strings have been processed. */
3723 xassert (it->sp == 0);
3724 push_it (it);
3726 /* Set up IT to deliver display elements from the first overlay
3727 string. */
3728 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = 0;
3729 it->string = it->overlay_strings[0];
3730 it->stop_charpos = 0;
3731 xassert (STRINGP (it->string));
3732 it->end_charpos = SCHARS (it->string);
3733 it->multibyte_p = STRING_MULTIBYTE (it->string);
3734 it->method = next_element_from_string;
3736 else
3738 it->string = Qnil;
3739 it->current.overlay_string_index = -1;
3740 it->method = next_element_from_buffer;
3743 CHECK_IT (it);
3745 /* Value is non-zero if we found at least one overlay string. */
3746 return STRINGP (it->string);
3751 /***********************************************************************
3752 Saving and restoring state
3753 ***********************************************************************/
3755 /* Save current settings of IT on IT->stack. Called, for example,
3756 before setting up IT for an overlay string, to be able to restore
3757 IT's settings to what they were after the overlay string has been
3758 processed. */
3760 static void
3761 push_it (it)
3762 struct it *it;
3764 struct iterator_stack_entry *p;
3766 xassert (it->sp < 2);
3767 p = it->stack + it->sp;
3769 p->stop_charpos = it->stop_charpos;
3770 xassert (it->face_id >= 0);
3771 p->face_id = it->face_id;
3772 p->string = it->string;
3773 p->pos = it->current;
3774 p->end_charpos = it->end_charpos;
3775 p->string_nchars = it->string_nchars;
3776 p->area = it->area;
3777 p->multibyte_p = it->multibyte_p;
3778 p->space_width = it->space_width;
3779 p->font_height = it->font_height;
3780 p->voffset = it->voffset;
3781 p->string_from_display_prop_p = it->string_from_display_prop_p;
3782 p->display_ellipsis_p = 0;
3783 ++it->sp;
3787 /* Restore IT's settings from IT->stack. Called, for example, when no
3788 more overlay strings must be processed, and we return to delivering
3789 display elements from a buffer, or when the end of a string from a
3790 `display' property is reached and we return to delivering display
3791 elements from an overlay string, or from a buffer. */
3793 static void
3794 pop_it (it)
3795 struct it *it;
3797 struct iterator_stack_entry *p;
3799 xassert (it->sp > 0);
3800 --it->sp;
3801 p = it->stack + it->sp;
3802 it->stop_charpos = p->stop_charpos;
3803 it->face_id = p->face_id;
3804 it->string = p->string;
3805 it->current = p->pos;
3806 it->end_charpos = p->end_charpos;
3807 it->string_nchars = p->string_nchars;
3808 it->area = p->area;
3809 it->multibyte_p = p->multibyte_p;
3810 it->space_width = p->space_width;
3811 it->font_height = p->font_height;
3812 it->voffset = p->voffset;
3813 it->string_from_display_prop_p = p->string_from_display_prop_p;
3818 /***********************************************************************
3819 Moving over lines
3820 ***********************************************************************/
3822 /* Set IT's current position to the previous line start. */
3824 static void
3825 back_to_previous_line_start (it)
3826 struct it *it;
3828 IT_CHARPOS (*it) = find_next_newline_no_quit (IT_CHARPOS (*it) - 1, -1);
3829 IT_BYTEPOS (*it) = CHAR_TO_BYTE (IT_CHARPOS (*it));
3833 /* Move IT to the next line start.
3835 Value is non-zero if a newline was found. Set *SKIPPED_P to 1 if
3836 we skipped over part of the text (as opposed to moving the iterator
3837 continuously over the text). Otherwise, don't change the value
3838 of *SKIPPED_P.
3840 Newlines may come from buffer text, overlay strings, or strings
3841 displayed via the `display' property. That's the reason we can't
3842 simply use find_next_newline_no_quit.
3844 Note that this function may not skip over invisible text that is so
3845 because of text properties and immediately follows a newline. If
3846 it would, function reseat_at_next_visible_line_start, when called
3847 from set_iterator_to_next, would effectively make invisible
3848 characters following a newline part of the wrong glyph row, which
3849 leads to wrong cursor motion. */
3851 static int
3852 forward_to_next_line_start (it, skipped_p)
3853 struct it *it;
3854 int *skipped_p;
3856 int old_selective, newline_found_p, n;
3857 const int MAX_NEWLINE_DISTANCE = 500;
3859 /* If already on a newline, just consume it to avoid unintended
3860 skipping over invisible text below. */
3861 if (it->what == IT_CHARACTER
3862 && it->c == '\n'
3863 && CHARPOS (it->position) == IT_CHARPOS (*it))
3865 set_iterator_to_next (it, 0);
3866 it->c = 0;
3867 return 1;
3870 /* Don't handle selective display in the following. It's (a)
3871 unnecessary because it's done by the caller, and (b) leads to an
3872 infinite recursion because next_element_from_ellipsis indirectly
3873 calls this function. */
3874 old_selective = it->selective;
3875 it->selective = 0;
3877 /* Scan for a newline within MAX_NEWLINE_DISTANCE display elements
3878 from buffer text. */
3879 for (n = newline_found_p = 0;
3880 !newline_found_p && n < MAX_NEWLINE_DISTANCE;
3881 n += STRINGP (it->string) ? 0 : 1)
3883 if (!get_next_display_element (it))
3884 return 0;
3885 newline_found_p = it->what == IT_CHARACTER && it->c == '\n';
3886 set_iterator_to_next (it, 0);
3889 /* If we didn't find a newline near enough, see if we can use a
3890 short-cut. */
3891 if (!newline_found_p)
3893 int start = IT_CHARPOS (*it);
3894 int limit = find_next_newline_no_quit (start, 1);
3895 Lisp_Object pos;
3897 xassert (!STRINGP (it->string));
3899 /* If there isn't any `display' property in sight, and no
3900 overlays, we can just use the position of the newline in
3901 buffer text. */
3902 if (it->stop_charpos >= limit
3903 || ((pos = Fnext_single_property_change (make_number (start),
3904 Qdisplay,
3905 Qnil, make_number (limit)),
3906 NILP (pos))
3907 && next_overlay_change (start) == ZV))
3909 IT_CHARPOS (*it) = limit;
3910 IT_BYTEPOS (*it) = CHAR_TO_BYTE (limit);
3911 *skipped_p = newline_found_p = 1;
3913 else
3915 while (get_next_display_element (it)
3916 && !newline_found_p)
3918 newline_found_p = ITERATOR_AT_END_OF_LINE_P (it);
3919 set_iterator_to_next (it, 0);
3924 it->selective = old_selective;
3925 return newline_found_p;
3929 /* Set IT's current position to the previous visible line start. Skip
3930 invisible text that is so either due to text properties or due to
3931 selective display. Caution: this does not change IT->current_x and
3932 IT->hpos. */
3934 static void
3935 back_to_previous_visible_line_start (it)
3936 struct it *it;
3938 int visible_p = 0;
3940 /* Go back one newline if not on BEGV already. */
3941 if (IT_CHARPOS (*it) > BEGV)
3942 back_to_previous_line_start (it);
3944 /* Move over lines that are invisible because of selective display
3945 or text properties. */
3946 while (IT_CHARPOS (*it) > BEGV
3947 && !visible_p)
3949 visible_p = 1;
3951 /* If selective > 0, then lines indented more than that values
3952 are invisible. */
3953 if (it->selective > 0
3954 && indented_beyond_p (IT_CHARPOS (*it), IT_BYTEPOS (*it),
3955 (double) it->selective)) /* iftc */
3956 visible_p = 0;
3957 else
3959 Lisp_Object prop;
3961 prop = Fget_char_property (make_number (IT_CHARPOS (*it)),
3962 Qinvisible, it->window);
3963 if (TEXT_PROP_MEANS_INVISIBLE (prop))
3964 visible_p = 0;
3967 /* Back one more newline if the current one is invisible. */
3968 if (!visible_p)
3969 back_to_previous_line_start (it);
3972 xassert (IT_CHARPOS (*it) >= BEGV);
3973 xassert (IT_CHARPOS (*it) == BEGV
3974 || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
3975 CHECK_IT (it);
3979 /* Reseat iterator IT at the previous visible line start. Skip
3980 invisible text that is so either due to text properties or due to
3981 selective display. At the end, update IT's overlay information,
3982 face information etc. */
3984 static void
3985 reseat_at_previous_visible_line_start (it)
3986 struct it *it;
3988 back_to_previous_visible_line_start (it);
3989 reseat (it, it->current.pos, 1);
3990 CHECK_IT (it);
3994 /* Reseat iterator IT on the next visible line start in the current
3995 buffer. ON_NEWLINE_P non-zero means position IT on the newline
3996 preceding the line start. Skip over invisible text that is so
3997 because of selective display. Compute faces, overlays etc at the
3998 new position. Note that this function does not skip over text that
3999 is invisible because of text properties. */
4001 static void
4002 reseat_at_next_visible_line_start (it, on_newline_p)
4003 struct it *it;
4004 int on_newline_p;
4006 int newline_found_p, skipped_p = 0;
4008 newline_found_p = forward_to_next_line_start (it, &skipped_p);
4010 /* Skip over lines that are invisible because they are indented
4011 more than the value of IT->selective. */
4012 if (it->selective > 0)
4013 while (IT_CHARPOS (*it) < ZV
4014 && indented_beyond_p (IT_CHARPOS (*it), IT_BYTEPOS (*it),
4015 (double) it->selective)) /* iftc */
4017 xassert (FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
4018 newline_found_p = forward_to_next_line_start (it, &skipped_p);
4021 /* Position on the newline if that's what's requested. */
4022 if (on_newline_p && newline_found_p)
4024 if (STRINGP (it->string))
4026 if (IT_STRING_CHARPOS (*it) > 0)
4028 --IT_STRING_CHARPOS (*it);
4029 --IT_STRING_BYTEPOS (*it);
4032 else if (IT_CHARPOS (*it) > BEGV)
4034 --IT_CHARPOS (*it);
4035 --IT_BYTEPOS (*it);
4036 reseat (it, it->current.pos, 0);
4039 else if (skipped_p)
4040 reseat (it, it->current.pos, 0);
4042 CHECK_IT (it);
4047 /***********************************************************************
4048 Changing an iterator's position
4049 ***********************************************************************/
4051 /* Change IT's current position to POS in current_buffer. If FORCE_P
4052 is non-zero, always check for text properties at the new position.
4053 Otherwise, text properties are only looked up if POS >=
4054 IT->check_charpos of a property. */
4056 static void
4057 reseat (it, pos, force_p)
4058 struct it *it;
4059 struct text_pos pos;
4060 int force_p;
4062 int original_pos = IT_CHARPOS (*it);
4064 reseat_1 (it, pos, 0);
4066 /* Determine where to check text properties. Avoid doing it
4067 where possible because text property lookup is very expensive. */
4068 if (force_p
4069 || CHARPOS (pos) > it->stop_charpos
4070 || CHARPOS (pos) < original_pos)
4071 handle_stop (it);
4073 CHECK_IT (it);
4077 /* Change IT's buffer position to POS. SET_STOP_P non-zero means set
4078 IT->stop_pos to POS, also. */
4080 static void
4081 reseat_1 (it, pos, set_stop_p)
4082 struct it *it;
4083 struct text_pos pos;
4084 int set_stop_p;
4086 /* Don't call this function when scanning a C string. */
4087 xassert (it->s == NULL);
4089 /* POS must be a reasonable value. */
4090 xassert (CHARPOS (pos) >= BEGV && CHARPOS (pos) <= ZV);
4092 it->current.pos = it->position = pos;
4093 XSETBUFFER (it->object, current_buffer);
4094 it->end_charpos = ZV;
4095 it->dpvec = NULL;
4096 it->current.dpvec_index = -1;
4097 it->current.overlay_string_index = -1;
4098 IT_STRING_CHARPOS (*it) = -1;
4099 IT_STRING_BYTEPOS (*it) = -1;
4100 it->string = Qnil;
4101 it->method = next_element_from_buffer;
4102 it->multibyte_p = !NILP (current_buffer->enable_multibyte_characters);
4103 it->sp = 0;
4104 it->face_before_selective_p = 0;
4106 if (set_stop_p)
4107 it->stop_charpos = CHARPOS (pos);
4111 /* Set up IT for displaying a string, starting at CHARPOS in window W.
4112 If S is non-null, it is a C string to iterate over. Otherwise,
4113 STRING gives a Lisp string to iterate over.
4115 If PRECISION > 0, don't return more then PRECISION number of
4116 characters from the string.
4118 If FIELD_WIDTH > 0, return padding spaces until FIELD_WIDTH
4119 characters have been returned. FIELD_WIDTH < 0 means an infinite
4120 field width.
4122 MULTIBYTE = 0 means disable processing of multibyte characters,
4123 MULTIBYTE > 0 means enable it,
4124 MULTIBYTE < 0 means use IT->multibyte_p.
4126 IT must be initialized via a prior call to init_iterator before
4127 calling this function. */
4129 static void
4130 reseat_to_string (it, s, string, charpos, precision, field_width, multibyte)
4131 struct it *it;
4132 unsigned char *s;
4133 Lisp_Object string;
4134 int charpos;
4135 int precision, field_width, multibyte;
4137 /* No region in strings. */
4138 it->region_beg_charpos = it->region_end_charpos = -1;
4140 /* No text property checks performed by default, but see below. */
4141 it->stop_charpos = -1;
4143 /* Set iterator position and end position. */
4144 bzero (&it->current, sizeof it->current);
4145 it->current.overlay_string_index = -1;
4146 it->current.dpvec_index = -1;
4147 xassert (charpos >= 0);
4149 /* If STRING is specified, use its multibyteness, otherwise use the
4150 setting of MULTIBYTE, if specified. */
4151 if (multibyte >= 0)
4152 it->multibyte_p = multibyte > 0;
4154 if (s == NULL)
4156 xassert (STRINGP (string));
4157 it->string = string;
4158 it->s = NULL;
4159 it->end_charpos = it->string_nchars = SCHARS (string);
4160 it->method = next_element_from_string;
4161 it->current.string_pos = string_pos (charpos, string);
4163 else
4165 it->s = s;
4166 it->string = Qnil;
4168 /* Note that we use IT->current.pos, not it->current.string_pos,
4169 for displaying C strings. */
4170 IT_STRING_CHARPOS (*it) = IT_STRING_BYTEPOS (*it) = -1;
4171 if (it->multibyte_p)
4173 it->current.pos = c_string_pos (charpos, s, 1);
4174 it->end_charpos = it->string_nchars = number_of_chars (s, 1);
4176 else
4178 IT_CHARPOS (*it) = IT_BYTEPOS (*it) = charpos;
4179 it->end_charpos = it->string_nchars = strlen (s);
4182 it->method = next_element_from_c_string;
4185 /* PRECISION > 0 means don't return more than PRECISION characters
4186 from the string. */
4187 if (precision > 0 && it->end_charpos - charpos > precision)
4188 it->end_charpos = it->string_nchars = charpos + precision;
4190 /* FIELD_WIDTH > 0 means pad with spaces until FIELD_WIDTH
4191 characters have been returned. FIELD_WIDTH == 0 means don't pad,
4192 FIELD_WIDTH < 0 means infinite field width. This is useful for
4193 padding with `-' at the end of a mode line. */
4194 if (field_width < 0)
4195 field_width = INFINITY;
4196 if (field_width > it->end_charpos - charpos)
4197 it->end_charpos = charpos + field_width;
4199 /* Use the standard display table for displaying strings. */
4200 if (DISP_TABLE_P (Vstandard_display_table))
4201 it->dp = XCHAR_TABLE (Vstandard_display_table);
4203 it->stop_charpos = charpos;
4204 CHECK_IT (it);
4209 /***********************************************************************
4210 Iteration
4211 ***********************************************************************/
4213 /* Load IT's display element fields with information about the next
4214 display element from the current position of IT. Value is zero if
4215 end of buffer (or C string) is reached. */
4218 get_next_display_element (it)
4219 struct it *it;
4221 /* Non-zero means that we found a display element. Zero means that
4222 we hit the end of what we iterate over. Performance note: the
4223 function pointer `method' used here turns out to be faster than
4224 using a sequence of if-statements. */
4225 int success_p = (*it->method) (it);
4227 if (it->what == IT_CHARACTER)
4229 /* Map via display table or translate control characters.
4230 IT->c, IT->len etc. have been set to the next character by
4231 the function call above. If we have a display table, and it
4232 contains an entry for IT->c, translate it. Don't do this if
4233 IT->c itself comes from a display table, otherwise we could
4234 end up in an infinite recursion. (An alternative could be to
4235 count the recursion depth of this function and signal an
4236 error when a certain maximum depth is reached.) Is it worth
4237 it? */
4238 if (success_p && it->dpvec == NULL)
4240 Lisp_Object dv;
4242 if (it->dp
4243 && (dv = DISP_CHAR_VECTOR (it->dp, it->c),
4244 VECTORP (dv)))
4246 struct Lisp_Vector *v = XVECTOR (dv);
4248 /* Return the first character from the display table
4249 entry, if not empty. If empty, don't display the
4250 current character. */
4251 if (v->size)
4253 it->dpvec_char_len = it->len;
4254 it->dpvec = v->contents;
4255 it->dpend = v->contents + v->size;
4256 it->current.dpvec_index = 0;
4257 it->method = next_element_from_display_vector;
4258 success_p = get_next_display_element (it);
4260 else
4262 set_iterator_to_next (it, 0);
4263 success_p = get_next_display_element (it);
4267 /* Translate control characters into `\003' or `^C' form.
4268 Control characters coming from a display table entry are
4269 currently not translated because we use IT->dpvec to hold
4270 the translation. This could easily be changed but I
4271 don't believe that it is worth doing.
4273 If it->multibyte_p is nonzero, eight-bit characters and
4274 non-printable multibyte characters are also translated to
4275 octal form.
4277 If it->multibyte_p is zero, eight-bit characters that
4278 don't have corresponding multibyte char code are also
4279 translated to octal form. */
4280 else if ((it->c < ' '
4281 && (it->area != TEXT_AREA
4282 || (it->c != '\n' && it->c != '\t')))
4283 || (it->multibyte_p
4284 ? ((it->c >= 127
4285 && it->len == 1)
4286 || !CHAR_PRINTABLE_P (it->c))
4287 : (it->c >= 127
4288 && it->c == unibyte_char_to_multibyte (it->c))))
4290 /* IT->c is a control character which must be displayed
4291 either as '\003' or as `^C' where the '\\' and '^'
4292 can be defined in the display table. Fill
4293 IT->ctl_chars with glyphs for what we have to
4294 display. Then, set IT->dpvec to these glyphs. */
4295 GLYPH g;
4297 if (it->c < 128 && it->ctl_arrow_p)
4299 /* Set IT->ctl_chars[0] to the glyph for `^'. */
4300 if (it->dp
4301 && INTEGERP (DISP_CTRL_GLYPH (it->dp))
4302 && GLYPH_CHAR_VALID_P (XINT (DISP_CTRL_GLYPH (it->dp))))
4303 g = XINT (DISP_CTRL_GLYPH (it->dp));
4304 else
4305 g = FAST_MAKE_GLYPH ('^', 0);
4306 XSETINT (it->ctl_chars[0], g);
4308 g = FAST_MAKE_GLYPH (it->c ^ 0100, 0);
4309 XSETINT (it->ctl_chars[1], g);
4311 /* Set up IT->dpvec and return first character from it. */
4312 it->dpvec_char_len = it->len;
4313 it->dpvec = it->ctl_chars;
4314 it->dpend = it->dpvec + 2;
4315 it->current.dpvec_index = 0;
4316 it->method = next_element_from_display_vector;
4317 get_next_display_element (it);
4319 else
4321 unsigned char str[MAX_MULTIBYTE_LENGTH];
4322 int len;
4323 int i;
4324 GLYPH escape_glyph;
4326 /* Set IT->ctl_chars[0] to the glyph for `\\'. */
4327 if (it->dp
4328 && INTEGERP (DISP_ESCAPE_GLYPH (it->dp))
4329 && GLYPH_CHAR_VALID_P (XFASTINT (DISP_ESCAPE_GLYPH (it->dp))))
4330 escape_glyph = XFASTINT (DISP_ESCAPE_GLYPH (it->dp));
4331 else
4332 escape_glyph = FAST_MAKE_GLYPH ('\\', 0);
4334 if (SINGLE_BYTE_CHAR_P (it->c))
4335 str[0] = it->c, len = 1;
4336 else
4338 len = CHAR_STRING_NO_SIGNAL (it->c, str);
4339 if (len < 0)
4341 /* It's an invalid character, which
4342 shouldn't happen actually, but due to
4343 bugs it may happen. Let's print the char
4344 as is, there's not much meaningful we can
4345 do with it. */
4346 str[0] = it->c;
4347 str[1] = it->c >> 8;
4348 str[2] = it->c >> 16;
4349 str[3] = it->c >> 24;
4350 len = 4;
4354 for (i = 0; i < len; i++)
4356 XSETINT (it->ctl_chars[i * 4], escape_glyph);
4357 /* Insert three more glyphs into IT->ctl_chars for
4358 the octal display of the character. */
4359 g = FAST_MAKE_GLYPH (((str[i] >> 6) & 7) + '0', 0);
4360 XSETINT (it->ctl_chars[i * 4 + 1], g);
4361 g = FAST_MAKE_GLYPH (((str[i] >> 3) & 7) + '0', 0);
4362 XSETINT (it->ctl_chars[i * 4 + 2], g);
4363 g = FAST_MAKE_GLYPH ((str[i] & 7) + '0', 0);
4364 XSETINT (it->ctl_chars[i * 4 + 3], g);
4367 /* Set up IT->dpvec and return the first character
4368 from it. */
4369 it->dpvec_char_len = it->len;
4370 it->dpvec = it->ctl_chars;
4371 it->dpend = it->dpvec + len * 4;
4372 it->current.dpvec_index = 0;
4373 it->method = next_element_from_display_vector;
4374 get_next_display_element (it);
4379 /* Adjust face id for a multibyte character. There are no
4380 multibyte character in unibyte text. */
4381 if (it->multibyte_p
4382 && success_p
4383 && FRAME_WINDOW_P (it->f))
4385 struct face *face = FACE_FROM_ID (it->f, it->face_id);
4386 it->face_id = FACE_FOR_CHAR (it->f, face, it->c);
4390 /* Is this character the last one of a run of characters with
4391 box? If yes, set IT->end_of_box_run_p to 1. */
4392 if (it->face_box_p
4393 && it->s == NULL)
4395 int face_id;
4396 struct face *face;
4398 it->end_of_box_run_p
4399 = ((face_id = face_after_it_pos (it),
4400 face_id != it->face_id)
4401 && (face = FACE_FROM_ID (it->f, face_id),
4402 face->box == FACE_NO_BOX));
4405 /* Value is 0 if end of buffer or string reached. */
4406 return success_p;
4410 /* Move IT to the next display element.
4412 RESEAT_P non-zero means if called on a newline in buffer text,
4413 skip to the next visible line start.
4415 Functions get_next_display_element and set_iterator_to_next are
4416 separate because I find this arrangement easier to handle than a
4417 get_next_display_element function that also increments IT's
4418 position. The way it is we can first look at an iterator's current
4419 display element, decide whether it fits on a line, and if it does,
4420 increment the iterator position. The other way around we probably
4421 would either need a flag indicating whether the iterator has to be
4422 incremented the next time, or we would have to implement a
4423 decrement position function which would not be easy to write. */
4425 void
4426 set_iterator_to_next (it, reseat_p)
4427 struct it *it;
4428 int reseat_p;
4430 /* Reset flags indicating start and end of a sequence of characters
4431 with box. Reset them at the start of this function because
4432 moving the iterator to a new position might set them. */
4433 it->start_of_box_run_p = it->end_of_box_run_p = 0;
4435 if (it->method == next_element_from_buffer)
4437 /* The current display element of IT is a character from
4438 current_buffer. Advance in the buffer, and maybe skip over
4439 invisible lines that are so because of selective display. */
4440 if (ITERATOR_AT_END_OF_LINE_P (it) && reseat_p)
4441 reseat_at_next_visible_line_start (it, 0);
4442 else
4444 xassert (it->len != 0);
4445 IT_BYTEPOS (*it) += it->len;
4446 IT_CHARPOS (*it) += 1;
4447 xassert (IT_BYTEPOS (*it) == CHAR_TO_BYTE (IT_CHARPOS (*it)));
4450 else if (it->method == next_element_from_composition)
4452 xassert (it->cmp_id >= 0 && it ->cmp_id < n_compositions);
4453 if (STRINGP (it->string))
4455 IT_STRING_BYTEPOS (*it) += it->len;
4456 IT_STRING_CHARPOS (*it) += it->cmp_len;
4457 it->method = next_element_from_string;
4458 goto consider_string_end;
4460 else
4462 IT_BYTEPOS (*it) += it->len;
4463 IT_CHARPOS (*it) += it->cmp_len;
4464 it->method = next_element_from_buffer;
4467 else if (it->method == next_element_from_c_string)
4469 /* Current display element of IT is from a C string. */
4470 IT_BYTEPOS (*it) += it->len;
4471 IT_CHARPOS (*it) += 1;
4473 else if (it->method == next_element_from_display_vector)
4475 /* Current display element of IT is from a display table entry.
4476 Advance in the display table definition. Reset it to null if
4477 end reached, and continue with characters from buffers/
4478 strings. */
4479 ++it->current.dpvec_index;
4481 /* Restore face of the iterator to what they were before the
4482 display vector entry (these entries may contain faces). */
4483 it->face_id = it->saved_face_id;
4485 if (it->dpvec + it->current.dpvec_index == it->dpend)
4487 if (it->s)
4488 it->method = next_element_from_c_string;
4489 else if (STRINGP (it->string))
4490 it->method = next_element_from_string;
4491 else
4492 it->method = next_element_from_buffer;
4494 it->dpvec = NULL;
4495 it->current.dpvec_index = -1;
4497 /* Skip over characters which were displayed via IT->dpvec. */
4498 if (it->dpvec_char_len < 0)
4499 reseat_at_next_visible_line_start (it, 1);
4500 else if (it->dpvec_char_len > 0)
4502 it->len = it->dpvec_char_len;
4503 set_iterator_to_next (it, reseat_p);
4507 else if (it->method == next_element_from_string)
4509 /* Current display element is a character from a Lisp string. */
4510 xassert (it->s == NULL && STRINGP (it->string));
4511 IT_STRING_BYTEPOS (*it) += it->len;
4512 IT_STRING_CHARPOS (*it) += 1;
4514 consider_string_end:
4516 if (it->current.overlay_string_index >= 0)
4518 /* IT->string is an overlay string. Advance to the
4519 next, if there is one. */
4520 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string))
4521 next_overlay_string (it);
4523 else
4525 /* IT->string is not an overlay string. If we reached
4526 its end, and there is something on IT->stack, proceed
4527 with what is on the stack. This can be either another
4528 string, this time an overlay string, or a buffer. */
4529 if (IT_STRING_CHARPOS (*it) == SCHARS (it->string)
4530 && it->sp > 0)
4532 pop_it (it);
4533 if (!STRINGP (it->string))
4534 it->method = next_element_from_buffer;
4535 else
4536 goto consider_string_end;
4540 else if (it->method == next_element_from_image
4541 || it->method == next_element_from_stretch)
4543 /* The position etc with which we have to proceed are on
4544 the stack. The position may be at the end of a string,
4545 if the `display' property takes up the whole string. */
4546 pop_it (it);
4547 it->image_id = 0;
4548 if (STRINGP (it->string))
4550 it->method = next_element_from_string;
4551 goto consider_string_end;
4553 else
4554 it->method = next_element_from_buffer;
4556 else
4557 /* There are no other methods defined, so this should be a bug. */
4558 abort ();
4560 xassert (it->method != next_element_from_string
4561 || (STRINGP (it->string)
4562 && IT_STRING_CHARPOS (*it) >= 0));
4566 /* Load IT's display element fields with information about the next
4567 display element which comes from a display table entry or from the
4568 result of translating a control character to one of the forms `^C'
4569 or `\003'. IT->dpvec holds the glyphs to return as characters. */
4571 static int
4572 next_element_from_display_vector (it)
4573 struct it *it;
4575 /* Precondition. */
4576 xassert (it->dpvec && it->current.dpvec_index >= 0);
4578 /* Remember the current face id in case glyphs specify faces.
4579 IT's face is restored in set_iterator_to_next. */
4580 it->saved_face_id = it->face_id;
4582 if (INTEGERP (*it->dpvec)
4583 && GLYPH_CHAR_VALID_P (XFASTINT (*it->dpvec)))
4585 int lface_id;
4586 GLYPH g;
4588 g = XFASTINT (it->dpvec[it->current.dpvec_index]);
4589 it->c = FAST_GLYPH_CHAR (g);
4590 it->len = CHAR_BYTES (it->c);
4592 /* The entry may contain a face id to use. Such a face id is
4593 the id of a Lisp face, not a realized face. A face id of
4594 zero means no face is specified. */
4595 lface_id = FAST_GLYPH_FACE (g);
4596 if (lface_id)
4598 /* The function returns -1 if lface_id is invalid. */
4599 int face_id = ascii_face_of_lisp_face (it->f, lface_id);
4600 if (face_id >= 0)
4601 it->face_id = face_id;
4604 else
4605 /* Display table entry is invalid. Return a space. */
4606 it->c = ' ', it->len = 1;
4608 /* Don't change position and object of the iterator here. They are
4609 still the values of the character that had this display table
4610 entry or was translated, and that's what we want. */
4611 it->what = IT_CHARACTER;
4612 return 1;
4616 /* Load IT with the next display element from Lisp string IT->string.
4617 IT->current.string_pos is the current position within the string.
4618 If IT->current.overlay_string_index >= 0, the Lisp string is an
4619 overlay string. */
4621 static int
4622 next_element_from_string (it)
4623 struct it *it;
4625 struct text_pos position;
4627 xassert (STRINGP (it->string));
4628 xassert (IT_STRING_CHARPOS (*it) >= 0);
4629 position = it->current.string_pos;
4631 /* Time to check for invisible text? */
4632 if (IT_STRING_CHARPOS (*it) < it->end_charpos
4633 && IT_STRING_CHARPOS (*it) == it->stop_charpos)
4635 handle_stop (it);
4637 /* Since a handler may have changed IT->method, we must
4638 recurse here. */
4639 return get_next_display_element (it);
4642 if (it->current.overlay_string_index >= 0)
4644 /* Get the next character from an overlay string. In overlay
4645 strings, There is no field width or padding with spaces to
4646 do. */
4647 if (IT_STRING_CHARPOS (*it) >= SCHARS (it->string))
4649 it->what = IT_EOB;
4650 return 0;
4652 else if (STRING_MULTIBYTE (it->string))
4654 int remaining = SBYTES (it->string) - IT_STRING_BYTEPOS (*it);
4655 const unsigned char *s = (SDATA (it->string)
4656 + IT_STRING_BYTEPOS (*it));
4657 it->c = string_char_and_length (s, remaining, &it->len);
4659 else
4661 it->c = SREF (it->string, IT_STRING_BYTEPOS (*it));
4662 it->len = 1;
4665 else
4667 /* Get the next character from a Lisp string that is not an
4668 overlay string. Such strings come from the mode line, for
4669 example. We may have to pad with spaces, or truncate the
4670 string. See also next_element_from_c_string. */
4671 if (IT_STRING_CHARPOS (*it) >= it->end_charpos)
4673 it->what = IT_EOB;
4674 return 0;
4676 else if (IT_STRING_CHARPOS (*it) >= it->string_nchars)
4678 /* Pad with spaces. */
4679 it->c = ' ', it->len = 1;
4680 CHARPOS (position) = BYTEPOS (position) = -1;
4682 else if (STRING_MULTIBYTE (it->string))
4684 int maxlen = SBYTES (it->string) - IT_STRING_BYTEPOS (*it);
4685 const unsigned char *s = (SDATA (it->string)
4686 + IT_STRING_BYTEPOS (*it));
4687 it->c = string_char_and_length (s, maxlen, &it->len);
4689 else
4691 it->c = SREF (it->string, IT_STRING_BYTEPOS (*it));
4692 it->len = 1;
4696 /* Record what we have and where it came from. Note that we store a
4697 buffer position in IT->position although it could arguably be a
4698 string position. */
4699 it->what = IT_CHARACTER;
4700 it->object = it->string;
4701 it->position = position;
4702 return 1;
4706 /* Load IT with next display element from C string IT->s.
4707 IT->string_nchars is the maximum number of characters to return
4708 from the string. IT->end_charpos may be greater than
4709 IT->string_nchars when this function is called, in which case we
4710 may have to return padding spaces. Value is zero if end of string
4711 reached, including padding spaces. */
4713 static int
4714 next_element_from_c_string (it)
4715 struct it *it;
4717 int success_p = 1;
4719 xassert (it->s);
4720 it->what = IT_CHARACTER;
4721 BYTEPOS (it->position) = CHARPOS (it->position) = 0;
4722 it->object = Qnil;
4724 /* IT's position can be greater IT->string_nchars in case a field
4725 width or precision has been specified when the iterator was
4726 initialized. */
4727 if (IT_CHARPOS (*it) >= it->end_charpos)
4729 /* End of the game. */
4730 it->what = IT_EOB;
4731 success_p = 0;
4733 else if (IT_CHARPOS (*it) >= it->string_nchars)
4735 /* Pad with spaces. */
4736 it->c = ' ', it->len = 1;
4737 BYTEPOS (it->position) = CHARPOS (it->position) = -1;
4739 else if (it->multibyte_p)
4741 /* Implementation note: The calls to strlen apparently aren't a
4742 performance problem because there is no noticeable performance
4743 difference between Emacs running in unibyte or multibyte mode. */
4744 int maxlen = strlen (it->s) - IT_BYTEPOS (*it);
4745 it->c = string_char_and_length (it->s + IT_BYTEPOS (*it),
4746 maxlen, &it->len);
4748 else
4749 it->c = it->s[IT_BYTEPOS (*it)], it->len = 1;
4751 return success_p;
4755 /* Set up IT to return characters from an ellipsis, if appropriate.
4756 The definition of the ellipsis glyphs may come from a display table
4757 entry. This function Fills IT with the first glyph from the
4758 ellipsis if an ellipsis is to be displayed. */
4760 static int
4761 next_element_from_ellipsis (it)
4762 struct it *it;
4764 if (it->selective_display_ellipsis_p)
4766 if (it->dp && VECTORP (DISP_INVIS_VECTOR (it->dp)))
4768 /* Use the display table definition for `...'. Invalid glyphs
4769 will be handled by the method returning elements from dpvec. */
4770 struct Lisp_Vector *v = XVECTOR (DISP_INVIS_VECTOR (it->dp));
4771 it->dpvec_char_len = it->len;
4772 it->dpvec = v->contents;
4773 it->dpend = v->contents + v->size;
4774 it->current.dpvec_index = 0;
4775 it->method = next_element_from_display_vector;
4777 else
4779 /* Use default `...' which is stored in default_invis_vector. */
4780 it->dpvec_char_len = it->len;
4781 it->dpvec = default_invis_vector;
4782 it->dpend = default_invis_vector + 3;
4783 it->current.dpvec_index = 0;
4784 it->method = next_element_from_display_vector;
4787 else
4789 /* The face at the current position may be different from the
4790 face we find after the invisible text. Remember what it
4791 was in IT->saved_face_id, and signal that it's there by
4792 setting face_before_selective_p. */
4793 it->saved_face_id = it->face_id;
4794 it->method = next_element_from_buffer;
4795 reseat_at_next_visible_line_start (it, 1);
4796 it->face_before_selective_p = 1;
4799 return get_next_display_element (it);
4803 /* Deliver an image display element. The iterator IT is already
4804 filled with image information (done in handle_display_prop). Value
4805 is always 1. */
4808 static int
4809 next_element_from_image (it)
4810 struct it *it;
4812 it->what = IT_IMAGE;
4813 return 1;
4817 /* Fill iterator IT with next display element from a stretch glyph
4818 property. IT->object is the value of the text property. Value is
4819 always 1. */
4821 static int
4822 next_element_from_stretch (it)
4823 struct it *it;
4825 it->what = IT_STRETCH;
4826 return 1;
4830 /* Load IT with the next display element from current_buffer. Value
4831 is zero if end of buffer reached. IT->stop_charpos is the next
4832 position at which to stop and check for text properties or buffer
4833 end. */
4835 static int
4836 next_element_from_buffer (it)
4837 struct it *it;
4839 int success_p = 1;
4841 /* Check this assumption, otherwise, we would never enter the
4842 if-statement, below. */
4843 xassert (IT_CHARPOS (*it) >= BEGV
4844 && IT_CHARPOS (*it) <= it->stop_charpos);
4846 if (IT_CHARPOS (*it) >= it->stop_charpos)
4848 if (IT_CHARPOS (*it) >= it->end_charpos)
4850 int overlay_strings_follow_p;
4852 /* End of the game, except when overlay strings follow that
4853 haven't been returned yet. */
4854 if (it->overlay_strings_at_end_processed_p)
4855 overlay_strings_follow_p = 0;
4856 else
4858 it->overlay_strings_at_end_processed_p = 1;
4859 overlay_strings_follow_p = get_overlay_strings (it, 0);
4862 if (overlay_strings_follow_p)
4863 success_p = get_next_display_element (it);
4864 else
4866 it->what = IT_EOB;
4867 it->position = it->current.pos;
4868 success_p = 0;
4871 else
4873 handle_stop (it);
4874 return get_next_display_element (it);
4877 else
4879 /* No face changes, overlays etc. in sight, so just return a
4880 character from current_buffer. */
4881 unsigned char *p;
4883 /* Maybe run the redisplay end trigger hook. Performance note:
4884 This doesn't seem to cost measurable time. */
4885 if (it->redisplay_end_trigger_charpos
4886 && it->glyph_row
4887 && IT_CHARPOS (*it) >= it->redisplay_end_trigger_charpos)
4888 run_redisplay_end_trigger_hook (it);
4890 /* Get the next character, maybe multibyte. */
4891 p = BYTE_POS_ADDR (IT_BYTEPOS (*it));
4892 if (it->multibyte_p && !ASCII_BYTE_P (*p))
4894 int maxlen = ((IT_BYTEPOS (*it) >= GPT_BYTE ? ZV_BYTE : GPT_BYTE)
4895 - IT_BYTEPOS (*it));
4896 it->c = string_char_and_length (p, maxlen, &it->len);
4898 else
4899 it->c = *p, it->len = 1;
4901 /* Record what we have and where it came from. */
4902 it->what = IT_CHARACTER;;
4903 it->object = it->w->buffer;
4904 it->position = it->current.pos;
4906 /* Normally we return the character found above, except when we
4907 really want to return an ellipsis for selective display. */
4908 if (it->selective)
4910 if (it->c == '\n')
4912 /* A value of selective > 0 means hide lines indented more
4913 than that number of columns. */
4914 if (it->selective > 0
4915 && IT_CHARPOS (*it) + 1 < ZV
4916 && indented_beyond_p (IT_CHARPOS (*it) + 1,
4917 IT_BYTEPOS (*it) + 1,
4918 (double) it->selective)) /* iftc */
4920 success_p = next_element_from_ellipsis (it);
4921 it->dpvec_char_len = -1;
4924 else if (it->c == '\r' && it->selective == -1)
4926 /* A value of selective == -1 means that everything from the
4927 CR to the end of the line is invisible, with maybe an
4928 ellipsis displayed for it. */
4929 success_p = next_element_from_ellipsis (it);
4930 it->dpvec_char_len = -1;
4935 /* Value is zero if end of buffer reached. */
4936 xassert (!success_p || it->what != IT_CHARACTER || it->len > 0);
4937 return success_p;
4941 /* Run the redisplay end trigger hook for IT. */
4943 static void
4944 run_redisplay_end_trigger_hook (it)
4945 struct it *it;
4947 Lisp_Object args[3];
4949 /* IT->glyph_row should be non-null, i.e. we should be actually
4950 displaying something, or otherwise we should not run the hook. */
4951 xassert (it->glyph_row);
4953 /* Set up hook arguments. */
4954 args[0] = Qredisplay_end_trigger_functions;
4955 args[1] = it->window;
4956 XSETINT (args[2], it->redisplay_end_trigger_charpos);
4957 it->redisplay_end_trigger_charpos = 0;
4959 /* Since we are *trying* to run these functions, don't try to run
4960 them again, even if they get an error. */
4961 it->w->redisplay_end_trigger = Qnil;
4962 Frun_hook_with_args (3, args);
4964 /* Notice if it changed the face of the character we are on. */
4965 handle_face_prop (it);
4969 /* Deliver a composition display element. The iterator IT is already
4970 filled with composition information (done in
4971 handle_composition_prop). Value is always 1. */
4973 static int
4974 next_element_from_composition (it)
4975 struct it *it;
4977 it->what = IT_COMPOSITION;
4978 it->position = (STRINGP (it->string)
4979 ? it->current.string_pos
4980 : it->current.pos);
4981 return 1;
4986 /***********************************************************************
4987 Moving an iterator without producing glyphs
4988 ***********************************************************************/
4990 /* Move iterator IT to a specified buffer or X position within one
4991 line on the display without producing glyphs.
4993 OP should be a bit mask including some or all of these bits:
4994 MOVE_TO_X: Stop on reaching x-position TO_X.
4995 MOVE_TO_POS: Stop on reaching buffer or string position TO_CHARPOS.
4996 Regardless of OP's value, stop in reaching the end of the display line.
4998 TO_X is normally a value 0 <= TO_X <= IT->last_visible_x.
4999 This means, in particular, that TO_X includes window's horizontal
5000 scroll amount.
5002 The return value has several possible values that
5003 say what condition caused the scan to stop:
5005 MOVE_POS_MATCH_OR_ZV
5006 - when TO_POS or ZV was reached.
5008 MOVE_X_REACHED
5009 -when TO_X was reached before TO_POS or ZV were reached.
5011 MOVE_LINE_CONTINUED
5012 - when we reached the end of the display area and the line must
5013 be continued.
5015 MOVE_LINE_TRUNCATED
5016 - when we reached the end of the display area and the line is
5017 truncated.
5019 MOVE_NEWLINE_OR_CR
5020 - when we stopped at a line end, i.e. a newline or a CR and selective
5021 display is on. */
5023 static enum move_it_result
5024 move_it_in_display_line_to (it, to_charpos, to_x, op)
5025 struct it *it;
5026 int to_charpos, to_x, op;
5028 enum move_it_result result = MOVE_UNDEFINED;
5029 struct glyph_row *saved_glyph_row;
5031 /* Don't produce glyphs in produce_glyphs. */
5032 saved_glyph_row = it->glyph_row;
5033 it->glyph_row = NULL;
5035 while (1)
5037 int x, i, ascent = 0, descent = 0;
5039 /* Stop when ZV or TO_CHARPOS reached. */
5040 if (!get_next_display_element (it)
5041 || ((op & MOVE_TO_POS) != 0
5042 && BUFFERP (it->object)
5043 && IT_CHARPOS (*it) >= to_charpos))
5045 result = MOVE_POS_MATCH_OR_ZV;
5046 break;
5049 /* The call to produce_glyphs will get the metrics of the
5050 display element IT is loaded with. We record in x the
5051 x-position before this display element in case it does not
5052 fit on the line. */
5053 x = it->current_x;
5055 /* Remember the line height so far in case the next element doesn't
5056 fit on the line. */
5057 if (!it->truncate_lines_p)
5059 ascent = it->max_ascent;
5060 descent = it->max_descent;
5063 PRODUCE_GLYPHS (it);
5065 if (it->area != TEXT_AREA)
5067 set_iterator_to_next (it, 1);
5068 continue;
5071 /* The number of glyphs we get back in IT->nglyphs will normally
5072 be 1 except when IT->c is (i) a TAB, or (ii) a multi-glyph
5073 character on a terminal frame, or (iii) a line end. For the
5074 second case, IT->nglyphs - 1 padding glyphs will be present
5075 (on X frames, there is only one glyph produced for a
5076 composite character.
5078 The behavior implemented below means, for continuation lines,
5079 that as many spaces of a TAB as fit on the current line are
5080 displayed there. For terminal frames, as many glyphs of a
5081 multi-glyph character are displayed in the current line, too.
5082 This is what the old redisplay code did, and we keep it that
5083 way. Under X, the whole shape of a complex character must
5084 fit on the line or it will be completely displayed in the
5085 next line.
5087 Note that both for tabs and padding glyphs, all glyphs have
5088 the same width. */
5089 if (it->nglyphs)
5091 /* More than one glyph or glyph doesn't fit on line. All
5092 glyphs have the same width. */
5093 int single_glyph_width = it->pixel_width / it->nglyphs;
5094 int new_x;
5096 for (i = 0; i < it->nglyphs; ++i, x = new_x)
5098 new_x = x + single_glyph_width;
5100 /* We want to leave anything reaching TO_X to the caller. */
5101 if ((op & MOVE_TO_X) && new_x > to_x)
5103 it->current_x = x;
5104 result = MOVE_X_REACHED;
5105 break;
5107 else if (/* Lines are continued. */
5108 !it->truncate_lines_p
5109 && (/* And glyph doesn't fit on the line. */
5110 new_x > it->last_visible_x
5111 /* Or it fits exactly and we're on a window
5112 system frame. */
5113 || (new_x == it->last_visible_x
5114 && FRAME_WINDOW_P (it->f))))
5116 if (/* IT->hpos == 0 means the very first glyph
5117 doesn't fit on the line, e.g. a wide image. */
5118 it->hpos == 0
5119 || (new_x == it->last_visible_x
5120 && FRAME_WINDOW_P (it->f)))
5122 ++it->hpos;
5123 it->current_x = new_x;
5124 if (i == it->nglyphs - 1)
5125 set_iterator_to_next (it, 1);
5127 else
5129 it->current_x = x;
5130 it->max_ascent = ascent;
5131 it->max_descent = descent;
5134 TRACE_MOVE ((stderr, "move_it_in: continued at %d\n",
5135 IT_CHARPOS (*it)));
5136 result = MOVE_LINE_CONTINUED;
5137 break;
5139 else if (new_x > it->first_visible_x)
5141 /* Glyph is visible. Increment number of glyphs that
5142 would be displayed. */
5143 ++it->hpos;
5145 else
5147 /* Glyph is completely off the left margin of the display
5148 area. Nothing to do. */
5152 if (result != MOVE_UNDEFINED)
5153 break;
5155 else if ((op & MOVE_TO_X) && it->current_x >= to_x)
5157 /* Stop when TO_X specified and reached. This check is
5158 necessary here because of lines consisting of a line end,
5159 only. The line end will not produce any glyphs and we
5160 would never get MOVE_X_REACHED. */
5161 xassert (it->nglyphs == 0);
5162 result = MOVE_X_REACHED;
5163 break;
5166 /* Is this a line end? If yes, we're done. */
5167 if (ITERATOR_AT_END_OF_LINE_P (it))
5169 result = MOVE_NEWLINE_OR_CR;
5170 break;
5173 /* The current display element has been consumed. Advance
5174 to the next. */
5175 set_iterator_to_next (it, 1);
5177 /* Stop if lines are truncated and IT's current x-position is
5178 past the right edge of the window now. */
5179 if (it->truncate_lines_p
5180 && it->current_x >= it->last_visible_x)
5182 result = MOVE_LINE_TRUNCATED;
5183 break;
5187 /* Restore the iterator settings altered at the beginning of this
5188 function. */
5189 it->glyph_row = saved_glyph_row;
5190 return result;
5194 /* Move IT forward until it satisfies one or more of the criteria in
5195 TO_CHARPOS, TO_X, TO_Y, and TO_VPOS.
5197 OP is a bit-mask that specifies where to stop, and in particular,
5198 which of those four position arguments makes a difference. See the
5199 description of enum move_operation_enum.
5201 If TO_CHARPOS is in invisible text, e.g. a truncated part of a
5202 screen line, this function will set IT to the next position >
5203 TO_CHARPOS. */
5205 void
5206 move_it_to (it, to_charpos, to_x, to_y, to_vpos, op)
5207 struct it *it;
5208 int to_charpos, to_x, to_y, to_vpos;
5209 int op;
5211 enum move_it_result skip, skip2 = MOVE_X_REACHED;
5212 int line_height;
5213 int reached = 0;
5215 for (;;)
5217 if (op & MOVE_TO_VPOS)
5219 /* If no TO_CHARPOS and no TO_X specified, stop at the
5220 start of the line TO_VPOS. */
5221 if ((op & (MOVE_TO_X | MOVE_TO_POS)) == 0)
5223 if (it->vpos == to_vpos)
5225 reached = 1;
5226 break;
5228 else
5229 skip = move_it_in_display_line_to (it, -1, -1, 0);
5231 else
5233 /* TO_VPOS >= 0 means stop at TO_X in the line at
5234 TO_VPOS, or at TO_POS, whichever comes first. */
5235 if (it->vpos == to_vpos)
5237 reached = 2;
5238 break;
5241 skip = move_it_in_display_line_to (it, to_charpos, to_x, op);
5243 if (skip == MOVE_POS_MATCH_OR_ZV || it->vpos == to_vpos)
5245 reached = 3;
5246 break;
5248 else if (skip == MOVE_X_REACHED && it->vpos != to_vpos)
5250 /* We have reached TO_X but not in the line we want. */
5251 skip = move_it_in_display_line_to (it, to_charpos,
5252 -1, MOVE_TO_POS);
5253 if (skip == MOVE_POS_MATCH_OR_ZV)
5255 reached = 4;
5256 break;
5261 else if (op & MOVE_TO_Y)
5263 struct it it_backup;
5265 /* TO_Y specified means stop at TO_X in the line containing
5266 TO_Y---or at TO_CHARPOS if this is reached first. The
5267 problem is that we can't really tell whether the line
5268 contains TO_Y before we have completely scanned it, and
5269 this may skip past TO_X. What we do is to first scan to
5270 TO_X.
5272 If TO_X is not specified, use a TO_X of zero. The reason
5273 is to make the outcome of this function more predictable.
5274 If we didn't use TO_X == 0, we would stop at the end of
5275 the line which is probably not what a caller would expect
5276 to happen. */
5277 skip = move_it_in_display_line_to (it, to_charpos,
5278 ((op & MOVE_TO_X)
5279 ? to_x : 0),
5280 (MOVE_TO_X
5281 | (op & MOVE_TO_POS)));
5283 /* If TO_CHARPOS is reached or ZV, we don't have to do more. */
5284 if (skip == MOVE_POS_MATCH_OR_ZV)
5286 reached = 5;
5287 break;
5290 /* If TO_X was reached, we would like to know whether TO_Y
5291 is in the line. This can only be said if we know the
5292 total line height which requires us to scan the rest of
5293 the line. */
5294 if (skip == MOVE_X_REACHED)
5296 it_backup = *it;
5297 TRACE_MOVE ((stderr, "move_it: from %d\n", IT_CHARPOS (*it)));
5298 skip2 = move_it_in_display_line_to (it, to_charpos, -1,
5299 op & MOVE_TO_POS);
5300 TRACE_MOVE ((stderr, "move_it: to %d\n", IT_CHARPOS (*it)));
5303 /* Now, decide whether TO_Y is in this line. */
5304 line_height = it->max_ascent + it->max_descent;
5305 TRACE_MOVE ((stderr, "move_it: line_height = %d\n", line_height));
5307 if (to_y >= it->current_y
5308 && to_y < it->current_y + line_height)
5310 if (skip == MOVE_X_REACHED)
5311 /* If TO_Y is in this line and TO_X was reached above,
5312 we scanned too far. We have to restore IT's settings
5313 to the ones before skipping. */
5314 *it = it_backup;
5315 reached = 6;
5317 else if (skip == MOVE_X_REACHED)
5319 skip = skip2;
5320 if (skip == MOVE_POS_MATCH_OR_ZV)
5321 reached = 7;
5324 if (reached)
5325 break;
5327 else
5328 skip = move_it_in_display_line_to (it, to_charpos, -1, MOVE_TO_POS);
5330 switch (skip)
5332 case MOVE_POS_MATCH_OR_ZV:
5333 reached = 8;
5334 goto out;
5336 case MOVE_NEWLINE_OR_CR:
5337 set_iterator_to_next (it, 1);
5338 it->continuation_lines_width = 0;
5339 break;
5341 case MOVE_LINE_TRUNCATED:
5342 it->continuation_lines_width = 0;
5343 reseat_at_next_visible_line_start (it, 0);
5344 if ((op & MOVE_TO_POS) != 0
5345 && IT_CHARPOS (*it) > to_charpos)
5347 reached = 9;
5348 goto out;
5350 break;
5352 case MOVE_LINE_CONTINUED:
5353 it->continuation_lines_width += it->current_x;
5354 break;
5356 default:
5357 abort ();
5360 /* Reset/increment for the next run. */
5361 recenter_overlay_lists (current_buffer, IT_CHARPOS (*it));
5362 it->current_x = it->hpos = 0;
5363 it->current_y += it->max_ascent + it->max_descent;
5364 ++it->vpos;
5365 last_height = it->max_ascent + it->max_descent;
5366 last_max_ascent = it->max_ascent;
5367 it->max_ascent = it->max_descent = 0;
5370 out:
5372 TRACE_MOVE ((stderr, "move_it_to: reached %d\n", reached));
5376 /* Move iterator IT backward by a specified y-distance DY, DY >= 0.
5378 If DY > 0, move IT backward at least that many pixels. DY = 0
5379 means move IT backward to the preceding line start or BEGV. This
5380 function may move over more than DY pixels if IT->current_y - DY
5381 ends up in the middle of a line; in this case IT->current_y will be
5382 set to the top of the line moved to. */
5384 void
5385 move_it_vertically_backward (it, dy)
5386 struct it *it;
5387 int dy;
5389 int nlines, h;
5390 struct it it2, it3;
5391 int start_pos = IT_CHARPOS (*it);
5393 xassert (dy >= 0);
5395 /* Estimate how many newlines we must move back. */
5396 nlines = max (1, dy / CANON_Y_UNIT (it->f));
5398 /* Set the iterator's position that many lines back. */
5399 while (nlines-- && IT_CHARPOS (*it) > BEGV)
5400 back_to_previous_visible_line_start (it);
5402 /* Reseat the iterator here. When moving backward, we don't want
5403 reseat to skip forward over invisible text, set up the iterator
5404 to deliver from overlay strings at the new position etc. So,
5405 use reseat_1 here. */
5406 reseat_1 (it, it->current.pos, 1);
5408 /* We are now surely at a line start. */
5409 it->current_x = it->hpos = 0;
5411 /* Move forward and see what y-distance we moved. First move to the
5412 start of the next line so that we get its height. We need this
5413 height to be able to tell whether we reached the specified
5414 y-distance. */
5415 it2 = *it;
5416 it2.max_ascent = it2.max_descent = 0;
5417 move_it_to (&it2, start_pos, -1, -1, it2.vpos + 1,
5418 MOVE_TO_POS | MOVE_TO_VPOS);
5419 xassert (IT_CHARPOS (*it) >= BEGV);
5420 it3 = it2;
5422 move_it_to (&it2, start_pos, -1, -1, -1, MOVE_TO_POS);
5423 xassert (IT_CHARPOS (*it) >= BEGV);
5424 h = it2.current_y - it->current_y;
5425 nlines = it2.vpos - it->vpos;
5427 /* Correct IT's y and vpos position. */
5428 it->vpos -= nlines;
5429 it->current_y -= h;
5431 if (dy == 0)
5433 /* DY == 0 means move to the start of the screen line. The
5434 value of nlines is > 0 if continuation lines were involved. */
5435 if (nlines > 0)
5436 move_it_by_lines (it, nlines, 1);
5437 xassert (IT_CHARPOS (*it) <= start_pos);
5439 else if (nlines)
5441 /* The y-position we try to reach. Note that h has been
5442 subtracted in front of the if-statement. */
5443 int target_y = it->current_y + h - dy;
5444 int y0 = it3.current_y;
5445 int y1 = line_bottom_y (&it3);
5446 int line_height = y1 - y0;
5448 /* If we did not reach target_y, try to move further backward if
5449 we can. If we moved too far backward, try to move forward. */
5450 if (target_y < it->current_y
5451 /* This is heuristic. In a window that's 3 lines high, with
5452 a line height of 13 pixels each, recentering with point
5453 on the bottom line will try to move -39/2 = 19 pixels
5454 backward. Try to avoid moving into the first line. */
5455 && it->current_y - target_y > line_height / 3 * 2
5456 && IT_CHARPOS (*it) > BEGV)
5458 TRACE_MOVE ((stderr, " not far enough -> move_vert %d\n",
5459 target_y - it->current_y));
5460 move_it_vertically (it, target_y - it->current_y);
5461 xassert (IT_CHARPOS (*it) >= BEGV);
5463 else if (target_y >= it->current_y + line_height
5464 && IT_CHARPOS (*it) < ZV)
5466 /* Should move forward by at least one line, maybe more.
5468 Note: Calling move_it_by_lines can be expensive on
5469 terminal frames, where compute_motion is used (via
5470 vmotion) to do the job, when there are very long lines
5471 and truncate-lines is nil. That's the reason for
5472 treating terminal frames specially here. */
5474 if (!FRAME_WINDOW_P (it->f))
5475 move_it_vertically (it, target_y - (it->current_y + line_height));
5476 else
5480 move_it_by_lines (it, 1, 1);
5482 while (target_y >= line_bottom_y (it) && IT_CHARPOS (*it) < ZV);
5485 xassert (IT_CHARPOS (*it) >= BEGV);
5491 /* Move IT by a specified amount of pixel lines DY. DY negative means
5492 move backwards. DY = 0 means move to start of screen line. At the
5493 end, IT will be on the start of a screen line. */
5495 void
5496 move_it_vertically (it, dy)
5497 struct it *it;
5498 int dy;
5500 if (dy <= 0)
5501 move_it_vertically_backward (it, -dy);
5502 else if (dy > 0)
5504 TRACE_MOVE ((stderr, "move_it_v: from %d, %d\n", IT_CHARPOS (*it), dy));
5505 move_it_to (it, ZV, -1, it->current_y + dy, -1,
5506 MOVE_TO_POS | MOVE_TO_Y);
5507 TRACE_MOVE ((stderr, "move_it_v: to %d\n", IT_CHARPOS (*it)));
5509 /* If buffer ends in ZV without a newline, move to the start of
5510 the line to satisfy the post-condition. */
5511 if (IT_CHARPOS (*it) == ZV
5512 && FETCH_BYTE (IT_BYTEPOS (*it) - 1) != '\n')
5513 move_it_by_lines (it, 0, 0);
5518 /* Move iterator IT past the end of the text line it is in. */
5520 void
5521 move_it_past_eol (it)
5522 struct it *it;
5524 enum move_it_result rc;
5526 rc = move_it_in_display_line_to (it, Z, 0, MOVE_TO_POS);
5527 if (rc == MOVE_NEWLINE_OR_CR)
5528 set_iterator_to_next (it, 0);
5532 #if 0 /* Currently not used. */
5534 /* Return non-zero if some text between buffer positions START_CHARPOS
5535 and END_CHARPOS is invisible. IT->window is the window for text
5536 property lookup. */
5538 static int
5539 invisible_text_between_p (it, start_charpos, end_charpos)
5540 struct it *it;
5541 int start_charpos, end_charpos;
5543 Lisp_Object prop, limit;
5544 int invisible_found_p;
5546 xassert (it != NULL && start_charpos <= end_charpos);
5548 /* Is text at START invisible? */
5549 prop = Fget_char_property (make_number (start_charpos), Qinvisible,
5550 it->window);
5551 if (TEXT_PROP_MEANS_INVISIBLE (prop))
5552 invisible_found_p = 1;
5553 else
5555 limit = Fnext_single_char_property_change (make_number (start_charpos),
5556 Qinvisible, Qnil,
5557 make_number (end_charpos));
5558 invisible_found_p = XFASTINT (limit) < end_charpos;
5561 return invisible_found_p;
5564 #endif /* 0 */
5567 /* Move IT by a specified number DVPOS of screen lines down. DVPOS
5568 negative means move up. DVPOS == 0 means move to the start of the
5569 screen line. NEED_Y_P non-zero means calculate IT->current_y. If
5570 NEED_Y_P is zero, IT->current_y will be left unchanged.
5572 Further optimization ideas: If we would know that IT->f doesn't use
5573 a face with proportional font, we could be faster for
5574 truncate-lines nil. */
5576 void
5577 move_it_by_lines (it, dvpos, need_y_p)
5578 struct it *it;
5579 int dvpos, need_y_p;
5581 struct position pos;
5583 if (!FRAME_WINDOW_P (it->f))
5585 struct text_pos textpos;
5587 /* We can use vmotion on frames without proportional fonts. */
5588 pos = *vmotion (IT_CHARPOS (*it), dvpos, it->w);
5589 SET_TEXT_POS (textpos, pos.bufpos, pos.bytepos);
5590 reseat (it, textpos, 1);
5591 it->vpos += pos.vpos;
5592 it->current_y += pos.vpos;
5594 else if (dvpos == 0)
5596 /* DVPOS == 0 means move to the start of the screen line. */
5597 move_it_vertically_backward (it, 0);
5598 xassert (it->current_x == 0 && it->hpos == 0);
5600 else if (dvpos > 0)
5601 move_it_to (it, -1, -1, -1, it->vpos + dvpos, MOVE_TO_VPOS);
5602 else
5604 struct it it2;
5605 int start_charpos, i;
5607 /* Start at the beginning of the screen line containing IT's
5608 position. */
5609 move_it_vertically_backward (it, 0);
5611 /* Go back -DVPOS visible lines and reseat the iterator there. */
5612 start_charpos = IT_CHARPOS (*it);
5613 for (i = -dvpos; i && IT_CHARPOS (*it) > BEGV; --i)
5614 back_to_previous_visible_line_start (it);
5615 reseat (it, it->current.pos, 1);
5616 it->current_x = it->hpos = 0;
5618 /* Above call may have moved too far if continuation lines
5619 are involved. Scan forward and see if it did. */
5620 it2 = *it;
5621 it2.vpos = it2.current_y = 0;
5622 move_it_to (&it2, start_charpos, -1, -1, -1, MOVE_TO_POS);
5623 it->vpos -= it2.vpos;
5624 it->current_y -= it2.current_y;
5625 it->current_x = it->hpos = 0;
5627 /* If we moved too far, move IT some lines forward. */
5628 if (it2.vpos > -dvpos)
5630 int delta = it2.vpos + dvpos;
5631 move_it_to (it, -1, -1, -1, it->vpos + delta, MOVE_TO_VPOS);
5638 /***********************************************************************
5639 Messages
5640 ***********************************************************************/
5643 /* Add a message with format string FORMAT and arguments ARG1 and ARG2
5644 to *Messages*. */
5646 void
5647 add_to_log (format, arg1, arg2)
5648 char *format;
5649 Lisp_Object arg1, arg2;
5651 Lisp_Object args[3];
5652 Lisp_Object msg, fmt;
5653 char *buffer;
5654 int len;
5655 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
5657 /* Do nothing if called asynchronously. Inserting text into
5658 a buffer may call after-change-functions and alike and
5659 that would means running Lisp asynchronously. */
5660 if (handling_signal)
5661 return;
5663 fmt = msg = Qnil;
5664 GCPRO4 (fmt, msg, arg1, arg2);
5666 args[0] = fmt = build_string (format);
5667 args[1] = arg1;
5668 args[2] = arg2;
5669 msg = Fformat (3, args);
5671 len = SBYTES (msg) + 1;
5672 buffer = (char *) alloca (len);
5673 bcopy (SDATA (msg), buffer, len);
5675 message_dolog (buffer, len - 1, 1, 0);
5676 UNGCPRO;
5680 /* Output a newline in the *Messages* buffer if "needs" one. */
5682 void
5683 message_log_maybe_newline ()
5685 if (message_log_need_newline)
5686 message_dolog ("", 0, 1, 0);
5690 /* Add a string M of length NBYTES to the message log, optionally
5691 terminated with a newline when NLFLAG is non-zero. MULTIBYTE, if
5692 nonzero, means interpret the contents of M as multibyte. This
5693 function calls low-level routines in order to bypass text property
5694 hooks, etc. which might not be safe to run. */
5696 void
5697 message_dolog (m, nbytes, nlflag, multibyte)
5698 const char *m;
5699 int nbytes, nlflag, multibyte;
5701 if (!NILP (Vmemory_full))
5702 return;
5704 if (!NILP (Vmessage_log_max))
5706 struct buffer *oldbuf;
5707 Lisp_Object oldpoint, oldbegv, oldzv;
5708 int old_windows_or_buffers_changed = windows_or_buffers_changed;
5709 int point_at_end = 0;
5710 int zv_at_end = 0;
5711 Lisp_Object old_deactivate_mark, tem;
5712 struct gcpro gcpro1;
5714 old_deactivate_mark = Vdeactivate_mark;
5715 oldbuf = current_buffer;
5716 Fset_buffer (Fget_buffer_create (Vmessages_buffer_name));
5717 current_buffer->undo_list = Qt;
5719 oldpoint = message_dolog_marker1;
5720 set_marker_restricted (oldpoint, make_number (PT), Qnil);
5721 oldbegv = message_dolog_marker2;
5722 set_marker_restricted (oldbegv, make_number (BEGV), Qnil);
5723 oldzv = message_dolog_marker3;
5724 set_marker_restricted (oldzv, make_number (ZV), Qnil);
5725 GCPRO1 (old_deactivate_mark);
5727 if (PT == Z)
5728 point_at_end = 1;
5729 if (ZV == Z)
5730 zv_at_end = 1;
5732 BEGV = BEG;
5733 BEGV_BYTE = BEG_BYTE;
5734 ZV = Z;
5735 ZV_BYTE = Z_BYTE;
5736 TEMP_SET_PT_BOTH (Z, Z_BYTE);
5738 /* Insert the string--maybe converting multibyte to single byte
5739 or vice versa, so that all the text fits the buffer. */
5740 if (multibyte
5741 && NILP (current_buffer->enable_multibyte_characters))
5743 int i, c, char_bytes;
5744 unsigned char work[1];
5746 /* Convert a multibyte string to single-byte
5747 for the *Message* buffer. */
5748 for (i = 0; i < nbytes; i += nbytes)
5750 c = string_char_and_length (m + i, nbytes - i, &char_bytes);
5751 work[0] = (SINGLE_BYTE_CHAR_P (c)
5753 : multibyte_char_to_unibyte (c, Qnil));
5754 insert_1_both (work, 1, 1, 1, 0, 0);
5757 else if (! multibyte
5758 && ! NILP (current_buffer->enable_multibyte_characters))
5760 int i, c, char_bytes;
5761 unsigned char *msg = (unsigned char *) m;
5762 unsigned char str[MAX_MULTIBYTE_LENGTH];
5763 /* Convert a single-byte string to multibyte
5764 for the *Message* buffer. */
5765 for (i = 0; i < nbytes; i++)
5767 c = unibyte_char_to_multibyte (msg[i]);
5768 char_bytes = CHAR_STRING (c, str);
5769 insert_1_both (str, 1, char_bytes, 1, 0, 0);
5772 else if (nbytes)
5773 insert_1 (m, nbytes, 1, 0, 0);
5775 if (nlflag)
5777 int this_bol, this_bol_byte, prev_bol, prev_bol_byte, dup;
5778 insert_1 ("\n", 1, 1, 0, 0);
5780 scan_newline (Z, Z_BYTE, BEG, BEG_BYTE, -2, 0);
5781 this_bol = PT;
5782 this_bol_byte = PT_BYTE;
5784 /* See if this line duplicates the previous one.
5785 If so, combine duplicates. */
5786 if (this_bol > BEG)
5788 scan_newline (PT, PT_BYTE, BEG, BEG_BYTE, -2, 0);
5789 prev_bol = PT;
5790 prev_bol_byte = PT_BYTE;
5792 dup = message_log_check_duplicate (prev_bol, prev_bol_byte,
5793 this_bol, this_bol_byte);
5794 if (dup)
5796 del_range_both (prev_bol, prev_bol_byte,
5797 this_bol, this_bol_byte, 0);
5798 if (dup > 1)
5800 char dupstr[40];
5801 int duplen;
5803 /* If you change this format, don't forget to also
5804 change message_log_check_duplicate. */
5805 sprintf (dupstr, " [%d times]", dup);
5806 duplen = strlen (dupstr);
5807 TEMP_SET_PT_BOTH (Z - 1, Z_BYTE - 1);
5808 insert_1 (dupstr, duplen, 1, 0, 1);
5813 /* If we have more than the desired maximum number of lines
5814 in the *Messages* buffer now, delete the oldest ones.
5815 This is safe because we don't have undo in this buffer. */
5817 if (NATNUMP (Vmessage_log_max))
5819 scan_newline (Z, Z_BYTE, BEG, BEG_BYTE,
5820 -XFASTINT (Vmessage_log_max) - 1, 0);
5821 del_range_both (BEG, BEG_BYTE, PT, PT_BYTE, 0);
5824 BEGV = XMARKER (oldbegv)->charpos;
5825 BEGV_BYTE = marker_byte_position (oldbegv);
5827 if (zv_at_end)
5829 ZV = Z;
5830 ZV_BYTE = Z_BYTE;
5832 else
5834 ZV = XMARKER (oldzv)->charpos;
5835 ZV_BYTE = marker_byte_position (oldzv);
5838 if (point_at_end)
5839 TEMP_SET_PT_BOTH (Z, Z_BYTE);
5840 else
5841 /* We can't do Fgoto_char (oldpoint) because it will run some
5842 Lisp code. */
5843 TEMP_SET_PT_BOTH (XMARKER (oldpoint)->charpos,
5844 XMARKER (oldpoint)->bytepos);
5846 UNGCPRO;
5847 unchain_marker (oldpoint);
5848 unchain_marker (oldbegv);
5849 unchain_marker (oldzv);
5851 tem = Fget_buffer_window (Fcurrent_buffer (), Qt);
5852 set_buffer_internal (oldbuf);
5853 if (NILP (tem))
5854 windows_or_buffers_changed = old_windows_or_buffers_changed;
5855 message_log_need_newline = !nlflag;
5856 Vdeactivate_mark = old_deactivate_mark;
5861 /* We are at the end of the buffer after just having inserted a newline.
5862 (Note: We depend on the fact we won't be crossing the gap.)
5863 Check to see if the most recent message looks a lot like the previous one.
5864 Return 0 if different, 1 if the new one should just replace it, or a
5865 value N > 1 if we should also append " [N times]". */
5867 static int
5868 message_log_check_duplicate (prev_bol, prev_bol_byte, this_bol, this_bol_byte)
5869 int prev_bol, this_bol;
5870 int prev_bol_byte, this_bol_byte;
5872 int i;
5873 int len = Z_BYTE - 1 - this_bol_byte;
5874 int seen_dots = 0;
5875 unsigned char *p1 = BUF_BYTE_ADDRESS (current_buffer, prev_bol_byte);
5876 unsigned char *p2 = BUF_BYTE_ADDRESS (current_buffer, this_bol_byte);
5878 for (i = 0; i < len; i++)
5880 if (i >= 3 && p1[i-3] == '.' && p1[i-2] == '.' && p1[i-1] == '.')
5881 seen_dots = 1;
5882 if (p1[i] != p2[i])
5883 return seen_dots;
5885 p1 += len;
5886 if (*p1 == '\n')
5887 return 2;
5888 if (*p1++ == ' ' && *p1++ == '[')
5890 int n = 0;
5891 while (*p1 >= '0' && *p1 <= '9')
5892 n = n * 10 + *p1++ - '0';
5893 if (strncmp (p1, " times]\n", 8) == 0)
5894 return n+1;
5896 return 0;
5900 /* Display an echo area message M with a specified length of NBYTES
5901 bytes. The string may include null characters. If M is 0, clear
5902 out any existing message, and let the mini-buffer text show
5903 through.
5905 The buffer M must continue to exist until after the echo area gets
5906 cleared or some other message gets displayed there. This means do
5907 not pass text that is stored in a Lisp string; do not pass text in
5908 a buffer that was alloca'd. */
5910 void
5911 message2 (m, nbytes, multibyte)
5912 const char *m;
5913 int nbytes;
5914 int multibyte;
5916 /* First flush out any partial line written with print. */
5917 message_log_maybe_newline ();
5918 if (m)
5919 message_dolog (m, nbytes, 1, multibyte);
5920 message2_nolog (m, nbytes, multibyte);
5924 /* The non-logging counterpart of message2. */
5926 void
5927 message2_nolog (m, nbytes, multibyte)
5928 const char *m;
5929 int nbytes;
5931 struct frame *sf = SELECTED_FRAME ();
5932 message_enable_multibyte = multibyte;
5934 if (noninteractive)
5936 if (noninteractive_need_newline)
5937 putc ('\n', stderr);
5938 noninteractive_need_newline = 0;
5939 if (m)
5940 fwrite (m, nbytes, 1, stderr);
5941 if (cursor_in_echo_area == 0)
5942 fprintf (stderr, "\n");
5943 fflush (stderr);
5945 /* A null message buffer means that the frame hasn't really been
5946 initialized yet. Error messages get reported properly by
5947 cmd_error, so this must be just an informative message; toss it. */
5948 else if (INTERACTIVE
5949 && sf->glyphs_initialized_p
5950 && FRAME_MESSAGE_BUF (sf))
5952 Lisp_Object mini_window;
5953 struct frame *f;
5955 /* Get the frame containing the mini-buffer
5956 that the selected frame is using. */
5957 mini_window = FRAME_MINIBUF_WINDOW (sf);
5958 f = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
5960 FRAME_SAMPLE_VISIBILITY (f);
5961 if (FRAME_VISIBLE_P (sf)
5962 && ! FRAME_VISIBLE_P (f))
5963 Fmake_frame_visible (WINDOW_FRAME (XWINDOW (mini_window)));
5965 if (m)
5967 set_message (m, Qnil, nbytes, multibyte);
5968 if (minibuffer_auto_raise)
5969 Fraise_frame (WINDOW_FRAME (XWINDOW (mini_window)));
5971 else
5972 clear_message (1, 1);
5974 do_pending_window_change (0);
5975 echo_area_display (1);
5976 do_pending_window_change (0);
5977 if (frame_up_to_date_hook != 0 && ! gc_in_progress)
5978 (*frame_up_to_date_hook) (f);
5983 /* Display an echo area message M with a specified length of NBYTES
5984 bytes. The string may include null characters. If M is not a
5985 string, clear out any existing message, and let the mini-buffer
5986 text show through. */
5988 void
5989 message3 (m, nbytes, multibyte)
5990 Lisp_Object m;
5991 int nbytes;
5992 int multibyte;
5994 struct gcpro gcpro1;
5996 GCPRO1 (m);
5998 /* First flush out any partial line written with print. */
5999 message_log_maybe_newline ();
6000 if (STRINGP (m))
6001 message_dolog (SDATA (m), nbytes, 1, multibyte);
6002 message3_nolog (m, nbytes, multibyte);
6004 UNGCPRO;
6008 /* The non-logging version of message3. */
6010 void
6011 message3_nolog (m, nbytes, multibyte)
6012 Lisp_Object m;
6013 int nbytes, multibyte;
6015 struct frame *sf = SELECTED_FRAME ();
6016 message_enable_multibyte = multibyte;
6018 if (noninteractive)
6020 if (noninteractive_need_newline)
6021 putc ('\n', stderr);
6022 noninteractive_need_newline = 0;
6023 if (STRINGP (m))
6024 fwrite (SDATA (m), nbytes, 1, stderr);
6025 if (cursor_in_echo_area == 0)
6026 fprintf (stderr, "\n");
6027 fflush (stderr);
6029 /* A null message buffer means that the frame hasn't really been
6030 initialized yet. Error messages get reported properly by
6031 cmd_error, so this must be just an informative message; toss it. */
6032 else if (INTERACTIVE
6033 && sf->glyphs_initialized_p
6034 && FRAME_MESSAGE_BUF (sf))
6036 Lisp_Object mini_window;
6037 Lisp_Object frame;
6038 struct frame *f;
6040 /* Get the frame containing the mini-buffer
6041 that the selected frame is using. */
6042 mini_window = FRAME_MINIBUF_WINDOW (sf);
6043 frame = XWINDOW (mini_window)->frame;
6044 f = XFRAME (frame);
6046 FRAME_SAMPLE_VISIBILITY (f);
6047 if (FRAME_VISIBLE_P (sf)
6048 && !FRAME_VISIBLE_P (f))
6049 Fmake_frame_visible (frame);
6051 if (STRINGP (m) && SCHARS (m) > 0)
6053 set_message (NULL, m, nbytes, multibyte);
6054 if (minibuffer_auto_raise)
6055 Fraise_frame (frame);
6057 else
6058 clear_message (1, 1);
6060 do_pending_window_change (0);
6061 echo_area_display (1);
6062 do_pending_window_change (0);
6063 if (frame_up_to_date_hook != 0 && ! gc_in_progress)
6064 (*frame_up_to_date_hook) (f);
6069 /* Display a null-terminated echo area message M. If M is 0, clear
6070 out any existing message, and let the mini-buffer text show through.
6072 The buffer M must continue to exist until after the echo area gets
6073 cleared or some other message gets displayed there. Do not pass
6074 text that is stored in a Lisp string. Do not pass text in a buffer
6075 that was alloca'd. */
6077 void
6078 message1 (m)
6079 char *m;
6081 message2 (m, (m ? strlen (m) : 0), 0);
6085 /* The non-logging counterpart of message1. */
6087 void
6088 message1_nolog (m)
6089 char *m;
6091 message2_nolog (m, (m ? strlen (m) : 0), 0);
6094 /* Display a message M which contains a single %s
6095 which gets replaced with STRING. */
6097 void
6098 message_with_string (m, string, log)
6099 char *m;
6100 Lisp_Object string;
6101 int log;
6103 CHECK_STRING (string);
6105 if (noninteractive)
6107 if (m)
6109 if (noninteractive_need_newline)
6110 putc ('\n', stderr);
6111 noninteractive_need_newline = 0;
6112 fprintf (stderr, m, SDATA (string));
6113 if (cursor_in_echo_area == 0)
6114 fprintf (stderr, "\n");
6115 fflush (stderr);
6118 else if (INTERACTIVE)
6120 /* The frame whose minibuffer we're going to display the message on.
6121 It may be larger than the selected frame, so we need
6122 to use its buffer, not the selected frame's buffer. */
6123 Lisp_Object mini_window;
6124 struct frame *f, *sf = SELECTED_FRAME ();
6126 /* Get the frame containing the minibuffer
6127 that the selected frame is using. */
6128 mini_window = FRAME_MINIBUF_WINDOW (sf);
6129 f = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
6131 /* A null message buffer means that the frame hasn't really been
6132 initialized yet. Error messages get reported properly by
6133 cmd_error, so this must be just an informative message; toss it. */
6134 if (FRAME_MESSAGE_BUF (f))
6136 Lisp_Object args[2], message;
6137 struct gcpro gcpro1, gcpro2;
6139 args[0] = build_string (m);
6140 args[1] = message = string;
6141 GCPRO2 (args[0], message);
6142 gcpro1.nvars = 2;
6144 message = Fformat (2, args);
6146 if (log)
6147 message3 (message, SBYTES (message), STRING_MULTIBYTE (message));
6148 else
6149 message3_nolog (message, SBYTES (message), STRING_MULTIBYTE (message));
6151 UNGCPRO;
6153 /* Print should start at the beginning of the message
6154 buffer next time. */
6155 message_buf_print = 0;
6161 /* Dump an informative message to the minibuf. If M is 0, clear out
6162 any existing message, and let the mini-buffer text show through. */
6164 /* VARARGS 1 */
6165 void
6166 message (m, a1, a2, a3)
6167 char *m;
6168 EMACS_INT a1, a2, a3;
6170 if (noninteractive)
6172 if (m)
6174 if (noninteractive_need_newline)
6175 putc ('\n', stderr);
6176 noninteractive_need_newline = 0;
6177 fprintf (stderr, m, a1, a2, a3);
6178 if (cursor_in_echo_area == 0)
6179 fprintf (stderr, "\n");
6180 fflush (stderr);
6183 else if (INTERACTIVE)
6185 /* The frame whose mini-buffer we're going to display the message
6186 on. It may be larger than the selected frame, so we need to
6187 use its buffer, not the selected frame's buffer. */
6188 Lisp_Object mini_window;
6189 struct frame *f, *sf = SELECTED_FRAME ();
6191 /* Get the frame containing the mini-buffer
6192 that the selected frame is using. */
6193 mini_window = FRAME_MINIBUF_WINDOW (sf);
6194 f = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
6196 /* A null message buffer means that the frame hasn't really been
6197 initialized yet. Error messages get reported properly by
6198 cmd_error, so this must be just an informative message; toss
6199 it. */
6200 if (FRAME_MESSAGE_BUF (f))
6202 if (m)
6204 int len;
6205 #ifdef NO_ARG_ARRAY
6206 char *a[3];
6207 a[0] = (char *) a1;
6208 a[1] = (char *) a2;
6209 a[2] = (char *) a3;
6211 len = doprnt (FRAME_MESSAGE_BUF (f),
6212 FRAME_MESSAGE_BUF_SIZE (f), m, (char *)0, 3, a);
6213 #else
6214 len = doprnt (FRAME_MESSAGE_BUF (f),
6215 FRAME_MESSAGE_BUF_SIZE (f), m, (char *)0, 3,
6216 (char **) &a1);
6217 #endif /* NO_ARG_ARRAY */
6219 message2 (FRAME_MESSAGE_BUF (f), len, 0);
6221 else
6222 message1 (0);
6224 /* Print should start at the beginning of the message
6225 buffer next time. */
6226 message_buf_print = 0;
6232 /* The non-logging version of message. */
6234 void
6235 message_nolog (m, a1, a2, a3)
6236 char *m;
6237 EMACS_INT a1, a2, a3;
6239 Lisp_Object old_log_max;
6240 old_log_max = Vmessage_log_max;
6241 Vmessage_log_max = Qnil;
6242 message (m, a1, a2, a3);
6243 Vmessage_log_max = old_log_max;
6247 /* Display the current message in the current mini-buffer. This is
6248 only called from error handlers in process.c, and is not time
6249 critical. */
6251 void
6252 update_echo_area ()
6254 if (!NILP (echo_area_buffer[0]))
6256 Lisp_Object string;
6257 string = Fcurrent_message ();
6258 message3 (string, SBYTES (string),
6259 !NILP (current_buffer->enable_multibyte_characters));
6264 /* Make sure echo area buffers in `echo_buffers' are live.
6265 If they aren't, make new ones. */
6267 static void
6268 ensure_echo_area_buffers ()
6270 int i;
6272 for (i = 0; i < 2; ++i)
6273 if (!BUFFERP (echo_buffer[i])
6274 || NILP (XBUFFER (echo_buffer[i])->name))
6276 char name[30];
6277 Lisp_Object old_buffer;
6278 int j;
6280 old_buffer = echo_buffer[i];
6281 sprintf (name, " *Echo Area %d*", i);
6282 echo_buffer[i] = Fget_buffer_create (build_string (name));
6283 XBUFFER (echo_buffer[i])->truncate_lines = Qnil;
6285 for (j = 0; j < 2; ++j)
6286 if (EQ (old_buffer, echo_area_buffer[j]))
6287 echo_area_buffer[j] = echo_buffer[i];
6292 /* Call FN with args A1..A4 with either the current or last displayed
6293 echo_area_buffer as current buffer.
6295 WHICH zero means use the current message buffer
6296 echo_area_buffer[0]. If that is nil, choose a suitable buffer
6297 from echo_buffer[] and clear it.
6299 WHICH > 0 means use echo_area_buffer[1]. If that is nil, choose a
6300 suitable buffer from echo_buffer[] and clear it.
6302 If WHICH < 0, set echo_area_buffer[1] to echo_area_buffer[0], so
6303 that the current message becomes the last displayed one, make
6304 choose a suitable buffer for echo_area_buffer[0], and clear it.
6306 Value is what FN returns. */
6308 static int
6309 with_echo_area_buffer (w, which, fn, a1, a2, a3, a4)
6310 struct window *w;
6311 int which;
6312 int (*fn) P_ ((EMACS_INT, Lisp_Object, EMACS_INT, EMACS_INT));
6313 EMACS_INT a1;
6314 Lisp_Object a2;
6315 EMACS_INT a3, a4;
6317 Lisp_Object buffer;
6318 int this_one, the_other, clear_buffer_p, rc;
6319 int count = SPECPDL_INDEX ();
6321 /* If buffers aren't live, make new ones. */
6322 ensure_echo_area_buffers ();
6324 clear_buffer_p = 0;
6326 if (which == 0)
6327 this_one = 0, the_other = 1;
6328 else if (which > 0)
6329 this_one = 1, the_other = 0;
6330 else
6332 this_one = 0, the_other = 1;
6333 clear_buffer_p = 1;
6335 /* We need a fresh one in case the current echo buffer equals
6336 the one containing the last displayed echo area message. */
6337 if (!NILP (echo_area_buffer[this_one])
6338 && EQ (echo_area_buffer[this_one], echo_area_buffer[the_other]))
6339 echo_area_buffer[this_one] = Qnil;
6342 /* Choose a suitable buffer from echo_buffer[] is we don't
6343 have one. */
6344 if (NILP (echo_area_buffer[this_one]))
6346 echo_area_buffer[this_one]
6347 = (EQ (echo_area_buffer[the_other], echo_buffer[this_one])
6348 ? echo_buffer[the_other]
6349 : echo_buffer[this_one]);
6350 clear_buffer_p = 1;
6353 buffer = echo_area_buffer[this_one];
6355 /* Don't get confused by reusing the buffer used for echoing
6356 for a different purpose. */
6357 if (echo_kboard == NULL && EQ (buffer, echo_message_buffer))
6358 cancel_echoing ();
6360 record_unwind_protect (unwind_with_echo_area_buffer,
6361 with_echo_area_buffer_unwind_data (w));
6363 /* Make the echo area buffer current. Note that for display
6364 purposes, it is not necessary that the displayed window's buffer
6365 == current_buffer, except for text property lookup. So, let's
6366 only set that buffer temporarily here without doing a full
6367 Fset_window_buffer. We must also change w->pointm, though,
6368 because otherwise an assertions in unshow_buffer fails, and Emacs
6369 aborts. */
6370 set_buffer_internal_1 (XBUFFER (buffer));
6371 if (w)
6373 w->buffer = buffer;
6374 set_marker_both (w->pointm, buffer, BEG, BEG_BYTE);
6377 current_buffer->undo_list = Qt;
6378 current_buffer->read_only = Qnil;
6379 specbind (Qinhibit_read_only, Qt);
6380 specbind (Qinhibit_modification_hooks, Qt);
6382 if (clear_buffer_p && Z > BEG)
6383 del_range (BEG, Z);
6385 xassert (BEGV >= BEG);
6386 xassert (ZV <= Z && ZV >= BEGV);
6388 rc = fn (a1, a2, a3, a4);
6390 xassert (BEGV >= BEG);
6391 xassert (ZV <= Z && ZV >= BEGV);
6393 unbind_to (count, Qnil);
6394 return rc;
6398 /* Save state that should be preserved around the call to the function
6399 FN called in with_echo_area_buffer. */
6401 static Lisp_Object
6402 with_echo_area_buffer_unwind_data (w)
6403 struct window *w;
6405 int i = 0;
6406 Lisp_Object vector;
6408 /* Reduce consing by keeping one vector in
6409 Vwith_echo_area_save_vector. */
6410 vector = Vwith_echo_area_save_vector;
6411 Vwith_echo_area_save_vector = Qnil;
6413 if (NILP (vector))
6414 vector = Fmake_vector (make_number (7), Qnil);
6416 XSETBUFFER (AREF (vector, i), current_buffer); ++i;
6417 AREF (vector, i) = Vdeactivate_mark, ++i;
6418 AREF (vector, i) = make_number (windows_or_buffers_changed), ++i;
6420 if (w)
6422 XSETWINDOW (AREF (vector, i), w); ++i;
6423 AREF (vector, i) = w->buffer; ++i;
6424 AREF (vector, i) = make_number (XMARKER (w->pointm)->charpos); ++i;
6425 AREF (vector, i) = make_number (XMARKER (w->pointm)->bytepos); ++i;
6427 else
6429 int end = i + 4;
6430 for (; i < end; ++i)
6431 AREF (vector, i) = Qnil;
6434 xassert (i == ASIZE (vector));
6435 return vector;
6439 /* Restore global state from VECTOR which was created by
6440 with_echo_area_buffer_unwind_data. */
6442 static Lisp_Object
6443 unwind_with_echo_area_buffer (vector)
6444 Lisp_Object vector;
6446 set_buffer_internal_1 (XBUFFER (AREF (vector, 0)));
6447 Vdeactivate_mark = AREF (vector, 1);
6448 windows_or_buffers_changed = XFASTINT (AREF (vector, 2));
6450 if (WINDOWP (AREF (vector, 3)))
6452 struct window *w;
6453 Lisp_Object buffer, charpos, bytepos;
6455 w = XWINDOW (AREF (vector, 3));
6456 buffer = AREF (vector, 4);
6457 charpos = AREF (vector, 5);
6458 bytepos = AREF (vector, 6);
6460 w->buffer = buffer;
6461 set_marker_both (w->pointm, buffer,
6462 XFASTINT (charpos), XFASTINT (bytepos));
6465 Vwith_echo_area_save_vector = vector;
6466 return Qnil;
6470 /* Set up the echo area for use by print functions. MULTIBYTE_P
6471 non-zero means we will print multibyte. */
6473 void
6474 setup_echo_area_for_printing (multibyte_p)
6475 int multibyte_p;
6477 ensure_echo_area_buffers ();
6479 if (!message_buf_print)
6481 /* A message has been output since the last time we printed.
6482 Choose a fresh echo area buffer. */
6483 if (EQ (echo_area_buffer[1], echo_buffer[0]))
6484 echo_area_buffer[0] = echo_buffer[1];
6485 else
6486 echo_area_buffer[0] = echo_buffer[0];
6488 /* Switch to that buffer and clear it. */
6489 set_buffer_internal (XBUFFER (echo_area_buffer[0]));
6490 current_buffer->truncate_lines = Qnil;
6492 if (Z > BEG)
6494 int count = SPECPDL_INDEX ();
6495 specbind (Qinhibit_read_only, Qt);
6496 /* Note that undo recording is always disabled. */
6497 del_range (BEG, Z);
6498 unbind_to (count, Qnil);
6500 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
6502 /* Set up the buffer for the multibyteness we need. */
6503 if (multibyte_p
6504 != !NILP (current_buffer->enable_multibyte_characters))
6505 Fset_buffer_multibyte (multibyte_p ? Qt : Qnil);
6507 /* Raise the frame containing the echo area. */
6508 if (minibuffer_auto_raise)
6510 struct frame *sf = SELECTED_FRAME ();
6511 Lisp_Object mini_window;
6512 mini_window = FRAME_MINIBUF_WINDOW (sf);
6513 Fraise_frame (WINDOW_FRAME (XWINDOW (mini_window)));
6516 message_log_maybe_newline ();
6517 message_buf_print = 1;
6519 else
6521 if (NILP (echo_area_buffer[0]))
6523 if (EQ (echo_area_buffer[1], echo_buffer[0]))
6524 echo_area_buffer[0] = echo_buffer[1];
6525 else
6526 echo_area_buffer[0] = echo_buffer[0];
6529 if (current_buffer != XBUFFER (echo_area_buffer[0]))
6531 /* Someone switched buffers between print requests. */
6532 set_buffer_internal (XBUFFER (echo_area_buffer[0]));
6533 current_buffer->truncate_lines = Qnil;
6539 /* Display an echo area message in window W. Value is non-zero if W's
6540 height is changed. If display_last_displayed_message_p is
6541 non-zero, display the message that was last displayed, otherwise
6542 display the current message. */
6544 static int
6545 display_echo_area (w)
6546 struct window *w;
6548 int i, no_message_p, window_height_changed_p, count;
6550 /* Temporarily disable garbage collections while displaying the echo
6551 area. This is done because a GC can print a message itself.
6552 That message would modify the echo area buffer's contents while a
6553 redisplay of the buffer is going on, and seriously confuse
6554 redisplay. */
6555 count = inhibit_garbage_collection ();
6557 /* If there is no message, we must call display_echo_area_1
6558 nevertheless because it resizes the window. But we will have to
6559 reset the echo_area_buffer in question to nil at the end because
6560 with_echo_area_buffer will sets it to an empty buffer. */
6561 i = display_last_displayed_message_p ? 1 : 0;
6562 no_message_p = NILP (echo_area_buffer[i]);
6564 window_height_changed_p
6565 = with_echo_area_buffer (w, display_last_displayed_message_p,
6566 display_echo_area_1,
6567 (EMACS_INT) w, Qnil, 0, 0);
6569 if (no_message_p)
6570 echo_area_buffer[i] = Qnil;
6572 unbind_to (count, Qnil);
6573 return window_height_changed_p;
6577 /* Helper for display_echo_area. Display the current buffer which
6578 contains the current echo area message in window W, a mini-window,
6579 a pointer to which is passed in A1. A2..A4 are currently not used.
6580 Change the height of W so that all of the message is displayed.
6581 Value is non-zero if height of W was changed. */
6583 static int
6584 display_echo_area_1 (a1, a2, a3, a4)
6585 EMACS_INT a1;
6586 Lisp_Object a2;
6587 EMACS_INT a3, a4;
6589 struct window *w = (struct window *) a1;
6590 Lisp_Object window;
6591 struct text_pos start;
6592 int window_height_changed_p = 0;
6594 /* Do this before displaying, so that we have a large enough glyph
6595 matrix for the display. */
6596 window_height_changed_p = resize_mini_window (w, 0);
6598 /* Display. */
6599 clear_glyph_matrix (w->desired_matrix);
6600 XSETWINDOW (window, w);
6601 SET_TEXT_POS (start, BEG, BEG_BYTE);
6602 try_window (window, start);
6604 return window_height_changed_p;
6608 /* Resize the echo area window to exactly the size needed for the
6609 currently displayed message, if there is one. If a mini-buffer
6610 is active, don't shrink it. */
6612 void
6613 resize_echo_area_exactly ()
6615 if (BUFFERP (echo_area_buffer[0])
6616 && WINDOWP (echo_area_window))
6618 struct window *w = XWINDOW (echo_area_window);
6619 int resized_p;
6620 Lisp_Object resize_exactly;
6622 if (minibuf_level == 0)
6623 resize_exactly = Qt;
6624 else
6625 resize_exactly = Qnil;
6627 resized_p = with_echo_area_buffer (w, 0, resize_mini_window_1,
6628 (EMACS_INT) w, resize_exactly, 0, 0);
6629 if (resized_p)
6631 ++windows_or_buffers_changed;
6632 ++update_mode_lines;
6633 redisplay_internal (0);
6639 /* Callback function for with_echo_area_buffer, when used from
6640 resize_echo_area_exactly. A1 contains a pointer to the window to
6641 resize, EXACTLY non-nil means resize the mini-window exactly to the
6642 size of the text displayed. A3 and A4 are not used. Value is what
6643 resize_mini_window returns. */
6645 static int
6646 resize_mini_window_1 (a1, exactly, a3, a4)
6647 EMACS_INT a1;
6648 Lisp_Object exactly;
6649 EMACS_INT a3, a4;
6651 return resize_mini_window ((struct window *) a1, !NILP (exactly));
6655 /* Resize mini-window W to fit the size of its contents. EXACT:P
6656 means size the window exactly to the size needed. Otherwise, it's
6657 only enlarged until W's buffer is empty. Value is non-zero if
6658 the window height has been changed. */
6661 resize_mini_window (w, exact_p)
6662 struct window *w;
6663 int exact_p;
6665 struct frame *f = XFRAME (w->frame);
6666 int window_height_changed_p = 0;
6668 xassert (MINI_WINDOW_P (w));
6670 /* Don't resize windows while redisplaying a window; it would
6671 confuse redisplay functions when the size of the window they are
6672 displaying changes from under them. Such a resizing can happen,
6673 for instance, when which-func prints a long message while
6674 we are running fontification-functions. We're running these
6675 functions with safe_call which binds inhibit-redisplay to t. */
6676 if (!NILP (Vinhibit_redisplay))
6677 return 0;
6679 /* Nil means don't try to resize. */
6680 if (NILP (Vresize_mini_windows)
6681 || (FRAME_X_P (f) && f->output_data.x == NULL))
6682 return 0;
6684 if (!FRAME_MINIBUF_ONLY_P (f))
6686 struct it it;
6687 struct window *root = XWINDOW (FRAME_ROOT_WINDOW (f));
6688 int total_height = XFASTINT (root->height) + XFASTINT (w->height);
6689 int height, max_height;
6690 int unit = CANON_Y_UNIT (f);
6691 struct text_pos start;
6692 struct buffer *old_current_buffer = NULL;
6694 if (current_buffer != XBUFFER (w->buffer))
6696 old_current_buffer = current_buffer;
6697 set_buffer_internal (XBUFFER (w->buffer));
6700 init_iterator (&it, w, BEGV, BEGV_BYTE, NULL, DEFAULT_FACE_ID);
6702 /* Compute the max. number of lines specified by the user. */
6703 if (FLOATP (Vmax_mini_window_height))
6704 max_height = XFLOATINT (Vmax_mini_window_height) * FRAME_HEIGHT (f);
6705 else if (INTEGERP (Vmax_mini_window_height))
6706 max_height = XINT (Vmax_mini_window_height);
6707 else
6708 max_height = total_height / 4;
6710 /* Correct that max. height if it's bogus. */
6711 max_height = max (1, max_height);
6712 max_height = min (total_height, max_height);
6714 /* Find out the height of the text in the window. */
6715 if (it.truncate_lines_p)
6716 height = 1;
6717 else
6719 last_height = 0;
6720 move_it_to (&it, ZV, -1, -1, -1, MOVE_TO_POS);
6721 if (it.max_ascent == 0 && it.max_descent == 0)
6722 height = it.current_y + last_height;
6723 else
6724 height = it.current_y + it.max_ascent + it.max_descent;
6725 height -= it.extra_line_spacing;
6726 height = (height + unit - 1) / unit;
6729 /* Compute a suitable window start. */
6730 if (height > max_height)
6732 height = max_height;
6733 init_iterator (&it, w, PT, PT_BYTE, NULL, DEFAULT_FACE_ID);
6734 move_it_vertically_backward (&it, (height - 1) * unit);
6735 start = it.current.pos;
6737 else
6738 SET_TEXT_POS (start, BEGV, BEGV_BYTE);
6739 SET_MARKER_FROM_TEXT_POS (w->start, start);
6741 if (EQ (Vresize_mini_windows, Qgrow_only))
6743 /* Let it grow only, until we display an empty message, in which
6744 case the window shrinks again. */
6745 if (height > XFASTINT (w->height))
6747 int old_height = XFASTINT (w->height);
6748 freeze_window_starts (f, 1);
6749 grow_mini_window (w, height - XFASTINT (w->height));
6750 window_height_changed_p = XFASTINT (w->height) != old_height;
6752 else if (height < XFASTINT (w->height)
6753 && (exact_p || BEGV == ZV))
6755 int old_height = XFASTINT (w->height);
6756 freeze_window_starts (f, 0);
6757 shrink_mini_window (w);
6758 window_height_changed_p = XFASTINT (w->height) != old_height;
6761 else
6763 /* Always resize to exact size needed. */
6764 if (height > XFASTINT (w->height))
6766 int old_height = XFASTINT (w->height);
6767 freeze_window_starts (f, 1);
6768 grow_mini_window (w, height - XFASTINT (w->height));
6769 window_height_changed_p = XFASTINT (w->height) != old_height;
6771 else if (height < XFASTINT (w->height))
6773 int old_height = XFASTINT (w->height);
6774 freeze_window_starts (f, 0);
6775 shrink_mini_window (w);
6777 if (height)
6779 freeze_window_starts (f, 1);
6780 grow_mini_window (w, height - XFASTINT (w->height));
6783 window_height_changed_p = XFASTINT (w->height) != old_height;
6787 if (old_current_buffer)
6788 set_buffer_internal (old_current_buffer);
6791 return window_height_changed_p;
6795 /* Value is the current message, a string, or nil if there is no
6796 current message. */
6798 Lisp_Object
6799 current_message ()
6801 Lisp_Object msg;
6803 if (NILP (echo_area_buffer[0]))
6804 msg = Qnil;
6805 else
6807 with_echo_area_buffer (0, 0, current_message_1,
6808 (EMACS_INT) &msg, Qnil, 0, 0);
6809 if (NILP (msg))
6810 echo_area_buffer[0] = Qnil;
6813 return msg;
6817 static int
6818 current_message_1 (a1, a2, a3, a4)
6819 EMACS_INT a1;
6820 Lisp_Object a2;
6821 EMACS_INT a3, a4;
6823 Lisp_Object *msg = (Lisp_Object *) a1;
6825 if (Z > BEG)
6826 *msg = make_buffer_string (BEG, Z, 1);
6827 else
6828 *msg = Qnil;
6829 return 0;
6833 /* Push the current message on Vmessage_stack for later restauration
6834 by restore_message. Value is non-zero if the current message isn't
6835 empty. This is a relatively infrequent operation, so it's not
6836 worth optimizing. */
6839 push_message ()
6841 Lisp_Object msg;
6842 msg = current_message ();
6843 Vmessage_stack = Fcons (msg, Vmessage_stack);
6844 return STRINGP (msg);
6848 /* Restore message display from the top of Vmessage_stack. */
6850 void
6851 restore_message ()
6853 Lisp_Object msg;
6855 xassert (CONSP (Vmessage_stack));
6856 msg = XCAR (Vmessage_stack);
6857 if (STRINGP (msg))
6858 message3_nolog (msg, SBYTES (msg), STRING_MULTIBYTE (msg));
6859 else
6860 message3_nolog (msg, 0, 0);
6864 /* Handler for record_unwind_protect calling pop_message. */
6866 Lisp_Object
6867 pop_message_unwind (dummy)
6868 Lisp_Object dummy;
6870 pop_message ();
6871 return Qnil;
6874 /* Pop the top-most entry off Vmessage_stack. */
6876 void
6877 pop_message ()
6879 xassert (CONSP (Vmessage_stack));
6880 Vmessage_stack = XCDR (Vmessage_stack);
6884 /* Check that Vmessage_stack is nil. Called from emacs.c when Emacs
6885 exits. If the stack is not empty, we have a missing pop_message
6886 somewhere. */
6888 void
6889 check_message_stack ()
6891 if (!NILP (Vmessage_stack))
6892 abort ();
6896 /* Truncate to NCHARS what will be displayed in the echo area the next
6897 time we display it---but don't redisplay it now. */
6899 void
6900 truncate_echo_area (nchars)
6901 int nchars;
6903 if (nchars == 0)
6904 echo_area_buffer[0] = Qnil;
6905 /* A null message buffer means that the frame hasn't really been
6906 initialized yet. Error messages get reported properly by
6907 cmd_error, so this must be just an informative message; toss it. */
6908 else if (!noninteractive
6909 && INTERACTIVE
6910 && !NILP (echo_area_buffer[0]))
6912 struct frame *sf = SELECTED_FRAME ();
6913 if (FRAME_MESSAGE_BUF (sf))
6914 with_echo_area_buffer (0, 0, truncate_message_1, nchars, Qnil, 0, 0);
6919 /* Helper function for truncate_echo_area. Truncate the current
6920 message to at most NCHARS characters. */
6922 static int
6923 truncate_message_1 (nchars, a2, a3, a4)
6924 EMACS_INT nchars;
6925 Lisp_Object a2;
6926 EMACS_INT a3, a4;
6928 if (BEG + nchars < Z)
6929 del_range (BEG + nchars, Z);
6930 if (Z == BEG)
6931 echo_area_buffer[0] = Qnil;
6932 return 0;
6936 /* Set the current message to a substring of S or STRING.
6938 If STRING is a Lisp string, set the message to the first NBYTES
6939 bytes from STRING. NBYTES zero means use the whole string. If
6940 STRING is multibyte, the message will be displayed multibyte.
6942 If S is not null, set the message to the first LEN bytes of S. LEN
6943 zero means use the whole string. MULTIBYTE_P non-zero means S is
6944 multibyte. Display the message multibyte in that case. */
6946 void
6947 set_message (s, string, nbytes, multibyte_p)
6948 const char *s;
6949 Lisp_Object string;
6950 int nbytes;
6952 message_enable_multibyte
6953 = ((s && multibyte_p)
6954 || (STRINGP (string) && STRING_MULTIBYTE (string)));
6956 with_echo_area_buffer (0, -1, set_message_1,
6957 (EMACS_INT) s, string, nbytes, multibyte_p);
6958 message_buf_print = 0;
6959 help_echo_showing_p = 0;
6963 /* Helper function for set_message. Arguments have the same meaning
6964 as there, with A1 corresponding to S and A2 corresponding to STRING
6965 This function is called with the echo area buffer being
6966 current. */
6968 static int
6969 set_message_1 (a1, a2, nbytes, multibyte_p)
6970 EMACS_INT a1;
6971 Lisp_Object a2;
6972 EMACS_INT nbytes, multibyte_p;
6974 const char *s = (const char *) a1;
6975 Lisp_Object string = a2;
6977 xassert (BEG == Z);
6979 /* Change multibyteness of the echo buffer appropriately. */
6980 if (message_enable_multibyte
6981 != !NILP (current_buffer->enable_multibyte_characters))
6982 Fset_buffer_multibyte (message_enable_multibyte ? Qt : Qnil);
6984 current_buffer->truncate_lines = message_truncate_lines ? Qt : Qnil;
6986 /* Insert new message at BEG. */
6987 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
6989 if (STRINGP (string))
6991 int nchars;
6993 if (nbytes == 0)
6994 nbytes = SBYTES (string);
6995 nchars = string_byte_to_char (string, nbytes);
6997 /* This function takes care of single/multibyte conversion. We
6998 just have to ensure that the echo area buffer has the right
6999 setting of enable_multibyte_characters. */
7000 insert_from_string (string, 0, 0, nchars, nbytes, 1);
7002 else if (s)
7004 if (nbytes == 0)
7005 nbytes = strlen (s);
7007 if (multibyte_p && NILP (current_buffer->enable_multibyte_characters))
7009 /* Convert from multi-byte to single-byte. */
7010 int i, c, n;
7011 unsigned char work[1];
7013 /* Convert a multibyte string to single-byte. */
7014 for (i = 0; i < nbytes; i += n)
7016 c = string_char_and_length (s + i, nbytes - i, &n);
7017 work[0] = (SINGLE_BYTE_CHAR_P (c)
7019 : multibyte_char_to_unibyte (c, Qnil));
7020 insert_1_both (work, 1, 1, 1, 0, 0);
7023 else if (!multibyte_p
7024 && !NILP (current_buffer->enable_multibyte_characters))
7026 /* Convert from single-byte to multi-byte. */
7027 int i, c, n;
7028 const unsigned char *msg = (const unsigned char *) s;
7029 unsigned char str[MAX_MULTIBYTE_LENGTH];
7031 /* Convert a single-byte string to multibyte. */
7032 for (i = 0; i < nbytes; i++)
7034 c = unibyte_char_to_multibyte (msg[i]);
7035 n = CHAR_STRING (c, str);
7036 insert_1_both (str, 1, n, 1, 0, 0);
7039 else
7040 insert_1 (s, nbytes, 1, 0, 0);
7043 return 0;
7047 /* Clear messages. CURRENT_P non-zero means clear the current
7048 message. LAST_DISPLAYED_P non-zero means clear the message
7049 last displayed. */
7051 void
7052 clear_message (current_p, last_displayed_p)
7053 int current_p, last_displayed_p;
7055 if (current_p)
7057 echo_area_buffer[0] = Qnil;
7058 message_cleared_p = 1;
7061 if (last_displayed_p)
7062 echo_area_buffer[1] = Qnil;
7064 message_buf_print = 0;
7067 /* Clear garbaged frames.
7069 This function is used where the old redisplay called
7070 redraw_garbaged_frames which in turn called redraw_frame which in
7071 turn called clear_frame. The call to clear_frame was a source of
7072 flickering. I believe a clear_frame is not necessary. It should
7073 suffice in the new redisplay to invalidate all current matrices,
7074 and ensure a complete redisplay of all windows. */
7076 static void
7077 clear_garbaged_frames ()
7079 if (frame_garbaged)
7081 Lisp_Object tail, frame;
7082 int changed_count = 0;
7084 FOR_EACH_FRAME (tail, frame)
7086 struct frame *f = XFRAME (frame);
7088 if (FRAME_VISIBLE_P (f) && FRAME_GARBAGED_P (f))
7090 if (f->resized_p)
7091 Fredraw_frame (frame);
7092 clear_current_matrices (f);
7093 changed_count++;
7094 f->garbaged = 0;
7095 f->resized_p = 0;
7099 frame_garbaged = 0;
7100 if (changed_count)
7101 ++windows_or_buffers_changed;
7106 /* Redisplay the echo area of the selected frame. If UPDATE_FRAME_P
7107 is non-zero update selected_frame. Value is non-zero if the
7108 mini-windows height has been changed. */
7110 static int
7111 echo_area_display (update_frame_p)
7112 int update_frame_p;
7114 Lisp_Object mini_window;
7115 struct window *w;
7116 struct frame *f;
7117 int window_height_changed_p = 0;
7118 struct frame *sf = SELECTED_FRAME ();
7120 mini_window = FRAME_MINIBUF_WINDOW (sf);
7121 w = XWINDOW (mini_window);
7122 f = XFRAME (WINDOW_FRAME (w));
7124 /* Don't display if frame is invisible or not yet initialized. */
7125 if (!FRAME_VISIBLE_P (f) || !f->glyphs_initialized_p)
7126 return 0;
7128 /* The terminal frame is used as the first Emacs frame on the Mac OS. */
7129 #ifndef MAC_OS8
7130 #ifdef HAVE_WINDOW_SYSTEM
7131 /* When Emacs starts, selected_frame may be a visible terminal
7132 frame, even if we run under a window system. If we let this
7133 through, a message would be displayed on the terminal. */
7134 if (EQ (selected_frame, Vterminal_frame)
7135 && !NILP (Vwindow_system))
7136 return 0;
7137 #endif /* HAVE_WINDOW_SYSTEM */
7138 #endif
7140 /* Redraw garbaged frames. */
7141 if (frame_garbaged)
7142 clear_garbaged_frames ();
7144 if (!NILP (echo_area_buffer[0]) || minibuf_level == 0)
7146 echo_area_window = mini_window;
7147 window_height_changed_p = display_echo_area (w);
7148 w->must_be_updated_p = 1;
7150 /* Update the display, unless called from redisplay_internal.
7151 Also don't update the screen during redisplay itself. The
7152 update will happen at the end of redisplay, and an update
7153 here could cause confusion. */
7154 if (update_frame_p && !redisplaying_p)
7156 int n = 0;
7158 /* If the display update has been interrupted by pending
7159 input, update mode lines in the frame. Due to the
7160 pending input, it might have been that redisplay hasn't
7161 been called, so that mode lines above the echo area are
7162 garbaged. This looks odd, so we prevent it here. */
7163 if (!display_completed)
7164 n = redisplay_mode_lines (FRAME_ROOT_WINDOW (f), 0);
7166 if (window_height_changed_p
7167 /* Don't do this if Emacs is shutting down. Redisplay
7168 needs to run hooks. */
7169 && !NILP (Vrun_hooks))
7171 /* Must update other windows. Likewise as in other
7172 cases, don't let this update be interrupted by
7173 pending input. */
7174 int count = SPECPDL_INDEX ();
7175 specbind (Qredisplay_dont_pause, Qt);
7176 windows_or_buffers_changed = 1;
7177 redisplay_internal (0);
7178 unbind_to (count, Qnil);
7180 else if (FRAME_WINDOW_P (f) && n == 0)
7182 /* Window configuration is the same as before.
7183 Can do with a display update of the echo area,
7184 unless we displayed some mode lines. */
7185 update_single_window (w, 1);
7186 rif->flush_display (f);
7188 else
7189 update_frame (f, 1, 1);
7191 /* If cursor is in the echo area, make sure that the next
7192 redisplay displays the minibuffer, so that the cursor will
7193 be replaced with what the minibuffer wants. */
7194 if (cursor_in_echo_area)
7195 ++windows_or_buffers_changed;
7198 else if (!EQ (mini_window, selected_window))
7199 windows_or_buffers_changed++;
7201 /* Last displayed message is now the current message. */
7202 echo_area_buffer[1] = echo_area_buffer[0];
7204 /* Prevent redisplay optimization in redisplay_internal by resetting
7205 this_line_start_pos. This is done because the mini-buffer now
7206 displays the message instead of its buffer text. */
7207 if (EQ (mini_window, selected_window))
7208 CHARPOS (this_line_start_pos) = 0;
7210 return window_height_changed_p;
7215 /***********************************************************************
7216 Frame Titles
7217 ***********************************************************************/
7220 /* The frame title buffering code is also used by Fformat_mode_line.
7221 So it is not conditioned by HAVE_WINDOW_SYSTEM. */
7223 /* A buffer for constructing frame titles in it; allocated from the
7224 heap in init_xdisp and resized as needed in store_frame_title_char. */
7226 static char *frame_title_buf;
7228 /* The buffer's end, and a current output position in it. */
7230 static char *frame_title_buf_end;
7231 static char *frame_title_ptr;
7234 /* Store a single character C for the frame title in frame_title_buf.
7235 Re-allocate frame_title_buf if necessary. */
7237 static void
7238 store_frame_title_char (c)
7239 char c;
7241 /* If output position has reached the end of the allocated buffer,
7242 double the buffer's size. */
7243 if (frame_title_ptr == frame_title_buf_end)
7245 int len = frame_title_ptr - frame_title_buf;
7246 int new_size = 2 * len * sizeof *frame_title_buf;
7247 frame_title_buf = (char *) xrealloc (frame_title_buf, new_size);
7248 frame_title_buf_end = frame_title_buf + new_size;
7249 frame_title_ptr = frame_title_buf + len;
7252 *frame_title_ptr++ = c;
7256 /* Store part of a frame title in frame_title_buf, beginning at
7257 frame_title_ptr. STR is the string to store. Do not copy
7258 characters that yield more columns than PRECISION; PRECISION <= 0
7259 means copy the whole string. Pad with spaces until FIELD_WIDTH
7260 number of characters have been copied; FIELD_WIDTH <= 0 means don't
7261 pad. Called from display_mode_element when it is used to build a
7262 frame title. */
7264 static int
7265 store_frame_title (str, field_width, precision)
7266 const unsigned char *str;
7267 int field_width, precision;
7269 int n = 0;
7270 int dummy, nbytes;
7272 /* Copy at most PRECISION chars from STR. */
7273 nbytes = strlen (str);
7274 n+= c_string_width (str, nbytes, precision, &dummy, &nbytes);
7275 while (nbytes--)
7276 store_frame_title_char (*str++);
7278 /* Fill up with spaces until FIELD_WIDTH reached. */
7279 while (field_width > 0
7280 && n < field_width)
7282 store_frame_title_char (' ');
7283 ++n;
7286 return n;
7289 #ifdef HAVE_WINDOW_SYSTEM
7291 /* Set the title of FRAME, if it has changed. The title format is
7292 Vicon_title_format if FRAME is iconified, otherwise it is
7293 frame_title_format. */
7295 static void
7296 x_consider_frame_title (frame)
7297 Lisp_Object frame;
7299 struct frame *f = XFRAME (frame);
7301 if (FRAME_WINDOW_P (f)
7302 || FRAME_MINIBUF_ONLY_P (f)
7303 || f->explicit_name)
7305 /* Do we have more than one visible frame on this X display? */
7306 Lisp_Object tail;
7307 Lisp_Object fmt;
7308 struct buffer *obuf;
7309 int len;
7310 struct it it;
7312 for (tail = Vframe_list; CONSP (tail); tail = XCDR (tail))
7314 Lisp_Object other_frame = XCAR (tail);
7315 struct frame *tf = XFRAME (other_frame);
7317 if (tf != f
7318 && FRAME_KBOARD (tf) == FRAME_KBOARD (f)
7319 && !FRAME_MINIBUF_ONLY_P (tf)
7320 && !EQ (other_frame, tip_frame)
7321 && (FRAME_VISIBLE_P (tf) || FRAME_ICONIFIED_P (tf)))
7322 break;
7325 /* Set global variable indicating that multiple frames exist. */
7326 multiple_frames = CONSP (tail);
7328 /* Switch to the buffer of selected window of the frame. Set up
7329 frame_title_ptr so that display_mode_element will output into it;
7330 then display the title. */
7331 obuf = current_buffer;
7332 set_buffer_internal_1 (XBUFFER (XWINDOW (f->selected_window)->buffer));
7333 fmt = FRAME_ICONIFIED_P (f) ? Vicon_title_format : Vframe_title_format;
7334 frame_title_ptr = frame_title_buf;
7335 init_iterator (&it, XWINDOW (f->selected_window), -1, -1,
7336 NULL, DEFAULT_FACE_ID);
7337 display_mode_element (&it, 0, -1, -1, fmt, Qnil, 0);
7338 len = frame_title_ptr - frame_title_buf;
7339 frame_title_ptr = NULL;
7340 set_buffer_internal_1 (obuf);
7342 /* Set the title only if it's changed. This avoids consing in
7343 the common case where it hasn't. (If it turns out that we've
7344 already wasted too much time by walking through the list with
7345 display_mode_element, then we might need to optimize at a
7346 higher level than this.) */
7347 if (! STRINGP (f->name)
7348 || SBYTES (f->name) != len
7349 || bcmp (frame_title_buf, SDATA (f->name), len) != 0)
7350 x_implicitly_set_name (f, make_string (frame_title_buf, len), Qnil);
7354 #endif /* not HAVE_WINDOW_SYSTEM */
7359 /***********************************************************************
7360 Menu Bars
7361 ***********************************************************************/
7364 /* Prepare for redisplay by updating menu-bar item lists when
7365 appropriate. This can call eval. */
7367 void
7368 prepare_menu_bars ()
7370 int all_windows;
7371 struct gcpro gcpro1, gcpro2;
7372 struct frame *f;
7373 Lisp_Object tooltip_frame;
7375 #ifdef HAVE_WINDOW_SYSTEM
7376 tooltip_frame = tip_frame;
7377 #else
7378 tooltip_frame = Qnil;
7379 #endif
7381 /* Update all frame titles based on their buffer names, etc. We do
7382 this before the menu bars so that the buffer-menu will show the
7383 up-to-date frame titles. */
7384 #ifdef HAVE_WINDOW_SYSTEM
7385 if (windows_or_buffers_changed || update_mode_lines)
7387 Lisp_Object tail, frame;
7389 FOR_EACH_FRAME (tail, frame)
7391 f = XFRAME (frame);
7392 if (!EQ (frame, tooltip_frame)
7393 && (FRAME_VISIBLE_P (f) || FRAME_ICONIFIED_P (f)))
7394 x_consider_frame_title (frame);
7397 #endif /* HAVE_WINDOW_SYSTEM */
7399 /* Update the menu bar item lists, if appropriate. This has to be
7400 done before any actual redisplay or generation of display lines. */
7401 all_windows = (update_mode_lines
7402 || buffer_shared > 1
7403 || windows_or_buffers_changed);
7404 if (all_windows)
7406 Lisp_Object tail, frame;
7407 int count = SPECPDL_INDEX ();
7409 record_unwind_protect (Fset_match_data, Fmatch_data (Qnil, Qnil));
7411 FOR_EACH_FRAME (tail, frame)
7413 f = XFRAME (frame);
7415 /* Ignore tooltip frame. */
7416 if (EQ (frame, tooltip_frame))
7417 continue;
7419 /* If a window on this frame changed size, report that to
7420 the user and clear the size-change flag. */
7421 if (FRAME_WINDOW_SIZES_CHANGED (f))
7423 Lisp_Object functions;
7425 /* Clear flag first in case we get an error below. */
7426 FRAME_WINDOW_SIZES_CHANGED (f) = 0;
7427 functions = Vwindow_size_change_functions;
7428 GCPRO2 (tail, functions);
7430 while (CONSP (functions))
7432 call1 (XCAR (functions), frame);
7433 functions = XCDR (functions);
7435 UNGCPRO;
7438 GCPRO1 (tail);
7439 update_menu_bar (f, 0);
7440 #ifdef HAVE_WINDOW_SYSTEM
7441 update_tool_bar (f, 0);
7442 #endif
7443 UNGCPRO;
7446 unbind_to (count, Qnil);
7448 else
7450 struct frame *sf = SELECTED_FRAME ();
7451 update_menu_bar (sf, 1);
7452 #ifdef HAVE_WINDOW_SYSTEM
7453 update_tool_bar (sf, 1);
7454 #endif
7457 /* Motif needs this. See comment in xmenu.c. Turn it off when
7458 pending_menu_activation is not defined. */
7459 #ifdef USE_X_TOOLKIT
7460 pending_menu_activation = 0;
7461 #endif
7465 /* Update the menu bar item list for frame F. This has to be done
7466 before we start to fill in any display lines, because it can call
7467 eval.
7469 If SAVE_MATCH_DATA is non-zero, we must save and restore it here. */
7471 static void
7472 update_menu_bar (f, save_match_data)
7473 struct frame *f;
7474 int save_match_data;
7476 Lisp_Object window;
7477 register struct window *w;
7479 /* If called recursively during a menu update, do nothing. This can
7480 happen when, for instance, an activate-menubar-hook causes a
7481 redisplay. */
7482 if (inhibit_menubar_update)
7483 return;
7485 window = FRAME_SELECTED_WINDOW (f);
7486 w = XWINDOW (window);
7488 #if 0 /* The if statement below this if statement used to include the
7489 condition !NILP (w->update_mode_line), rather than using
7490 update_mode_lines directly, and this if statement may have
7491 been added to make that condition work. Now the if
7492 statement below matches its comment, this isn't needed. */
7493 if (update_mode_lines)
7494 w->update_mode_line = Qt;
7495 #endif
7497 if (FRAME_WINDOW_P (f)
7499 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) || defined (MAC_OS)
7500 FRAME_EXTERNAL_MENU_BAR (f)
7501 #else
7502 FRAME_MENU_BAR_LINES (f) > 0
7503 #endif
7504 : FRAME_MENU_BAR_LINES (f) > 0)
7506 /* If the user has switched buffers or windows, we need to
7507 recompute to reflect the new bindings. But we'll
7508 recompute when update_mode_lines is set too; that means
7509 that people can use force-mode-line-update to request
7510 that the menu bar be recomputed. The adverse effect on
7511 the rest of the redisplay algorithm is about the same as
7512 windows_or_buffers_changed anyway. */
7513 if (windows_or_buffers_changed
7514 /* This used to test w->update_mode_line, but we believe
7515 there is no need to recompute the menu in that case. */
7516 || update_mode_lines
7517 || ((BUF_SAVE_MODIFF (XBUFFER (w->buffer))
7518 < BUF_MODIFF (XBUFFER (w->buffer)))
7519 != !NILP (w->last_had_star))
7520 || ((!NILP (Vtransient_mark_mode)
7521 && !NILP (XBUFFER (w->buffer)->mark_active))
7522 != !NILP (w->region_showing)))
7524 struct buffer *prev = current_buffer;
7525 int count = SPECPDL_INDEX ();
7527 specbind (Qinhibit_menubar_update, Qt);
7529 set_buffer_internal_1 (XBUFFER (w->buffer));
7530 if (save_match_data)
7531 record_unwind_protect (Fset_match_data, Fmatch_data (Qnil, Qnil));
7532 if (NILP (Voverriding_local_map_menu_flag))
7534 specbind (Qoverriding_terminal_local_map, Qnil);
7535 specbind (Qoverriding_local_map, Qnil);
7538 /* Run the Lucid hook. */
7539 safe_run_hooks (Qactivate_menubar_hook);
7541 /* If it has changed current-menubar from previous value,
7542 really recompute the menu-bar from the value. */
7543 if (! NILP (Vlucid_menu_bar_dirty_flag))
7544 call0 (Qrecompute_lucid_menubar);
7546 safe_run_hooks (Qmenu_bar_update_hook);
7547 FRAME_MENU_BAR_ITEMS (f) = menu_bar_items (FRAME_MENU_BAR_ITEMS (f));
7549 /* Redisplay the menu bar in case we changed it. */
7550 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) || defined (MAC_OS)
7551 if (FRAME_WINDOW_P (f)
7552 #if defined (MAC_OS)
7553 /* All frames on Mac OS share the same menubar. So only the
7554 selected frame should be allowed to set it. */
7555 && f == SELECTED_FRAME ()
7556 #endif
7558 set_frame_menubar (f, 0, 0);
7559 else
7560 /* On a terminal screen, the menu bar is an ordinary screen
7561 line, and this makes it get updated. */
7562 w->update_mode_line = Qt;
7563 #else /* ! (USE_X_TOOLKIT || HAVE_NTGUI) */
7564 /* In the non-toolkit version, the menu bar is an ordinary screen
7565 line, and this makes it get updated. */
7566 w->update_mode_line = Qt;
7567 #endif /* ! (USE_X_TOOLKIT || HAVE_NTGUI) */
7569 unbind_to (count, Qnil);
7570 set_buffer_internal_1 (prev);
7577 /***********************************************************************
7578 Tool-bars
7579 ***********************************************************************/
7581 #ifdef HAVE_WINDOW_SYSTEM
7583 /* Update the tool-bar item list for frame F. This has to be done
7584 before we start to fill in any display lines. Called from
7585 prepare_menu_bars. If SAVE_MATCH_DATA is non-zero, we must save
7586 and restore it here. */
7588 static void
7589 update_tool_bar (f, save_match_data)
7590 struct frame *f;
7591 int save_match_data;
7593 if (WINDOWP (f->tool_bar_window)
7594 && XFASTINT (XWINDOW (f->tool_bar_window)->height) > 0)
7596 Lisp_Object window;
7597 struct window *w;
7599 window = FRAME_SELECTED_WINDOW (f);
7600 w = XWINDOW (window);
7602 /* If the user has switched buffers or windows, we need to
7603 recompute to reflect the new bindings. But we'll
7604 recompute when update_mode_lines is set too; that means
7605 that people can use force-mode-line-update to request
7606 that the menu bar be recomputed. The adverse effect on
7607 the rest of the redisplay algorithm is about the same as
7608 windows_or_buffers_changed anyway. */
7609 if (windows_or_buffers_changed
7610 || !NILP (w->update_mode_line)
7611 || ((BUF_SAVE_MODIFF (XBUFFER (w->buffer))
7612 < BUF_MODIFF (XBUFFER (w->buffer)))
7613 != !NILP (w->last_had_star))
7614 || ((!NILP (Vtransient_mark_mode)
7615 && !NILP (XBUFFER (w->buffer)->mark_active))
7616 != !NILP (w->region_showing)))
7618 struct buffer *prev = current_buffer;
7619 int count = SPECPDL_INDEX ();
7621 /* Set current_buffer to the buffer of the selected
7622 window of the frame, so that we get the right local
7623 keymaps. */
7624 set_buffer_internal_1 (XBUFFER (w->buffer));
7626 /* Save match data, if we must. */
7627 if (save_match_data)
7628 record_unwind_protect (Fset_match_data, Fmatch_data (Qnil, Qnil));
7630 /* Make sure that we don't accidentally use bogus keymaps. */
7631 if (NILP (Voverriding_local_map_menu_flag))
7633 specbind (Qoverriding_terminal_local_map, Qnil);
7634 specbind (Qoverriding_local_map, Qnil);
7637 /* Build desired tool-bar items from keymaps. */
7638 f->tool_bar_items
7639 = tool_bar_items (f->tool_bar_items, &f->n_tool_bar_items);
7641 /* Redisplay the tool-bar in case we changed it. */
7642 w->update_mode_line = Qt;
7644 unbind_to (count, Qnil);
7645 set_buffer_internal_1 (prev);
7651 /* Set F->desired_tool_bar_string to a Lisp string representing frame
7652 F's desired tool-bar contents. F->tool_bar_items must have
7653 been set up previously by calling prepare_menu_bars. */
7655 static void
7656 build_desired_tool_bar_string (f)
7657 struct frame *f;
7659 int i, size, size_needed;
7660 struct gcpro gcpro1, gcpro2, gcpro3;
7661 Lisp_Object image, plist, props;
7663 image = plist = props = Qnil;
7664 GCPRO3 (image, plist, props);
7666 /* Prepare F->desired_tool_bar_string. If we can reuse it, do so.
7667 Otherwise, make a new string. */
7669 /* The size of the string we might be able to reuse. */
7670 size = (STRINGP (f->desired_tool_bar_string)
7671 ? SCHARS (f->desired_tool_bar_string)
7672 : 0);
7674 /* We need one space in the string for each image. */
7675 size_needed = f->n_tool_bar_items;
7677 /* Reuse f->desired_tool_bar_string, if possible. */
7678 if (size < size_needed || NILP (f->desired_tool_bar_string))
7679 f->desired_tool_bar_string = Fmake_string (make_number (size_needed),
7680 make_number (' '));
7681 else
7683 props = list4 (Qdisplay, Qnil, Qmenu_item, Qnil);
7684 Fremove_text_properties (make_number (0), make_number (size),
7685 props, f->desired_tool_bar_string);
7688 /* Put a `display' property on the string for the images to display,
7689 put a `menu_item' property on tool-bar items with a value that
7690 is the index of the item in F's tool-bar item vector. */
7691 for (i = 0; i < f->n_tool_bar_items; ++i)
7693 #define PROP(IDX) AREF (f->tool_bar_items, i * TOOL_BAR_ITEM_NSLOTS + (IDX))
7695 int enabled_p = !NILP (PROP (TOOL_BAR_ITEM_ENABLED_P));
7696 int selected_p = !NILP (PROP (TOOL_BAR_ITEM_SELECTED_P));
7697 int hmargin, vmargin, relief, idx, end;
7698 extern Lisp_Object QCrelief, QCmargin, QCconversion, Qimage;
7700 /* If image is a vector, choose the image according to the
7701 button state. */
7702 image = PROP (TOOL_BAR_ITEM_IMAGES);
7703 if (VECTORP (image))
7705 if (enabled_p)
7706 idx = (selected_p
7707 ? TOOL_BAR_IMAGE_ENABLED_SELECTED
7708 : TOOL_BAR_IMAGE_ENABLED_DESELECTED);
7709 else
7710 idx = (selected_p
7711 ? TOOL_BAR_IMAGE_DISABLED_SELECTED
7712 : TOOL_BAR_IMAGE_DISABLED_DESELECTED);
7714 xassert (ASIZE (image) >= idx);
7715 image = AREF (image, idx);
7717 else
7718 idx = -1;
7720 /* Ignore invalid image specifications. */
7721 if (!valid_image_p (image))
7722 continue;
7724 /* Display the tool-bar button pressed, or depressed. */
7725 plist = Fcopy_sequence (XCDR (image));
7727 /* Compute margin and relief to draw. */
7728 relief = (tool_bar_button_relief >= 0
7729 ? tool_bar_button_relief
7730 : DEFAULT_TOOL_BAR_BUTTON_RELIEF);
7731 hmargin = vmargin = relief;
7733 if (INTEGERP (Vtool_bar_button_margin)
7734 && XINT (Vtool_bar_button_margin) > 0)
7736 hmargin += XFASTINT (Vtool_bar_button_margin);
7737 vmargin += XFASTINT (Vtool_bar_button_margin);
7739 else if (CONSP (Vtool_bar_button_margin))
7741 if (INTEGERP (XCAR (Vtool_bar_button_margin))
7742 && XINT (XCAR (Vtool_bar_button_margin)) > 0)
7743 hmargin += XFASTINT (XCAR (Vtool_bar_button_margin));
7745 if (INTEGERP (XCDR (Vtool_bar_button_margin))
7746 && XINT (XCDR (Vtool_bar_button_margin)) > 0)
7747 vmargin += XFASTINT (XCDR (Vtool_bar_button_margin));
7750 if (auto_raise_tool_bar_buttons_p)
7752 /* Add a `:relief' property to the image spec if the item is
7753 selected. */
7754 if (selected_p)
7756 plist = Fplist_put (plist, QCrelief, make_number (-relief));
7757 hmargin -= relief;
7758 vmargin -= relief;
7761 else
7763 /* If image is selected, display it pressed, i.e. with a
7764 negative relief. If it's not selected, display it with a
7765 raised relief. */
7766 plist = Fplist_put (plist, QCrelief,
7767 (selected_p
7768 ? make_number (-relief)
7769 : make_number (relief)));
7770 hmargin -= relief;
7771 vmargin -= relief;
7774 /* Put a margin around the image. */
7775 if (hmargin || vmargin)
7777 if (hmargin == vmargin)
7778 plist = Fplist_put (plist, QCmargin, make_number (hmargin));
7779 else
7780 plist = Fplist_put (plist, QCmargin,
7781 Fcons (make_number (hmargin),
7782 make_number (vmargin)));
7785 /* If button is not enabled, and we don't have special images
7786 for the disabled state, make the image appear disabled by
7787 applying an appropriate algorithm to it. */
7788 if (!enabled_p && idx < 0)
7789 plist = Fplist_put (plist, QCconversion, Qdisabled);
7791 /* Put a `display' text property on the string for the image to
7792 display. Put a `menu-item' property on the string that gives
7793 the start of this item's properties in the tool-bar items
7794 vector. */
7795 image = Fcons (Qimage, plist);
7796 props = list4 (Qdisplay, image,
7797 Qmenu_item, make_number (i * TOOL_BAR_ITEM_NSLOTS));
7799 /* Let the last image hide all remaining spaces in the tool bar
7800 string. The string can be longer than needed when we reuse a
7801 previous string. */
7802 if (i + 1 == f->n_tool_bar_items)
7803 end = SCHARS (f->desired_tool_bar_string);
7804 else
7805 end = i + 1;
7806 Fadd_text_properties (make_number (i), make_number (end),
7807 props, f->desired_tool_bar_string);
7808 #undef PROP
7811 UNGCPRO;
7815 /* Display one line of the tool-bar of frame IT->f. */
7817 static void
7818 display_tool_bar_line (it)
7819 struct it *it;
7821 struct glyph_row *row = it->glyph_row;
7822 int max_x = it->last_visible_x;
7823 struct glyph *last;
7825 prepare_desired_row (row);
7826 row->y = it->current_y;
7828 /* Note that this isn't made use of if the face hasn't a box,
7829 so there's no need to check the face here. */
7830 it->start_of_box_run_p = 1;
7832 while (it->current_x < max_x)
7834 int x_before, x, n_glyphs_before, i, nglyphs;
7836 /* Get the next display element. */
7837 if (!get_next_display_element (it))
7838 break;
7840 /* Produce glyphs. */
7841 x_before = it->current_x;
7842 n_glyphs_before = it->glyph_row->used[TEXT_AREA];
7843 PRODUCE_GLYPHS (it);
7845 nglyphs = it->glyph_row->used[TEXT_AREA] - n_glyphs_before;
7846 i = 0;
7847 x = x_before;
7848 while (i < nglyphs)
7850 struct glyph *glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
7852 if (x + glyph->pixel_width > max_x)
7854 /* Glyph doesn't fit on line. */
7855 it->glyph_row->used[TEXT_AREA] = n_glyphs_before + i;
7856 it->current_x = x;
7857 goto out;
7860 ++it->hpos;
7861 x += glyph->pixel_width;
7862 ++i;
7865 /* Stop at line ends. */
7866 if (ITERATOR_AT_END_OF_LINE_P (it))
7867 break;
7869 set_iterator_to_next (it, 1);
7872 out:;
7874 row->displays_text_p = row->used[TEXT_AREA] != 0;
7875 extend_face_to_end_of_line (it);
7876 last = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1;
7877 last->right_box_line_p = 1;
7878 if (last == row->glyphs[TEXT_AREA])
7879 last->left_box_line_p = 1;
7880 compute_line_metrics (it);
7882 /* If line is empty, make it occupy the rest of the tool-bar. */
7883 if (!row->displays_text_p)
7885 row->height = row->phys_height = it->last_visible_y - row->y;
7886 row->ascent = row->phys_ascent = 0;
7889 row->full_width_p = 1;
7890 row->continued_p = 0;
7891 row->truncated_on_left_p = 0;
7892 row->truncated_on_right_p = 0;
7894 it->current_x = it->hpos = 0;
7895 it->current_y += row->height;
7896 ++it->vpos;
7897 ++it->glyph_row;
7901 /* Value is the number of screen lines needed to make all tool-bar
7902 items of frame F visible. */
7904 static int
7905 tool_bar_lines_needed (f)
7906 struct frame *f;
7908 struct window *w = XWINDOW (f->tool_bar_window);
7909 struct it it;
7911 /* Initialize an iterator for iteration over
7912 F->desired_tool_bar_string in the tool-bar window of frame F. */
7913 init_iterator (&it, w, -1, -1, w->desired_matrix->rows, TOOL_BAR_FACE_ID);
7914 it.first_visible_x = 0;
7915 it.last_visible_x = FRAME_WINDOW_WIDTH (f) * CANON_X_UNIT (f);
7916 reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
7918 while (!ITERATOR_AT_END_P (&it))
7920 it.glyph_row = w->desired_matrix->rows;
7921 clear_glyph_row (it.glyph_row);
7922 display_tool_bar_line (&it);
7925 return (it.current_y + CANON_Y_UNIT (f) - 1) / CANON_Y_UNIT (f);
7929 DEFUN ("tool-bar-lines-needed", Ftool_bar_lines_needed, Stool_bar_lines_needed,
7930 0, 1, 0,
7931 doc: /* Return the number of lines occupied by the tool bar of FRAME. */)
7932 (frame)
7933 Lisp_Object frame;
7935 struct frame *f;
7936 struct window *w;
7937 int nlines = 0;
7939 if (NILP (frame))
7940 frame = selected_frame;
7941 else
7942 CHECK_FRAME (frame);
7943 f = XFRAME (frame);
7945 if (WINDOWP (f->tool_bar_window)
7946 || (w = XWINDOW (f->tool_bar_window),
7947 XFASTINT (w->height) > 0))
7949 update_tool_bar (f, 1);
7950 if (f->n_tool_bar_items)
7952 build_desired_tool_bar_string (f);
7953 nlines = tool_bar_lines_needed (f);
7957 return make_number (nlines);
7961 /* Display the tool-bar of frame F. Value is non-zero if tool-bar's
7962 height should be changed. */
7964 static int
7965 redisplay_tool_bar (f)
7966 struct frame *f;
7968 struct window *w;
7969 struct it it;
7970 struct glyph_row *row;
7971 int change_height_p = 0;
7973 /* If frame hasn't a tool-bar window or if it is zero-height, don't
7974 do anything. This means you must start with tool-bar-lines
7975 non-zero to get the auto-sizing effect. Or in other words, you
7976 can turn off tool-bars by specifying tool-bar-lines zero. */
7977 if (!WINDOWP (f->tool_bar_window)
7978 || (w = XWINDOW (f->tool_bar_window),
7979 XFASTINT (w->height) == 0))
7980 return 0;
7982 /* Set up an iterator for the tool-bar window. */
7983 init_iterator (&it, w, -1, -1, w->desired_matrix->rows, TOOL_BAR_FACE_ID);
7984 it.first_visible_x = 0;
7985 it.last_visible_x = FRAME_WINDOW_WIDTH (f) * CANON_X_UNIT (f);
7986 row = it.glyph_row;
7988 /* Build a string that represents the contents of the tool-bar. */
7989 build_desired_tool_bar_string (f);
7990 reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
7992 /* Display as many lines as needed to display all tool-bar items. */
7993 while (it.current_y < it.last_visible_y)
7994 display_tool_bar_line (&it);
7996 /* It doesn't make much sense to try scrolling in the tool-bar
7997 window, so don't do it. */
7998 w->desired_matrix->no_scrolling_p = 1;
7999 w->must_be_updated_p = 1;
8001 if (auto_resize_tool_bars_p)
8003 int nlines;
8005 /* If we couldn't display everything, change the tool-bar's
8006 height. */
8007 if (IT_STRING_CHARPOS (it) < it.end_charpos)
8008 change_height_p = 1;
8010 /* If there are blank lines at the end, except for a partially
8011 visible blank line at the end that is smaller than
8012 CANON_Y_UNIT, change the tool-bar's height. */
8013 row = it.glyph_row - 1;
8014 if (!row->displays_text_p
8015 && row->height >= CANON_Y_UNIT (f))
8016 change_height_p = 1;
8018 /* If row displays tool-bar items, but is partially visible,
8019 change the tool-bar's height. */
8020 if (row->displays_text_p
8021 && MATRIX_ROW_BOTTOM_Y (row) > it.last_visible_y)
8022 change_height_p = 1;
8024 /* Resize windows as needed by changing the `tool-bar-lines'
8025 frame parameter. */
8026 if (change_height_p
8027 && (nlines = tool_bar_lines_needed (f),
8028 nlines != XFASTINT (w->height)))
8030 extern Lisp_Object Qtool_bar_lines;
8031 Lisp_Object frame;
8032 int old_height = XFASTINT (w->height);
8034 XSETFRAME (frame, f);
8035 clear_glyph_matrix (w->desired_matrix);
8036 Fmodify_frame_parameters (frame,
8037 Fcons (Fcons (Qtool_bar_lines,
8038 make_number (nlines)),
8039 Qnil));
8040 if (XFASTINT (w->height) != old_height)
8041 fonts_changed_p = 1;
8045 return change_height_p;
8049 /* Get information about the tool-bar item which is displayed in GLYPH
8050 on frame F. Return in *PROP_IDX the index where tool-bar item
8051 properties start in F->tool_bar_items. Value is zero if
8052 GLYPH doesn't display a tool-bar item. */
8055 tool_bar_item_info (f, glyph, prop_idx)
8056 struct frame *f;
8057 struct glyph *glyph;
8058 int *prop_idx;
8060 Lisp_Object prop;
8061 int success_p;
8062 int charpos;
8064 /* This function can be called asynchronously, which means we must
8065 exclude any possibility that Fget_text_property signals an
8066 error. */
8067 charpos = min (SCHARS (f->current_tool_bar_string), glyph->charpos);
8068 charpos = max (0, charpos);
8070 /* Get the text property `menu-item' at pos. The value of that
8071 property is the start index of this item's properties in
8072 F->tool_bar_items. */
8073 prop = Fget_text_property (make_number (charpos),
8074 Qmenu_item, f->current_tool_bar_string);
8075 if (INTEGERP (prop))
8077 *prop_idx = XINT (prop);
8078 success_p = 1;
8080 else
8081 success_p = 0;
8083 return success_p;
8086 #endif /* HAVE_WINDOW_SYSTEM */
8090 /************************************************************************
8091 Horizontal scrolling
8092 ************************************************************************/
8094 static int hscroll_window_tree P_ ((Lisp_Object));
8095 static int hscroll_windows P_ ((Lisp_Object));
8097 /* For all leaf windows in the window tree rooted at WINDOW, set their
8098 hscroll value so that PT is (i) visible in the window, and (ii) so
8099 that it is not within a certain margin at the window's left and
8100 right border. Value is non-zero if any window's hscroll has been
8101 changed. */
8103 static int
8104 hscroll_window_tree (window)
8105 Lisp_Object window;
8107 int hscrolled_p = 0;
8108 int hscroll_relative_p = FLOATP (Vhscroll_step);
8109 int hscroll_step_abs = 0;
8110 double hscroll_step_rel = 0;
8112 if (hscroll_relative_p)
8114 hscroll_step_rel = XFLOAT_DATA (Vhscroll_step);
8115 if (hscroll_step_rel < 0)
8117 hscroll_relative_p = 0;
8118 hscroll_step_abs = 0;
8121 else if (INTEGERP (Vhscroll_step))
8123 hscroll_step_abs = XINT (Vhscroll_step);
8124 if (hscroll_step_abs < 0)
8125 hscroll_step_abs = 0;
8127 else
8128 hscroll_step_abs = 0;
8130 while (WINDOWP (window))
8132 struct window *w = XWINDOW (window);
8134 if (WINDOWP (w->hchild))
8135 hscrolled_p |= hscroll_window_tree (w->hchild);
8136 else if (WINDOWP (w->vchild))
8137 hscrolled_p |= hscroll_window_tree (w->vchild);
8138 else if (w->cursor.vpos >= 0)
8140 int h_margin, text_area_x, text_area_y;
8141 int text_area_width, text_area_height;
8142 struct glyph_row *current_cursor_row
8143 = MATRIX_ROW (w->current_matrix, w->cursor.vpos);
8144 struct glyph_row *desired_cursor_row
8145 = MATRIX_ROW (w->desired_matrix, w->cursor.vpos);
8146 struct glyph_row *cursor_row
8147 = (desired_cursor_row->enabled_p
8148 ? desired_cursor_row
8149 : current_cursor_row);
8151 window_box (w, TEXT_AREA, &text_area_x, &text_area_y,
8152 &text_area_width, &text_area_height);
8154 /* Scroll when cursor is inside this scroll margin. */
8155 h_margin = hscroll_margin * CANON_X_UNIT (XFRAME (w->frame));
8157 if ((XFASTINT (w->hscroll)
8158 && w->cursor.x <= h_margin)
8159 || (cursor_row->enabled_p
8160 && cursor_row->truncated_on_right_p
8161 && (w->cursor.x >= text_area_width - h_margin)))
8163 struct it it;
8164 int hscroll;
8165 struct buffer *saved_current_buffer;
8166 int pt;
8167 int wanted_x;
8169 /* Find point in a display of infinite width. */
8170 saved_current_buffer = current_buffer;
8171 current_buffer = XBUFFER (w->buffer);
8173 if (w == XWINDOW (selected_window))
8174 pt = BUF_PT (current_buffer);
8175 else
8177 pt = marker_position (w->pointm);
8178 pt = max (BEGV, pt);
8179 pt = min (ZV, pt);
8182 /* Move iterator to pt starting at cursor_row->start in
8183 a line with infinite width. */
8184 init_to_row_start (&it, w, cursor_row);
8185 it.last_visible_x = INFINITY;
8186 move_it_in_display_line_to (&it, pt, -1, MOVE_TO_POS);
8187 current_buffer = saved_current_buffer;
8189 /* Position cursor in window. */
8190 if (!hscroll_relative_p && hscroll_step_abs == 0)
8191 hscroll = max (0, it.current_x - text_area_width / 2)
8192 / CANON_X_UNIT (it.f);
8193 else if (w->cursor.x >= text_area_width - h_margin)
8195 if (hscroll_relative_p)
8196 wanted_x = text_area_width * (1 - hscroll_step_rel)
8197 - h_margin;
8198 else
8199 wanted_x = text_area_width
8200 - hscroll_step_abs * CANON_X_UNIT (it.f)
8201 - h_margin;
8202 hscroll
8203 = max (0, it.current_x - wanted_x) / CANON_X_UNIT (it.f);
8205 else
8207 if (hscroll_relative_p)
8208 wanted_x = text_area_width * hscroll_step_rel
8209 + h_margin;
8210 else
8211 wanted_x = hscroll_step_abs * CANON_X_UNIT (it.f)
8212 + h_margin;
8213 hscroll
8214 = max (0, it.current_x - wanted_x) / CANON_X_UNIT (it.f);
8216 hscroll = max (hscroll, XFASTINT (w->min_hscroll));
8218 /* Don't call Fset_window_hscroll if value hasn't
8219 changed because it will prevent redisplay
8220 optimizations. */
8221 if (XFASTINT (w->hscroll) != hscroll)
8223 XBUFFER (w->buffer)->prevent_redisplay_optimizations_p = 1;
8224 w->hscroll = make_number (hscroll);
8225 hscrolled_p = 1;
8230 window = w->next;
8233 /* Value is non-zero if hscroll of any leaf window has been changed. */
8234 return hscrolled_p;
8238 /* Set hscroll so that cursor is visible and not inside horizontal
8239 scroll margins for all windows in the tree rooted at WINDOW. See
8240 also hscroll_window_tree above. Value is non-zero if any window's
8241 hscroll has been changed. If it has, desired matrices on the frame
8242 of WINDOW are cleared. */
8244 static int
8245 hscroll_windows (window)
8246 Lisp_Object window;
8248 int hscrolled_p;
8250 if (automatic_hscrolling_p)
8252 hscrolled_p = hscroll_window_tree (window);
8253 if (hscrolled_p)
8254 clear_desired_matrices (XFRAME (WINDOW_FRAME (XWINDOW (window))));
8256 else
8257 hscrolled_p = 0;
8258 return hscrolled_p;
8263 /************************************************************************
8264 Redisplay
8265 ************************************************************************/
8267 /* Variables holding some state of redisplay if GLYPH_DEBUG is defined
8268 to a non-zero value. This is sometimes handy to have in a debugger
8269 session. */
8271 #if GLYPH_DEBUG
8273 /* First and last unchanged row for try_window_id. */
8275 int debug_first_unchanged_at_end_vpos;
8276 int debug_last_unchanged_at_beg_vpos;
8278 /* Delta vpos and y. */
8280 int debug_dvpos, debug_dy;
8282 /* Delta in characters and bytes for try_window_id. */
8284 int debug_delta, debug_delta_bytes;
8286 /* Values of window_end_pos and window_end_vpos at the end of
8287 try_window_id. */
8289 EMACS_INT debug_end_pos, debug_end_vpos;
8291 /* Append a string to W->desired_matrix->method. FMT is a printf
8292 format string. A1...A9 are a supplement for a variable-length
8293 argument list. If trace_redisplay_p is non-zero also printf the
8294 resulting string to stderr. */
8296 static void
8297 debug_method_add (w, fmt, a1, a2, a3, a4, a5, a6, a7, a8, a9)
8298 struct window *w;
8299 char *fmt;
8300 int a1, a2, a3, a4, a5, a6, a7, a8, a9;
8302 char buffer[512];
8303 char *method = w->desired_matrix->method;
8304 int len = strlen (method);
8305 int size = sizeof w->desired_matrix->method;
8306 int remaining = size - len - 1;
8308 sprintf (buffer, fmt, a1, a2, a3, a4, a5, a6, a7, a8, a9);
8309 if (len && remaining)
8311 method[len] = '|';
8312 --remaining, ++len;
8315 strncpy (method + len, buffer, remaining);
8317 if (trace_redisplay_p)
8318 fprintf (stderr, "%p (%s): %s\n",
8320 ((BUFFERP (w->buffer)
8321 && STRINGP (XBUFFER (w->buffer)->name))
8322 ? (char *) SDATA (XBUFFER (w->buffer)->name)
8323 : "no buffer"),
8324 buffer);
8327 #endif /* GLYPH_DEBUG */
8330 /* Value is non-zero if all changes in window W, which displays
8331 current_buffer, are in the text between START and END. START is a
8332 buffer position, END is given as a distance from Z. Used in
8333 redisplay_internal for display optimization. */
8335 static INLINE int
8336 text_outside_line_unchanged_p (w, start, end)
8337 struct window *w;
8338 int start, end;
8340 int unchanged_p = 1;
8342 /* If text or overlays have changed, see where. */
8343 if (XFASTINT (w->last_modified) < MODIFF
8344 || XFASTINT (w->last_overlay_modified) < OVERLAY_MODIFF)
8346 /* Gap in the line? */
8347 if (GPT < start || Z - GPT < end)
8348 unchanged_p = 0;
8350 /* Changes start in front of the line, or end after it? */
8351 if (unchanged_p
8352 && (BEG_UNCHANGED < start - 1
8353 || END_UNCHANGED < end))
8354 unchanged_p = 0;
8356 /* If selective display, can't optimize if changes start at the
8357 beginning of the line. */
8358 if (unchanged_p
8359 && INTEGERP (current_buffer->selective_display)
8360 && XINT (current_buffer->selective_display) > 0
8361 && (BEG_UNCHANGED < start || GPT <= start))
8362 unchanged_p = 0;
8364 /* If there are overlays at the start or end of the line, these
8365 may have overlay strings with newlines in them. A change at
8366 START, for instance, may actually concern the display of such
8367 overlay strings as well, and they are displayed on different
8368 lines. So, quickly rule out this case. (For the future, it
8369 might be desirable to implement something more telling than
8370 just BEG/END_UNCHANGED.) */
8371 if (unchanged_p)
8373 if (BEG + BEG_UNCHANGED == start
8374 && overlay_touches_p (start))
8375 unchanged_p = 0;
8376 if (END_UNCHANGED == end
8377 && overlay_touches_p (Z - end))
8378 unchanged_p = 0;
8382 return unchanged_p;
8386 /* Do a frame update, taking possible shortcuts into account. This is
8387 the main external entry point for redisplay.
8389 If the last redisplay displayed an echo area message and that message
8390 is no longer requested, we clear the echo area or bring back the
8391 mini-buffer if that is in use. */
8393 void
8394 redisplay ()
8396 redisplay_internal (0);
8400 /* Return 1 if point moved out of or into a composition. Otherwise
8401 return 0. PREV_BUF and PREV_PT are the last point buffer and
8402 position. BUF and PT are the current point buffer and position. */
8405 check_point_in_composition (prev_buf, prev_pt, buf, pt)
8406 struct buffer *prev_buf, *buf;
8407 int prev_pt, pt;
8409 int start, end;
8410 Lisp_Object prop;
8411 Lisp_Object buffer;
8413 XSETBUFFER (buffer, buf);
8414 /* Check a composition at the last point if point moved within the
8415 same buffer. */
8416 if (prev_buf == buf)
8418 if (prev_pt == pt)
8419 /* Point didn't move. */
8420 return 0;
8422 if (prev_pt > BUF_BEGV (buf) && prev_pt < BUF_ZV (buf)
8423 && find_composition (prev_pt, -1, &start, &end, &prop, buffer)
8424 && COMPOSITION_VALID_P (start, end, prop)
8425 && start < prev_pt && end > prev_pt)
8426 /* The last point was within the composition. Return 1 iff
8427 point moved out of the composition. */
8428 return (pt <= start || pt >= end);
8431 /* Check a composition at the current point. */
8432 return (pt > BUF_BEGV (buf) && pt < BUF_ZV (buf)
8433 && find_composition (pt, -1, &start, &end, &prop, buffer)
8434 && COMPOSITION_VALID_P (start, end, prop)
8435 && start < pt && end > pt);
8439 /* Reconsider the setting of B->clip_changed which is displayed
8440 in window W. */
8442 static INLINE void
8443 reconsider_clip_changes (w, b)
8444 struct window *w;
8445 struct buffer *b;
8447 if (b->clip_changed
8448 && !NILP (w->window_end_valid)
8449 && w->current_matrix->buffer == b
8450 && w->current_matrix->zv == BUF_ZV (b)
8451 && w->current_matrix->begv == BUF_BEGV (b))
8452 b->clip_changed = 0;
8454 /* If display wasn't paused, and W is not a tool bar window, see if
8455 point has been moved into or out of a composition. In that case,
8456 we set b->clip_changed to 1 to force updating the screen. If
8457 b->clip_changed has already been set to 1, we can skip this
8458 check. */
8459 if (!b->clip_changed
8460 && BUFFERP (w->buffer) && !NILP (w->window_end_valid))
8462 int pt;
8464 if (w == XWINDOW (selected_window))
8465 pt = BUF_PT (current_buffer);
8466 else
8467 pt = marker_position (w->pointm);
8469 if ((w->current_matrix->buffer != XBUFFER (w->buffer)
8470 || pt != XINT (w->last_point))
8471 && check_point_in_composition (w->current_matrix->buffer,
8472 XINT (w->last_point),
8473 XBUFFER (w->buffer), pt))
8474 b->clip_changed = 1;
8478 #define STOP_POLLING \
8479 do { if (! polling_stopped_here) stop_polling (); \
8480 polling_stopped_here = 1; } while (0)
8482 #define RESUME_POLLING \
8483 do { if (polling_stopped_here) start_polling (); \
8484 polling_stopped_here = 0; } while (0)
8487 /* If PRESERVE_ECHO_AREA is nonzero, it means this redisplay is not in
8488 response to any user action; therefore, we should preserve the echo
8489 area. (Actually, our caller does that job.) Perhaps in the future
8490 avoid recentering windows if it is not necessary; currently that
8491 causes some problems. */
8493 static void
8494 redisplay_internal (preserve_echo_area)
8495 int preserve_echo_area;
8497 struct window *w = XWINDOW (selected_window);
8498 struct frame *f = XFRAME (w->frame);
8499 int pause;
8500 int must_finish = 0;
8501 struct text_pos tlbufpos, tlendpos;
8502 int number_of_visible_frames;
8503 int count;
8504 struct frame *sf = SELECTED_FRAME ();
8505 int polling_stopped_here = 0;
8507 /* Non-zero means redisplay has to consider all windows on all
8508 frames. Zero means, only selected_window is considered. */
8509 int consider_all_windows_p;
8511 TRACE ((stderr, "redisplay_internal %d\n", redisplaying_p));
8513 /* No redisplay if running in batch mode or frame is not yet fully
8514 initialized, or redisplay is explicitly turned off by setting
8515 Vinhibit_redisplay. */
8516 if (noninteractive
8517 || !NILP (Vinhibit_redisplay)
8518 || !f->glyphs_initialized_p)
8519 return;
8521 /* The flag redisplay_performed_directly_p is set by
8522 direct_output_for_insert when it already did the whole screen
8523 update necessary. */
8524 if (redisplay_performed_directly_p)
8526 redisplay_performed_directly_p = 0;
8527 if (!hscroll_windows (selected_window))
8528 return;
8531 #ifdef USE_X_TOOLKIT
8532 if (popup_activated ())
8533 return;
8534 #endif
8536 /* I don't think this happens but let's be paranoid. */
8537 if (redisplaying_p)
8538 return;
8540 /* Record a function that resets redisplaying_p to its old value
8541 when we leave this function. */
8542 count = SPECPDL_INDEX ();
8543 record_unwind_protect (unwind_redisplay, make_number (redisplaying_p));
8544 ++redisplaying_p;
8545 specbind (Qinhibit_free_realized_faces, Qnil);
8547 retry:
8548 pause = 0;
8549 reconsider_clip_changes (w, current_buffer);
8551 /* If new fonts have been loaded that make a glyph matrix adjustment
8552 necessary, do it. */
8553 if (fonts_changed_p)
8555 adjust_glyphs (NULL);
8556 ++windows_or_buffers_changed;
8557 fonts_changed_p = 0;
8560 /* If face_change_count is non-zero, init_iterator will free all
8561 realized faces, which includes the faces referenced from current
8562 matrices. So, we can't reuse current matrices in this case. */
8563 if (face_change_count)
8564 ++windows_or_buffers_changed;
8566 if (! FRAME_WINDOW_P (sf)
8567 && previous_terminal_frame != sf)
8569 /* Since frames on an ASCII terminal share the same display
8570 area, displaying a different frame means redisplay the whole
8571 thing. */
8572 windows_or_buffers_changed++;
8573 SET_FRAME_GARBAGED (sf);
8574 XSETFRAME (Vterminal_frame, sf);
8576 previous_terminal_frame = sf;
8578 /* Set the visible flags for all frames. Do this before checking
8579 for resized or garbaged frames; they want to know if their frames
8580 are visible. See the comment in frame.h for
8581 FRAME_SAMPLE_VISIBILITY. */
8583 Lisp_Object tail, frame;
8585 number_of_visible_frames = 0;
8587 FOR_EACH_FRAME (tail, frame)
8589 struct frame *f = XFRAME (frame);
8591 FRAME_SAMPLE_VISIBILITY (f);
8592 if (FRAME_VISIBLE_P (f))
8593 ++number_of_visible_frames;
8594 clear_desired_matrices (f);
8598 /* Notice any pending interrupt request to change frame size. */
8599 do_pending_window_change (1);
8601 /* Clear frames marked as garbaged. */
8602 if (frame_garbaged)
8603 clear_garbaged_frames ();
8605 /* Build menubar and tool-bar items. */
8606 prepare_menu_bars ();
8608 if (windows_or_buffers_changed)
8609 update_mode_lines++;
8611 /* Detect case that we need to write or remove a star in the mode line. */
8612 if ((SAVE_MODIFF < MODIFF) != !NILP (w->last_had_star))
8614 w->update_mode_line = Qt;
8615 if (buffer_shared > 1)
8616 update_mode_lines++;
8619 /* If %c is in the mode line, update it if needed. */
8620 if (!NILP (w->column_number_displayed)
8621 /* This alternative quickly identifies a common case
8622 where no change is needed. */
8623 && !(PT == XFASTINT (w->last_point)
8624 && XFASTINT (w->last_modified) >= MODIFF
8625 && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF)
8626 && (XFASTINT (w->column_number_displayed)
8627 != (int) current_column ())) /* iftc */
8628 w->update_mode_line = Qt;
8630 FRAME_SCROLL_BOTTOM_VPOS (XFRAME (w->frame)) = -1;
8632 /* The variable buffer_shared is set in redisplay_window and
8633 indicates that we redisplay a buffer in different windows. See
8634 there. */
8635 consider_all_windows_p = (update_mode_lines || buffer_shared > 1
8636 || cursor_type_changed);
8638 /* If specs for an arrow have changed, do thorough redisplay
8639 to ensure we remove any arrow that should no longer exist. */
8640 if (! EQ (COERCE_MARKER (Voverlay_arrow_position), last_arrow_position)
8641 || ! EQ (Voverlay_arrow_string, last_arrow_string))
8642 consider_all_windows_p = windows_or_buffers_changed = 1;
8644 /* Normally the message* functions will have already displayed and
8645 updated the echo area, but the frame may have been trashed, or
8646 the update may have been preempted, so display the echo area
8647 again here. Checking message_cleared_p captures the case that
8648 the echo area should be cleared. */
8649 if ((!NILP (echo_area_buffer[0]) && !display_last_displayed_message_p)
8650 || (!NILP (echo_area_buffer[1]) && display_last_displayed_message_p)
8651 || (message_cleared_p
8652 && minibuf_level == 0
8653 /* If the mini-window is currently selected, this means the
8654 echo-area doesn't show through. */
8655 && !MINI_WINDOW_P (XWINDOW (selected_window))))
8657 int window_height_changed_p = echo_area_display (0);
8658 must_finish = 1;
8660 /* If we don't display the current message, don't clear the
8661 message_cleared_p flag, because, if we did, we wouldn't clear
8662 the echo area in the next redisplay which doesn't preserve
8663 the echo area. */
8664 if (!display_last_displayed_message_p)
8665 message_cleared_p = 0;
8667 if (fonts_changed_p)
8668 goto retry;
8669 else if (window_height_changed_p)
8671 consider_all_windows_p = 1;
8672 ++update_mode_lines;
8673 ++windows_or_buffers_changed;
8675 /* If window configuration was changed, frames may have been
8676 marked garbaged. Clear them or we will experience
8677 surprises wrt scrolling. */
8678 if (frame_garbaged)
8679 clear_garbaged_frames ();
8682 else if (EQ (selected_window, minibuf_window)
8683 && (current_buffer->clip_changed
8684 || XFASTINT (w->last_modified) < MODIFF
8685 || XFASTINT (w->last_overlay_modified) < OVERLAY_MODIFF)
8686 && resize_mini_window (w, 0))
8688 /* Resized active mini-window to fit the size of what it is
8689 showing if its contents might have changed. */
8690 must_finish = 1;
8691 consider_all_windows_p = 1;
8692 ++windows_or_buffers_changed;
8693 ++update_mode_lines;
8695 /* If window configuration was changed, frames may have been
8696 marked garbaged. Clear them or we will experience
8697 surprises wrt scrolling. */
8698 if (frame_garbaged)
8699 clear_garbaged_frames ();
8703 /* If showing the region, and mark has changed, we must redisplay
8704 the whole window. The assignment to this_line_start_pos prevents
8705 the optimization directly below this if-statement. */
8706 if (((!NILP (Vtransient_mark_mode)
8707 && !NILP (XBUFFER (w->buffer)->mark_active))
8708 != !NILP (w->region_showing))
8709 || (!NILP (w->region_showing)
8710 && !EQ (w->region_showing,
8711 Fmarker_position (XBUFFER (w->buffer)->mark))))
8712 CHARPOS (this_line_start_pos) = 0;
8714 /* Optimize the case that only the line containing the cursor in the
8715 selected window has changed. Variables starting with this_ are
8716 set in display_line and record information about the line
8717 containing the cursor. */
8718 tlbufpos = this_line_start_pos;
8719 tlendpos = this_line_end_pos;
8720 if (!consider_all_windows_p
8721 && CHARPOS (tlbufpos) > 0
8722 && NILP (w->update_mode_line)
8723 && !current_buffer->clip_changed
8724 && !current_buffer->prevent_redisplay_optimizations_p
8725 && FRAME_VISIBLE_P (XFRAME (w->frame))
8726 && !FRAME_OBSCURED_P (XFRAME (w->frame))
8727 /* Make sure recorded data applies to current buffer, etc. */
8728 && this_line_buffer == current_buffer
8729 && current_buffer == XBUFFER (w->buffer)
8730 && NILP (w->force_start)
8731 && NILP (w->optional_new_start)
8732 /* Point must be on the line that we have info recorded about. */
8733 && PT >= CHARPOS (tlbufpos)
8734 && PT <= Z - CHARPOS (tlendpos)
8735 /* All text outside that line, including its final newline,
8736 must be unchanged */
8737 && text_outside_line_unchanged_p (w, CHARPOS (tlbufpos),
8738 CHARPOS (tlendpos)))
8740 if (CHARPOS (tlbufpos) > BEGV
8741 && FETCH_BYTE (BYTEPOS (tlbufpos) - 1) != '\n'
8742 && (CHARPOS (tlbufpos) == ZV
8743 || FETCH_BYTE (BYTEPOS (tlbufpos)) == '\n'))
8744 /* Former continuation line has disappeared by becoming empty */
8745 goto cancel;
8746 else if (XFASTINT (w->last_modified) < MODIFF
8747 || XFASTINT (w->last_overlay_modified) < OVERLAY_MODIFF
8748 || MINI_WINDOW_P (w))
8750 /* We have to handle the case of continuation around a
8751 wide-column character (See the comment in indent.c around
8752 line 885).
8754 For instance, in the following case:
8756 -------- Insert --------
8757 K_A_N_\\ `a' K_A_N_a\ `X_' are wide-column chars.
8758 J_I_ ==> J_I_ `^^' are cursors.
8759 ^^ ^^
8760 -------- --------
8762 As we have to redraw the line above, we should goto cancel. */
8764 struct it it;
8765 int line_height_before = this_line_pixel_height;
8767 /* Note that start_display will handle the case that the
8768 line starting at tlbufpos is a continuation lines. */
8769 start_display (&it, w, tlbufpos);
8771 /* Implementation note: It this still necessary? */
8772 if (it.current_x != this_line_start_x)
8773 goto cancel;
8775 TRACE ((stderr, "trying display optimization 1\n"));
8776 w->cursor.vpos = -1;
8777 overlay_arrow_seen = 0;
8778 it.vpos = this_line_vpos;
8779 it.current_y = this_line_y;
8780 it.glyph_row = MATRIX_ROW (w->desired_matrix, this_line_vpos);
8781 display_line (&it);
8783 /* If line contains point, is not continued,
8784 and ends at same distance from eob as before, we win */
8785 if (w->cursor.vpos >= 0
8786 /* Line is not continued, otherwise this_line_start_pos
8787 would have been set to 0 in display_line. */
8788 && CHARPOS (this_line_start_pos)
8789 /* Line ends as before. */
8790 && CHARPOS (this_line_end_pos) == CHARPOS (tlendpos)
8791 /* Line has same height as before. Otherwise other lines
8792 would have to be shifted up or down. */
8793 && this_line_pixel_height == line_height_before)
8795 /* If this is not the window's last line, we must adjust
8796 the charstarts of the lines below. */
8797 if (it.current_y < it.last_visible_y)
8799 struct glyph_row *row
8800 = MATRIX_ROW (w->current_matrix, this_line_vpos + 1);
8801 int delta, delta_bytes;
8803 if (Z - CHARPOS (tlendpos) == ZV)
8805 /* This line ends at end of (accessible part of)
8806 buffer. There is no newline to count. */
8807 delta = (Z
8808 - CHARPOS (tlendpos)
8809 - MATRIX_ROW_START_CHARPOS (row));
8810 delta_bytes = (Z_BYTE
8811 - BYTEPOS (tlendpos)
8812 - MATRIX_ROW_START_BYTEPOS (row));
8814 else
8816 /* This line ends in a newline. Must take
8817 account of the newline and the rest of the
8818 text that follows. */
8819 delta = (Z
8820 - CHARPOS (tlendpos)
8821 - MATRIX_ROW_START_CHARPOS (row));
8822 delta_bytes = (Z_BYTE
8823 - BYTEPOS (tlendpos)
8824 - MATRIX_ROW_START_BYTEPOS (row));
8827 increment_matrix_positions (w->current_matrix,
8828 this_line_vpos + 1,
8829 w->current_matrix->nrows,
8830 delta, delta_bytes);
8833 /* If this row displays text now but previously didn't,
8834 or vice versa, w->window_end_vpos may have to be
8835 adjusted. */
8836 if ((it.glyph_row - 1)->displays_text_p)
8838 if (XFASTINT (w->window_end_vpos) < this_line_vpos)
8839 XSETINT (w->window_end_vpos, this_line_vpos);
8841 else if (XFASTINT (w->window_end_vpos) == this_line_vpos
8842 && this_line_vpos > 0)
8843 XSETINT (w->window_end_vpos, this_line_vpos - 1);
8844 w->window_end_valid = Qnil;
8846 /* Update hint: No need to try to scroll in update_window. */
8847 w->desired_matrix->no_scrolling_p = 1;
8849 #if GLYPH_DEBUG
8850 *w->desired_matrix->method = 0;
8851 debug_method_add (w, "optimization 1");
8852 #endif
8853 goto update;
8855 else
8856 goto cancel;
8858 else if (/* Cursor position hasn't changed. */
8859 PT == XFASTINT (w->last_point)
8860 /* Make sure the cursor was last displayed
8861 in this window. Otherwise we have to reposition it. */
8862 && 0 <= w->cursor.vpos
8863 && XINT (w->height) > w->cursor.vpos)
8865 if (!must_finish)
8867 do_pending_window_change (1);
8869 /* We used to always goto end_of_redisplay here, but this
8870 isn't enough if we have a blinking cursor. */
8871 if (w->cursor_off_p == w->last_cursor_off_p)
8872 goto end_of_redisplay;
8874 goto update;
8876 /* If highlighting the region, or if the cursor is in the echo area,
8877 then we can't just move the cursor. */
8878 else if (! (!NILP (Vtransient_mark_mode)
8879 && !NILP (current_buffer->mark_active))
8880 && (EQ (selected_window, current_buffer->last_selected_window)
8881 || highlight_nonselected_windows)
8882 && NILP (w->region_showing)
8883 && NILP (Vshow_trailing_whitespace)
8884 && !cursor_in_echo_area)
8886 struct it it;
8887 struct glyph_row *row;
8889 /* Skip from tlbufpos to PT and see where it is. Note that
8890 PT may be in invisible text. If so, we will end at the
8891 next visible position. */
8892 init_iterator (&it, w, CHARPOS (tlbufpos), BYTEPOS (tlbufpos),
8893 NULL, DEFAULT_FACE_ID);
8894 it.current_x = this_line_start_x;
8895 it.current_y = this_line_y;
8896 it.vpos = this_line_vpos;
8898 /* The call to move_it_to stops in front of PT, but
8899 moves over before-strings. */
8900 move_it_to (&it, PT, -1, -1, -1, MOVE_TO_POS);
8902 if (it.vpos == this_line_vpos
8903 && (row = MATRIX_ROW (w->current_matrix, this_line_vpos),
8904 row->enabled_p))
8906 xassert (this_line_vpos == it.vpos);
8907 xassert (this_line_y == it.current_y);
8908 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
8909 #if GLYPH_DEBUG
8910 *w->desired_matrix->method = 0;
8911 debug_method_add (w, "optimization 3");
8912 #endif
8913 goto update;
8915 else
8916 goto cancel;
8919 cancel:
8920 /* Text changed drastically or point moved off of line. */
8921 SET_MATRIX_ROW_ENABLED_P (w->desired_matrix, this_line_vpos, 0);
8924 CHARPOS (this_line_start_pos) = 0;
8925 consider_all_windows_p |= buffer_shared > 1;
8926 ++clear_face_cache_count;
8929 /* Build desired matrices, and update the display. If
8930 consider_all_windows_p is non-zero, do it for all windows on all
8931 frames. Otherwise do it for selected_window, only. */
8933 if (consider_all_windows_p)
8935 Lisp_Object tail, frame;
8936 int i, n = 0, size = 50;
8937 struct frame **updated
8938 = (struct frame **) alloca (size * sizeof *updated);
8940 /* Clear the face cache eventually. */
8941 if (clear_face_cache_count > CLEAR_FACE_CACHE_COUNT)
8943 clear_face_cache (0);
8944 clear_face_cache_count = 0;
8947 /* Recompute # windows showing selected buffer. This will be
8948 incremented each time such a window is displayed. */
8949 buffer_shared = 0;
8951 FOR_EACH_FRAME (tail, frame)
8953 struct frame *f = XFRAME (frame);
8955 if (FRAME_WINDOW_P (f) || f == sf)
8957 #ifdef HAVE_WINDOW_SYSTEM
8958 if (clear_face_cache_count % 50 == 0
8959 && FRAME_WINDOW_P (f))
8960 clear_image_cache (f, 0);
8961 #endif /* HAVE_WINDOW_SYSTEM */
8963 /* Mark all the scroll bars to be removed; we'll redeem
8964 the ones we want when we redisplay their windows. */
8965 if (condemn_scroll_bars_hook)
8966 condemn_scroll_bars_hook (f);
8968 if (FRAME_VISIBLE_P (f) && !FRAME_OBSCURED_P (f))
8969 redisplay_windows (FRAME_ROOT_WINDOW (f));
8971 /* Any scroll bars which redisplay_windows should have
8972 nuked should now go away. */
8973 if (judge_scroll_bars_hook)
8974 judge_scroll_bars_hook (f);
8976 /* If fonts changed, display again. */
8977 /* ??? rms: I suspect it is a mistake to jump all the way
8978 back to retry here. It should just retry this frame. */
8979 if (fonts_changed_p)
8980 goto retry;
8982 if (FRAME_VISIBLE_P (f) && !FRAME_OBSCURED_P (f))
8984 /* See if we have to hscroll. */
8985 if (hscroll_windows (f->root_window))
8986 goto retry;
8988 /* Prevent various kinds of signals during display
8989 update. stdio is not robust about handling
8990 signals, which can cause an apparent I/O
8991 error. */
8992 if (interrupt_input)
8993 unrequest_sigio ();
8994 STOP_POLLING;
8996 /* Update the display. */
8997 set_window_update_flags (XWINDOW (f->root_window), 1);
8998 pause |= update_frame (f, 0, 0);
8999 if (pause)
9000 break;
9002 if (n == size)
9004 int nbytes = size * sizeof *updated;
9005 struct frame **p = (struct frame **) alloca (2 * nbytes);
9006 bcopy (updated, p, nbytes);
9007 size *= 2;
9010 updated[n++] = f;
9015 /* Do the mark_window_display_accurate after all windows have
9016 been redisplayed because this call resets flags in buffers
9017 which are needed for proper redisplay. */
9018 for (i = 0; i < n; ++i)
9020 struct frame *f = updated[i];
9021 mark_window_display_accurate (f->root_window, 1);
9022 if (frame_up_to_date_hook)
9023 frame_up_to_date_hook (f);
9026 else if (FRAME_VISIBLE_P (sf) && !FRAME_OBSCURED_P (sf))
9028 Lisp_Object mini_window;
9029 struct frame *mini_frame;
9031 displayed_buffer = XBUFFER (XWINDOW (selected_window)->buffer);
9032 /* Use list_of_error, not Qerror, so that
9033 we catch only errors and don't run the debugger. */
9034 internal_condition_case_1 (redisplay_window_1, selected_window,
9035 list_of_error,
9036 redisplay_window_error);
9038 /* Compare desired and current matrices, perform output. */
9040 update:
9041 /* If fonts changed, display again. */
9042 if (fonts_changed_p)
9043 goto retry;
9045 /* Prevent various kinds of signals during display update.
9046 stdio is not robust about handling signals,
9047 which can cause an apparent I/O error. */
9048 if (interrupt_input)
9049 unrequest_sigio ();
9050 STOP_POLLING;
9052 if (FRAME_VISIBLE_P (sf) && !FRAME_OBSCURED_P (sf))
9054 if (hscroll_windows (selected_window))
9055 goto retry;
9057 XWINDOW (selected_window)->must_be_updated_p = 1;
9058 pause = update_frame (sf, 0, 0);
9061 /* We may have called echo_area_display at the top of this
9062 function. If the echo area is on another frame, that may
9063 have put text on a frame other than the selected one, so the
9064 above call to update_frame would not have caught it. Catch
9065 it here. */
9066 mini_window = FRAME_MINIBUF_WINDOW (sf);
9067 mini_frame = XFRAME (WINDOW_FRAME (XWINDOW (mini_window)));
9069 if (mini_frame != sf && FRAME_WINDOW_P (mini_frame))
9071 XWINDOW (mini_window)->must_be_updated_p = 1;
9072 pause |= update_frame (mini_frame, 0, 0);
9073 if (!pause && hscroll_windows (mini_window))
9074 goto retry;
9078 /* If display was paused because of pending input, make sure we do a
9079 thorough update the next time. */
9080 if (pause)
9082 /* Prevent the optimization at the beginning of
9083 redisplay_internal that tries a single-line update of the
9084 line containing the cursor in the selected window. */
9085 CHARPOS (this_line_start_pos) = 0;
9087 /* Let the overlay arrow be updated the next time. */
9088 if (!NILP (last_arrow_position))
9090 last_arrow_position = Qt;
9091 last_arrow_string = Qt;
9094 /* If we pause after scrolling, some rows in the current
9095 matrices of some windows are not valid. */
9096 if (!WINDOW_FULL_WIDTH_P (w)
9097 && !FRAME_WINDOW_P (XFRAME (w->frame)))
9098 update_mode_lines = 1;
9100 else
9102 if (!consider_all_windows_p)
9104 /* This has already been done above if
9105 consider_all_windows_p is set. */
9106 mark_window_display_accurate_1 (w, 1);
9108 last_arrow_position = COERCE_MARKER (Voverlay_arrow_position);
9109 last_arrow_string = Voverlay_arrow_string;
9111 if (frame_up_to_date_hook != 0)
9112 frame_up_to_date_hook (sf);
9115 update_mode_lines = 0;
9116 windows_or_buffers_changed = 0;
9117 cursor_type_changed = 0;
9120 /* Start SIGIO interrupts coming again. Having them off during the
9121 code above makes it less likely one will discard output, but not
9122 impossible, since there might be stuff in the system buffer here.
9123 But it is much hairier to try to do anything about that. */
9124 if (interrupt_input)
9125 request_sigio ();
9126 RESUME_POLLING;
9128 /* If a frame has become visible which was not before, redisplay
9129 again, so that we display it. Expose events for such a frame
9130 (which it gets when becoming visible) don't call the parts of
9131 redisplay constructing glyphs, so simply exposing a frame won't
9132 display anything in this case. So, we have to display these
9133 frames here explicitly. */
9134 if (!pause)
9136 Lisp_Object tail, frame;
9137 int new_count = 0;
9139 FOR_EACH_FRAME (tail, frame)
9141 int this_is_visible = 0;
9143 if (XFRAME (frame)->visible)
9144 this_is_visible = 1;
9145 FRAME_SAMPLE_VISIBILITY (XFRAME (frame));
9146 if (XFRAME (frame)->visible)
9147 this_is_visible = 1;
9149 if (this_is_visible)
9150 new_count++;
9153 if (new_count != number_of_visible_frames)
9154 windows_or_buffers_changed++;
9157 /* Change frame size now if a change is pending. */
9158 do_pending_window_change (1);
9160 /* If we just did a pending size change, or have additional
9161 visible frames, redisplay again. */
9162 if (windows_or_buffers_changed && !pause)
9163 goto retry;
9165 end_of_redisplay:
9166 unbind_to (count, Qnil);
9167 RESUME_POLLING;
9171 /* Redisplay, but leave alone any recent echo area message unless
9172 another message has been requested in its place.
9174 This is useful in situations where you need to redisplay but no
9175 user action has occurred, making it inappropriate for the message
9176 area to be cleared. See tracking_off and
9177 wait_reading_process_input for examples of these situations.
9179 FROM_WHERE is an integer saying from where this function was
9180 called. This is useful for debugging. */
9182 void
9183 redisplay_preserve_echo_area (from_where)
9184 int from_where;
9186 TRACE ((stderr, "redisplay_preserve_echo_area (%d)\n", from_where));
9188 if (!NILP (echo_area_buffer[1]))
9190 /* We have a previously displayed message, but no current
9191 message. Redisplay the previous message. */
9192 display_last_displayed_message_p = 1;
9193 redisplay_internal (1);
9194 display_last_displayed_message_p = 0;
9196 else
9197 redisplay_internal (1);
9201 /* Function registered with record_unwind_protect in
9202 redisplay_internal. Reset redisplaying_p to the value it had
9203 before redisplay_internal was called, and clear
9204 prevent_freeing_realized_faces_p. */
9206 static Lisp_Object
9207 unwind_redisplay (old_redisplaying_p)
9208 Lisp_Object old_redisplaying_p;
9210 redisplaying_p = XFASTINT (old_redisplaying_p);
9211 return Qnil;
9215 /* Mark the display of window W as accurate or inaccurate. If
9216 ACCURATE_P is non-zero mark display of W as accurate. If
9217 ACCURATE_P is zero, arrange for W to be redisplayed the next time
9218 redisplay_internal is called. */
9220 static void
9221 mark_window_display_accurate_1 (w, accurate_p)
9222 struct window *w;
9223 int accurate_p;
9225 if (BUFFERP (w->buffer))
9227 struct buffer *b = XBUFFER (w->buffer);
9229 w->last_modified
9230 = make_number (accurate_p ? BUF_MODIFF (b) : 0);
9231 w->last_overlay_modified
9232 = make_number (accurate_p ? BUF_OVERLAY_MODIFF (b) : 0);
9233 w->last_had_star
9234 = BUF_MODIFF (b) > BUF_SAVE_MODIFF (b) ? Qt : Qnil;
9236 if (accurate_p)
9238 b->clip_changed = 0;
9239 b->prevent_redisplay_optimizations_p = 0;
9241 BUF_UNCHANGED_MODIFIED (b) = BUF_MODIFF (b);
9242 BUF_OVERLAY_UNCHANGED_MODIFIED (b) = BUF_OVERLAY_MODIFF (b);
9243 BUF_BEG_UNCHANGED (b) = BUF_GPT (b) - BUF_BEG (b);
9244 BUF_END_UNCHANGED (b) = BUF_Z (b) - BUF_GPT (b);
9246 w->current_matrix->buffer = b;
9247 w->current_matrix->begv = BUF_BEGV (b);
9248 w->current_matrix->zv = BUF_ZV (b);
9250 w->last_cursor = w->cursor;
9251 w->last_cursor_off_p = w->cursor_off_p;
9253 if (w == XWINDOW (selected_window))
9254 w->last_point = make_number (BUF_PT (b));
9255 else
9256 w->last_point = make_number (XMARKER (w->pointm)->charpos);
9260 if (accurate_p)
9262 w->window_end_valid = w->buffer;
9263 #if 0 /* This is incorrect with variable-height lines. */
9264 xassert (XINT (w->window_end_vpos)
9265 < (XINT (w->height)
9266 - (WINDOW_WANTS_MODELINE_P (w) ? 1 : 0)));
9267 #endif
9268 w->update_mode_line = Qnil;
9273 /* Mark the display of windows in the window tree rooted at WINDOW as
9274 accurate or inaccurate. If ACCURATE_P is non-zero mark display of
9275 windows as accurate. If ACCURATE_P is zero, arrange for windows to
9276 be redisplayed the next time redisplay_internal is called. */
9278 void
9279 mark_window_display_accurate (window, accurate_p)
9280 Lisp_Object window;
9281 int accurate_p;
9283 struct window *w;
9285 for (; !NILP (window); window = w->next)
9287 w = XWINDOW (window);
9288 mark_window_display_accurate_1 (w, accurate_p);
9290 if (!NILP (w->vchild))
9291 mark_window_display_accurate (w->vchild, accurate_p);
9292 if (!NILP (w->hchild))
9293 mark_window_display_accurate (w->hchild, accurate_p);
9296 if (accurate_p)
9298 last_arrow_position = COERCE_MARKER (Voverlay_arrow_position);
9299 last_arrow_string = Voverlay_arrow_string;
9301 else
9303 /* Force a thorough redisplay the next time by setting
9304 last_arrow_position and last_arrow_string to t, which is
9305 unequal to any useful value of Voverlay_arrow_... */
9306 last_arrow_position = Qt;
9307 last_arrow_string = Qt;
9312 /* Return value in display table DP (Lisp_Char_Table *) for character
9313 C. Since a display table doesn't have any parent, we don't have to
9314 follow parent. Do not call this function directly but use the
9315 macro DISP_CHAR_VECTOR. */
9317 Lisp_Object
9318 disp_char_vector (dp, c)
9319 struct Lisp_Char_Table *dp;
9320 int c;
9322 int code[4], i;
9323 Lisp_Object val;
9325 if (SINGLE_BYTE_CHAR_P (c))
9326 return (dp->contents[c]);
9328 SPLIT_CHAR (c, code[0], code[1], code[2]);
9329 if (code[1] < 32)
9330 code[1] = -1;
9331 else if (code[2] < 32)
9332 code[2] = -1;
9334 /* Here, the possible range of code[0] (== charset ID) is
9335 128..max_charset. Since the top level char table contains data
9336 for multibyte characters after 256th element, we must increment
9337 code[0] by 128 to get a correct index. */
9338 code[0] += 128;
9339 code[3] = -1; /* anchor */
9341 for (i = 0; code[i] >= 0; i++, dp = XCHAR_TABLE (val))
9343 val = dp->contents[code[i]];
9344 if (!SUB_CHAR_TABLE_P (val))
9345 return (NILP (val) ? dp->defalt : val);
9348 /* Here, val is a sub char table. We return the default value of
9349 it. */
9350 return (dp->defalt);
9355 /***********************************************************************
9356 Window Redisplay
9357 ***********************************************************************/
9359 /* Redisplay all leaf windows in the window tree rooted at WINDOW. */
9361 static void
9362 redisplay_windows (window)
9363 Lisp_Object window;
9365 while (!NILP (window))
9367 struct window *w = XWINDOW (window);
9369 if (!NILP (w->hchild))
9370 redisplay_windows (w->hchild);
9371 else if (!NILP (w->vchild))
9372 redisplay_windows (w->vchild);
9373 else
9375 displayed_buffer = XBUFFER (w->buffer);
9376 /* Use list_of_error, not Qerror, so that
9377 we catch only errors and don't run the debugger. */
9378 internal_condition_case_1 (redisplay_window_0, window,
9379 list_of_error,
9380 redisplay_window_error);
9383 window = w->next;
9387 static Lisp_Object
9388 redisplay_window_error ()
9390 displayed_buffer->display_error_modiff = BUF_MODIFF (displayed_buffer);
9391 return Qnil;
9394 static Lisp_Object
9395 redisplay_window_0 (window)
9396 Lisp_Object window;
9398 if (displayed_buffer->display_error_modiff < BUF_MODIFF (displayed_buffer))
9399 redisplay_window (window, 0);
9400 return Qnil;
9403 static Lisp_Object
9404 redisplay_window_1 (window)
9405 Lisp_Object window;
9407 if (displayed_buffer->display_error_modiff < BUF_MODIFF (displayed_buffer))
9408 redisplay_window (window, 1);
9409 return Qnil;
9412 /* Set cursor position of W. PT is assumed to be displayed in ROW.
9413 DELTA is the number of bytes by which positions recorded in ROW
9414 differ from current buffer positions. */
9416 void
9417 set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
9418 struct window *w;
9419 struct glyph_row *row;
9420 struct glyph_matrix *matrix;
9421 int delta, delta_bytes, dy, dvpos;
9423 struct glyph *glyph = row->glyphs[TEXT_AREA];
9424 struct glyph *end = glyph + row->used[TEXT_AREA];
9425 int x = row->x;
9426 int pt_old = PT - delta;
9428 /* Skip over glyphs not having an object at the start of the row.
9429 These are special glyphs like truncation marks on terminal
9430 frames. */
9431 if (row->displays_text_p)
9432 while (glyph < end
9433 && INTEGERP (glyph->object)
9434 && glyph->charpos < 0)
9436 x += glyph->pixel_width;
9437 ++glyph;
9440 while (glyph < end
9441 && !INTEGERP (glyph->object)
9442 && (!BUFFERP (glyph->object)
9443 || glyph->charpos < pt_old))
9445 x += glyph->pixel_width;
9446 ++glyph;
9449 w->cursor.hpos = glyph - row->glyphs[TEXT_AREA];
9450 w->cursor.x = x;
9451 w->cursor.vpos = MATRIX_ROW_VPOS (row, matrix) + dvpos;
9452 w->cursor.y = row->y + dy;
9454 if (w == XWINDOW (selected_window))
9456 if (!row->continued_p
9457 && !MATRIX_ROW_CONTINUATION_LINE_P (row)
9458 && row->x == 0)
9460 this_line_buffer = XBUFFER (w->buffer);
9462 CHARPOS (this_line_start_pos)
9463 = MATRIX_ROW_START_CHARPOS (row) + delta;
9464 BYTEPOS (this_line_start_pos)
9465 = MATRIX_ROW_START_BYTEPOS (row) + delta_bytes;
9467 CHARPOS (this_line_end_pos)
9468 = Z - (MATRIX_ROW_END_CHARPOS (row) + delta);
9469 BYTEPOS (this_line_end_pos)
9470 = Z_BYTE - (MATRIX_ROW_END_BYTEPOS (row) + delta_bytes);
9472 this_line_y = w->cursor.y;
9473 this_line_pixel_height = row->height;
9474 this_line_vpos = w->cursor.vpos;
9475 this_line_start_x = row->x;
9477 else
9478 CHARPOS (this_line_start_pos) = 0;
9483 /* Run window scroll functions, if any, for WINDOW with new window
9484 start STARTP. Sets the window start of WINDOW to that position.
9486 We assume that the window's buffer is really current. */
9488 static INLINE struct text_pos
9489 run_window_scroll_functions (window, startp)
9490 Lisp_Object window;
9491 struct text_pos startp;
9493 struct window *w = XWINDOW (window);
9494 SET_MARKER_FROM_TEXT_POS (w->start, startp);
9496 if (current_buffer != XBUFFER (w->buffer))
9497 abort ();
9499 if (!NILP (Vwindow_scroll_functions))
9501 run_hook_with_args_2 (Qwindow_scroll_functions, window,
9502 make_number (CHARPOS (startp)));
9503 SET_TEXT_POS_FROM_MARKER (startp, w->start);
9504 /* In case the hook functions switch buffers. */
9505 if (current_buffer != XBUFFER (w->buffer))
9506 set_buffer_internal_1 (XBUFFER (w->buffer));
9509 return startp;
9513 /* Make sure the line containing the cursor is fully visible.
9514 A value of 1 means there is nothing to be done.
9515 (Either the line is fully visible, or it cannot be made so,
9516 or we cannot tell.)
9517 A value of 0 means the caller should do scrolling
9518 as if point had gone off the screen. */
9520 static int
9521 make_cursor_line_fully_visible (w)
9522 struct window *w;
9524 struct glyph_matrix *matrix;
9525 struct glyph_row *row;
9526 int window_height;
9528 /* It's not always possible to find the cursor, e.g, when a window
9529 is full of overlay strings. Don't do anything in that case. */
9530 if (w->cursor.vpos < 0)
9531 return 1;
9533 matrix = w->desired_matrix;
9534 row = MATRIX_ROW (matrix, w->cursor.vpos);
9536 /* If the cursor row is not partially visible, there's nothing to do. */
9537 if (!MATRIX_ROW_PARTIALLY_VISIBLE_P (row))
9538 return 1;
9540 /* If the row the cursor is in is taller than the window's height,
9541 it's not clear what to do, so do nothing. */
9542 window_height = window_box_height (w);
9543 if (row->height >= window_height)
9544 return 1;
9546 return 0;
9548 #if 0
9549 /* This code used to try to scroll the window just enough to make
9550 the line visible. It returned 0 to say that the caller should
9551 allocate larger glyph matrices. */
9553 if (MATRIX_ROW_PARTIALLY_VISIBLE_AT_TOP_P (w, row))
9555 int dy = row->height - row->visible_height;
9556 w->vscroll = 0;
9557 w->cursor.y += dy;
9558 shift_glyph_matrix (w, matrix, 0, matrix->nrows, dy);
9560 else /* MATRIX_ROW_PARTIALLY_VISIBLE_AT_BOTTOM_P (w, row)) */
9562 int dy = - (row->height - row->visible_height);
9563 w->vscroll = dy;
9564 w->cursor.y += dy;
9565 shift_glyph_matrix (w, matrix, 0, matrix->nrows, dy);
9568 /* When we change the cursor y-position of the selected window,
9569 change this_line_y as well so that the display optimization for
9570 the cursor line of the selected window in redisplay_internal uses
9571 the correct y-position. */
9572 if (w == XWINDOW (selected_window))
9573 this_line_y = w->cursor.y;
9575 /* If vscrolling requires a larger glyph matrix, arrange for a fresh
9576 redisplay with larger matrices. */
9577 if (matrix->nrows < required_matrix_height (w))
9579 fonts_changed_p = 1;
9580 return 0;
9583 return 1;
9584 #endif /* 0 */
9588 /* Try scrolling PT into view in window WINDOW. JUST_THIS_ONE_P
9589 non-zero means only WINDOW is redisplayed in redisplay_internal.
9590 TEMP_SCROLL_STEP has the same meaning as scroll_step, and is used
9591 in redisplay_window to bring a partially visible line into view in
9592 the case that only the cursor has moved.
9594 Value is
9596 1 if scrolling succeeded
9598 0 if scrolling didn't find point.
9600 -1 if new fonts have been loaded so that we must interrupt
9601 redisplay, adjust glyph matrices, and try again. */
9603 enum
9605 SCROLLING_SUCCESS,
9606 SCROLLING_FAILED,
9607 SCROLLING_NEED_LARGER_MATRICES
9610 static int
9611 try_scrolling (window, just_this_one_p, scroll_conservatively,
9612 scroll_step, temp_scroll_step)
9613 Lisp_Object window;
9614 int just_this_one_p;
9615 EMACS_INT scroll_conservatively, scroll_step;
9616 int temp_scroll_step;
9618 struct window *w = XWINDOW (window);
9619 struct frame *f = XFRAME (w->frame);
9620 struct text_pos scroll_margin_pos;
9621 struct text_pos pos;
9622 struct text_pos startp;
9623 struct it it;
9624 Lisp_Object window_end;
9625 int this_scroll_margin;
9626 int dy = 0;
9627 int scroll_max;
9628 int rc;
9629 int amount_to_scroll = 0;
9630 Lisp_Object aggressive;
9631 int height;
9633 #if GLYPH_DEBUG
9634 debug_method_add (w, "try_scrolling");
9635 #endif
9637 SET_TEXT_POS_FROM_MARKER (startp, w->start);
9639 /* Compute scroll margin height in pixels. We scroll when point is
9640 within this distance from the top or bottom of the window. */
9641 if (scroll_margin > 0)
9643 this_scroll_margin = min (scroll_margin, XINT (w->height) / 4);
9644 this_scroll_margin *= CANON_Y_UNIT (f);
9646 else
9647 this_scroll_margin = 0;
9649 /* Compute how much we should try to scroll maximally to bring point
9650 into view. */
9651 if (scroll_step || scroll_conservatively || temp_scroll_step)
9652 scroll_max = max (scroll_step,
9653 max (scroll_conservatively, temp_scroll_step));
9654 else if (NUMBERP (current_buffer->scroll_down_aggressively)
9655 || NUMBERP (current_buffer->scroll_up_aggressively))
9656 /* We're trying to scroll because of aggressive scrolling
9657 but no scroll_step is set. Choose an arbitrary one. Maybe
9658 there should be a variable for this. */
9659 scroll_max = 10;
9660 else
9661 scroll_max = 0;
9662 scroll_max *= CANON_Y_UNIT (f);
9664 /* Decide whether we have to scroll down. Start at the window end
9665 and move this_scroll_margin up to find the position of the scroll
9666 margin. */
9667 window_end = Fwindow_end (window, Qt);
9668 CHARPOS (scroll_margin_pos) = XINT (window_end);
9669 BYTEPOS (scroll_margin_pos) = CHAR_TO_BYTE (CHARPOS (scroll_margin_pos));
9670 if (this_scroll_margin)
9672 start_display (&it, w, scroll_margin_pos);
9673 move_it_vertically (&it, - this_scroll_margin);
9674 scroll_margin_pos = it.current.pos;
9677 if (PT >= CHARPOS (scroll_margin_pos))
9679 int y0;
9681 too_near_end:
9682 /* Point is in the scroll margin at the bottom of the window, or
9683 below. Compute a new window start that makes point visible. */
9685 /* Compute the distance from the scroll margin to PT.
9686 Give up if the distance is greater than scroll_max. */
9687 start_display (&it, w, scroll_margin_pos);
9688 y0 = it.current_y;
9689 move_it_to (&it, PT, 0, it.last_visible_y, -1,
9690 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
9692 /* To make point visible, we have to move the window start
9693 down so that the line the cursor is in is visible, which
9694 means we have to add in the height of the cursor line. */
9695 dy = line_bottom_y (&it) - y0;
9697 if (dy > scroll_max)
9698 return SCROLLING_FAILED;
9700 /* Move the window start down. If scrolling conservatively,
9701 move it just enough down to make point visible. If
9702 scroll_step is set, move it down by scroll_step. */
9703 start_display (&it, w, startp);
9705 if (scroll_conservatively)
9706 amount_to_scroll
9707 = max (max (dy, CANON_Y_UNIT (f)),
9708 CANON_Y_UNIT (f) * max (scroll_step, temp_scroll_step));
9709 else if (scroll_step || temp_scroll_step)
9710 amount_to_scroll = scroll_max;
9711 else
9713 aggressive = current_buffer->scroll_up_aggressively;
9714 height = (WINDOW_DISPLAY_HEIGHT_NO_MODE_LINE (w)
9715 - WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w));
9716 if (NUMBERP (aggressive))
9717 amount_to_scroll = XFLOATINT (aggressive) * height;
9720 if (amount_to_scroll <= 0)
9721 return SCROLLING_FAILED;
9723 move_it_vertically (&it, amount_to_scroll);
9724 startp = it.current.pos;
9726 else
9728 /* See if point is inside the scroll margin at the top of the
9729 window. */
9730 scroll_margin_pos = startp;
9731 if (this_scroll_margin)
9733 start_display (&it, w, startp);
9734 move_it_vertically (&it, this_scroll_margin);
9735 scroll_margin_pos = it.current.pos;
9738 if (PT < CHARPOS (scroll_margin_pos))
9740 /* Point is in the scroll margin at the top of the window or
9741 above what is displayed in the window. */
9742 int y0;
9744 /* Compute the vertical distance from PT to the scroll
9745 margin position. Give up if distance is greater than
9746 scroll_max. */
9747 SET_TEXT_POS (pos, PT, PT_BYTE);
9748 start_display (&it, w, pos);
9749 y0 = it.current_y;
9750 move_it_to (&it, CHARPOS (scroll_margin_pos), 0,
9751 it.last_visible_y, -1,
9752 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
9753 dy = it.current_y - y0;
9754 if (dy > scroll_max)
9755 return SCROLLING_FAILED;
9757 /* Compute new window start. */
9758 start_display (&it, w, startp);
9760 if (scroll_conservatively)
9761 amount_to_scroll =
9762 max (dy, CANON_Y_UNIT (f) * max (scroll_step, temp_scroll_step));
9763 else if (scroll_step || temp_scroll_step)
9764 amount_to_scroll = scroll_max;
9765 else
9767 aggressive = current_buffer->scroll_down_aggressively;
9768 height = (WINDOW_DISPLAY_HEIGHT_NO_MODE_LINE (w)
9769 - WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w));
9770 if (NUMBERP (aggressive))
9771 amount_to_scroll = XFLOATINT (aggressive) * height;
9774 if (amount_to_scroll <= 0)
9775 return SCROLLING_FAILED;
9777 move_it_vertically (&it, - amount_to_scroll);
9778 startp = it.current.pos;
9782 /* Run window scroll functions. */
9783 startp = run_window_scroll_functions (window, startp);
9785 /* Display the window. Give up if new fonts are loaded, or if point
9786 doesn't appear. */
9787 if (!try_window (window, startp))
9788 rc = SCROLLING_NEED_LARGER_MATRICES;
9789 else if (w->cursor.vpos < 0)
9791 clear_glyph_matrix (w->desired_matrix);
9792 rc = SCROLLING_FAILED;
9794 else
9796 /* Maybe forget recorded base line for line number display. */
9797 if (!just_this_one_p
9798 || current_buffer->clip_changed
9799 || BEG_UNCHANGED < CHARPOS (startp))
9800 w->base_line_number = Qnil;
9802 /* If cursor ends up on a partially visible line,
9803 treat that as being off the bottom of the screen. */
9804 if (! make_cursor_line_fully_visible (w))
9806 clear_glyph_matrix (w->desired_matrix);
9807 goto too_near_end;
9809 rc = SCROLLING_SUCCESS;
9812 return rc;
9816 /* Compute a suitable window start for window W if display of W starts
9817 on a continuation line. Value is non-zero if a new window start
9818 was computed.
9820 The new window start will be computed, based on W's width, starting
9821 from the start of the continued line. It is the start of the
9822 screen line with the minimum distance from the old start W->start. */
9824 static int
9825 compute_window_start_on_continuation_line (w)
9826 struct window *w;
9828 struct text_pos pos, start_pos;
9829 int window_start_changed_p = 0;
9831 SET_TEXT_POS_FROM_MARKER (start_pos, w->start);
9833 /* If window start is on a continuation line... Window start may be
9834 < BEGV in case there's invisible text at the start of the
9835 buffer (M-x rmail, for example). */
9836 if (CHARPOS (start_pos) > BEGV
9837 && FETCH_BYTE (BYTEPOS (start_pos) - 1) != '\n')
9839 struct it it;
9840 struct glyph_row *row;
9842 /* Handle the case that the window start is out of range. */
9843 if (CHARPOS (start_pos) < BEGV)
9844 SET_TEXT_POS (start_pos, BEGV, BEGV_BYTE);
9845 else if (CHARPOS (start_pos) > ZV)
9846 SET_TEXT_POS (start_pos, ZV, ZV_BYTE);
9848 /* Find the start of the continued line. This should be fast
9849 because scan_buffer is fast (newline cache). */
9850 row = w->desired_matrix->rows + (WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0);
9851 init_iterator (&it, w, CHARPOS (start_pos), BYTEPOS (start_pos),
9852 row, DEFAULT_FACE_ID);
9853 reseat_at_previous_visible_line_start (&it);
9855 /* If the line start is "too far" away from the window start,
9856 say it takes too much time to compute a new window start. */
9857 if (CHARPOS (start_pos) - IT_CHARPOS (it)
9858 < XFASTINT (w->height) * XFASTINT (w->width))
9860 int min_distance, distance;
9862 /* Move forward by display lines to find the new window
9863 start. If window width was enlarged, the new start can
9864 be expected to be > the old start. If window width was
9865 decreased, the new window start will be < the old start.
9866 So, we're looking for the display line start with the
9867 minimum distance from the old window start. */
9868 pos = it.current.pos;
9869 min_distance = INFINITY;
9870 while ((distance = abs (CHARPOS (start_pos) - IT_CHARPOS (it))),
9871 distance < min_distance)
9873 min_distance = distance;
9874 pos = it.current.pos;
9875 move_it_by_lines (&it, 1, 0);
9878 /* Set the window start there. */
9879 SET_MARKER_FROM_TEXT_POS (w->start, pos);
9880 window_start_changed_p = 1;
9884 return window_start_changed_p;
9888 /* Try cursor movement in case text has not changed in window WINDOW,
9889 with window start STARTP. Value is
9891 CURSOR_MOVEMENT_SUCCESS if successful
9893 CURSOR_MOVEMENT_CANNOT_BE_USED if this method cannot be used
9895 CURSOR_MOVEMENT_MUST_SCROLL if we know we have to scroll the
9896 display. *SCROLL_STEP is set to 1, under certain circumstances, if
9897 we want to scroll as if scroll-step were set to 1. See the code.
9899 CURSOR_MOVEMENT_NEED_LARGER_MATRICES if we need larger matrices, in
9900 which case we have to abort this redisplay, and adjust matrices
9901 first. */
9903 enum
9905 CURSOR_MOVEMENT_SUCCESS,
9906 CURSOR_MOVEMENT_CANNOT_BE_USED,
9907 CURSOR_MOVEMENT_MUST_SCROLL,
9908 CURSOR_MOVEMENT_NEED_LARGER_MATRICES
9911 static int
9912 try_cursor_movement (window, startp, scroll_step)
9913 Lisp_Object window;
9914 struct text_pos startp;
9915 int *scroll_step;
9917 struct window *w = XWINDOW (window);
9918 struct frame *f = XFRAME (w->frame);
9919 int rc = CURSOR_MOVEMENT_CANNOT_BE_USED;
9921 #if GLYPH_DEBUG
9922 if (inhibit_try_cursor_movement)
9923 return rc;
9924 #endif
9926 /* Handle case where text has not changed, only point, and it has
9927 not moved off the frame. */
9928 if (/* Point may be in this window. */
9929 PT >= CHARPOS (startp)
9930 /* Selective display hasn't changed. */
9931 && !current_buffer->clip_changed
9932 /* Function force-mode-line-update is used to force a thorough
9933 redisplay. It sets either windows_or_buffers_changed or
9934 update_mode_lines. So don't take a shortcut here for these
9935 cases. */
9936 && !update_mode_lines
9937 && !windows_or_buffers_changed
9938 && !cursor_type_changed
9939 /* Can't use this case if highlighting a region. When a
9940 region exists, cursor movement has to do more than just
9941 set the cursor. */
9942 && !(!NILP (Vtransient_mark_mode)
9943 && !NILP (current_buffer->mark_active))
9944 && NILP (w->region_showing)
9945 && NILP (Vshow_trailing_whitespace)
9946 /* Right after splitting windows, last_point may be nil. */
9947 && INTEGERP (w->last_point)
9948 /* This code is not used for mini-buffer for the sake of the case
9949 of redisplaying to replace an echo area message; since in
9950 that case the mini-buffer contents per se are usually
9951 unchanged. This code is of no real use in the mini-buffer
9952 since the handling of this_line_start_pos, etc., in redisplay
9953 handles the same cases. */
9954 && !EQ (window, minibuf_window)
9955 /* When splitting windows or for new windows, it happens that
9956 redisplay is called with a nil window_end_vpos or one being
9957 larger than the window. This should really be fixed in
9958 window.c. I don't have this on my list, now, so we do
9959 approximately the same as the old redisplay code. --gerd. */
9960 && INTEGERP (w->window_end_vpos)
9961 && XFASTINT (w->window_end_vpos) < w->current_matrix->nrows
9962 && (FRAME_WINDOW_P (f)
9963 || !MARKERP (Voverlay_arrow_position)
9964 || current_buffer != XMARKER (Voverlay_arrow_position)->buffer))
9966 int this_scroll_margin;
9967 struct glyph_row *row = NULL;
9969 #if GLYPH_DEBUG
9970 debug_method_add (w, "cursor movement");
9971 #endif
9973 /* Scroll if point within this distance from the top or bottom
9974 of the window. This is a pixel value. */
9975 this_scroll_margin = max (0, scroll_margin);
9976 this_scroll_margin = min (this_scroll_margin, XFASTINT (w->height) / 4);
9977 this_scroll_margin *= CANON_Y_UNIT (f);
9979 /* Start with the row the cursor was displayed during the last
9980 not paused redisplay. Give up if that row is not valid. */
9981 if (w->last_cursor.vpos < 0
9982 || w->last_cursor.vpos >= w->current_matrix->nrows)
9983 rc = CURSOR_MOVEMENT_MUST_SCROLL;
9984 else
9986 row = MATRIX_ROW (w->current_matrix, w->last_cursor.vpos);
9987 if (row->mode_line_p)
9988 ++row;
9989 if (!row->enabled_p)
9990 rc = CURSOR_MOVEMENT_MUST_SCROLL;
9993 if (rc == CURSOR_MOVEMENT_CANNOT_BE_USED)
9995 int scroll_p = 0;
9996 int last_y = window_text_bottom_y (w) - this_scroll_margin;
9998 if (PT > XFASTINT (w->last_point))
10000 /* Point has moved forward. */
10001 while (MATRIX_ROW_END_CHARPOS (row) < PT
10002 && MATRIX_ROW_BOTTOM_Y (row) < last_y)
10004 xassert (row->enabled_p);
10005 ++row;
10008 /* The end position of a row equals the start position
10009 of the next row. If PT is there, we would rather
10010 display it in the next line. */
10011 while (MATRIX_ROW_BOTTOM_Y (row) < last_y
10012 && MATRIX_ROW_END_CHARPOS (row) == PT
10013 && !cursor_row_p (w, row))
10014 ++row;
10016 /* If within the scroll margin, scroll. Note that
10017 MATRIX_ROW_BOTTOM_Y gives the pixel position at which
10018 the next line would be drawn, and that
10019 this_scroll_margin can be zero. */
10020 if (MATRIX_ROW_BOTTOM_Y (row) > last_y
10021 || PT > MATRIX_ROW_END_CHARPOS (row)
10022 /* Line is completely visible last line in window
10023 and PT is to be set in the next line. */
10024 || (MATRIX_ROW_BOTTOM_Y (row) == last_y
10025 && PT == MATRIX_ROW_END_CHARPOS (row)
10026 && !row->ends_at_zv_p
10027 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row)))
10028 scroll_p = 1;
10030 else if (PT < XFASTINT (w->last_point))
10032 /* Cursor has to be moved backward. Note that PT >=
10033 CHARPOS (startp) because of the outer
10034 if-statement. */
10035 while (!row->mode_line_p
10036 && (MATRIX_ROW_START_CHARPOS (row) > PT
10037 || (MATRIX_ROW_START_CHARPOS (row) == PT
10038 && MATRIX_ROW_STARTS_IN_MIDDLE_OF_CHAR_P (row)))
10039 && (row->y > this_scroll_margin
10040 || CHARPOS (startp) == BEGV))
10042 xassert (row->enabled_p);
10043 --row;
10046 /* Consider the following case: Window starts at BEGV,
10047 there is invisible, intangible text at BEGV, so that
10048 display starts at some point START > BEGV. It can
10049 happen that we are called with PT somewhere between
10050 BEGV and START. Try to handle that case. */
10051 if (row < w->current_matrix->rows
10052 || row->mode_line_p)
10054 row = w->current_matrix->rows;
10055 if (row->mode_line_p)
10056 ++row;
10059 /* Due to newlines in overlay strings, we may have to
10060 skip forward over overlay strings. */
10061 while (MATRIX_ROW_BOTTOM_Y (row) < last_y
10062 && MATRIX_ROW_END_CHARPOS (row) == PT
10063 && !cursor_row_p (w, row))
10064 ++row;
10066 /* If within the scroll margin, scroll. */
10067 if (row->y < this_scroll_margin
10068 && CHARPOS (startp) != BEGV)
10069 scroll_p = 1;
10072 if (PT < MATRIX_ROW_START_CHARPOS (row)
10073 || PT > MATRIX_ROW_END_CHARPOS (row))
10075 /* if PT is not in the glyph row, give up. */
10076 rc = CURSOR_MOVEMENT_MUST_SCROLL;
10078 else if (MATRIX_ROW_PARTIALLY_VISIBLE_P (row))
10080 if (PT == MATRIX_ROW_END_CHARPOS (row)
10081 && !row->ends_at_zv_p
10082 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))
10083 rc = CURSOR_MOVEMENT_MUST_SCROLL;
10084 else if (row->height > window_box_height (w))
10086 /* If we end up in a partially visible line, let's
10087 make it fully visible, except when it's taller
10088 than the window, in which case we can't do much
10089 about it. */
10090 *scroll_step = 1;
10091 rc = CURSOR_MOVEMENT_MUST_SCROLL;
10093 else
10095 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
10096 try_window (window, startp);
10097 if (!make_cursor_line_fully_visible (w))
10098 rc = CURSOR_MOVEMENT_MUST_SCROLL;
10099 else
10100 rc = CURSOR_MOVEMENT_SUCCESS;
10103 else if (scroll_p)
10104 rc = CURSOR_MOVEMENT_MUST_SCROLL;
10105 else
10107 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
10108 rc = CURSOR_MOVEMENT_SUCCESS;
10113 return rc;
10117 /* Redisplay leaf window WINDOW. JUST_THIS_ONE_P non-zero means only
10118 selected_window is redisplayed.
10120 We can return without actually redisplaying the window if
10121 fonts_changed_p is nonzero. In that case, redisplay_internal will
10122 retry. */
10124 static void
10125 redisplay_window (window, just_this_one_p)
10126 Lisp_Object window;
10127 int just_this_one_p;
10129 struct window *w = XWINDOW (window);
10130 struct frame *f = XFRAME (w->frame);
10131 struct buffer *buffer = XBUFFER (w->buffer);
10132 struct buffer *old = current_buffer;
10133 struct text_pos lpoint, opoint, startp;
10134 int update_mode_line;
10135 int tem;
10136 struct it it;
10137 /* Record it now because it's overwritten. */
10138 int current_matrix_up_to_date_p = 0;
10139 /* This is less strict than current_matrix_up_to_date_p.
10140 It indictes that the buffer contents and narrowing are unchanged. */
10141 int buffer_unchanged_p = 0;
10142 int temp_scroll_step = 0;
10143 int count = SPECPDL_INDEX ();
10144 int rc;
10145 int centering_position;
10147 SET_TEXT_POS (lpoint, PT, PT_BYTE);
10148 opoint = lpoint;
10150 /* W must be a leaf window here. */
10151 xassert (!NILP (w->buffer));
10152 #if GLYPH_DEBUG
10153 *w->desired_matrix->method = 0;
10154 #endif
10156 specbind (Qinhibit_point_motion_hooks, Qt);
10158 reconsider_clip_changes (w, buffer);
10160 /* Has the mode line to be updated? */
10161 update_mode_line = (!NILP (w->update_mode_line)
10162 || update_mode_lines
10163 || buffer->clip_changed
10164 || buffer->prevent_redisplay_optimizations_p);
10166 if (MINI_WINDOW_P (w))
10168 if (w == XWINDOW (echo_area_window)
10169 && !NILP (echo_area_buffer[0]))
10171 if (update_mode_line)
10172 /* We may have to update a tty frame's menu bar or a
10173 tool-bar. Example `M-x C-h C-h C-g'. */
10174 goto finish_menu_bars;
10175 else
10176 /* We've already displayed the echo area glyphs in this window. */
10177 goto finish_scroll_bars;
10179 else if (w != XWINDOW (minibuf_window))
10181 /* W is a mini-buffer window, but it's not the currently
10182 active one, so clear it. */
10183 int yb = window_text_bottom_y (w);
10184 struct glyph_row *row;
10185 int y;
10187 for (y = 0, row = w->desired_matrix->rows;
10188 y < yb;
10189 y += row->height, ++row)
10190 blank_row (w, row, y);
10191 goto finish_scroll_bars;
10194 clear_glyph_matrix (w->desired_matrix);
10197 /* Otherwise set up data on this window; select its buffer and point
10198 value. */
10199 /* Really select the buffer, for the sake of buffer-local
10200 variables. */
10201 set_buffer_internal_1 (XBUFFER (w->buffer));
10202 SET_TEXT_POS (opoint, PT, PT_BYTE);
10204 current_matrix_up_to_date_p
10205 = (!NILP (w->window_end_valid)
10206 && !current_buffer->clip_changed
10207 && !current_buffer->prevent_redisplay_optimizations_p
10208 && XFASTINT (w->last_modified) >= MODIFF
10209 && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF);
10211 buffer_unchanged_p
10212 = (!NILP (w->window_end_valid)
10213 && !current_buffer->clip_changed
10214 && XFASTINT (w->last_modified) >= MODIFF
10215 && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF);
10217 /* When windows_or_buffers_changed is non-zero, we can't rely on
10218 the window end being valid, so set it to nil there. */
10219 if (windows_or_buffers_changed)
10221 /* If window starts on a continuation line, maybe adjust the
10222 window start in case the window's width changed. */
10223 if (XMARKER (w->start)->buffer == current_buffer)
10224 compute_window_start_on_continuation_line (w);
10226 w->window_end_valid = Qnil;
10229 /* Some sanity checks. */
10230 CHECK_WINDOW_END (w);
10231 if (Z == Z_BYTE && CHARPOS (opoint) != BYTEPOS (opoint))
10232 abort ();
10233 if (BYTEPOS (opoint) < CHARPOS (opoint))
10234 abort ();
10236 /* If %c is in mode line, update it if needed. */
10237 if (!NILP (w->column_number_displayed)
10238 /* This alternative quickly identifies a common case
10239 where no change is needed. */
10240 && !(PT == XFASTINT (w->last_point)
10241 && XFASTINT (w->last_modified) >= MODIFF
10242 && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF)
10243 && (XFASTINT (w->column_number_displayed)
10244 != (int) current_column ())) /* iftc */
10245 update_mode_line = 1;
10247 /* Count number of windows showing the selected buffer. An indirect
10248 buffer counts as its base buffer. */
10249 if (!just_this_one_p)
10251 struct buffer *current_base, *window_base;
10252 current_base = current_buffer;
10253 window_base = XBUFFER (XWINDOW (selected_window)->buffer);
10254 if (current_base->base_buffer)
10255 current_base = current_base->base_buffer;
10256 if (window_base->base_buffer)
10257 window_base = window_base->base_buffer;
10258 if (current_base == window_base)
10259 buffer_shared++;
10262 /* Point refers normally to the selected window. For any other
10263 window, set up appropriate value. */
10264 if (!EQ (window, selected_window))
10266 int new_pt = XMARKER (w->pointm)->charpos;
10267 int new_pt_byte = marker_byte_position (w->pointm);
10268 if (new_pt < BEGV)
10270 new_pt = BEGV;
10271 new_pt_byte = BEGV_BYTE;
10272 set_marker_both (w->pointm, Qnil, BEGV, BEGV_BYTE);
10274 else if (new_pt > (ZV - 1))
10276 new_pt = ZV;
10277 new_pt_byte = ZV_BYTE;
10278 set_marker_both (w->pointm, Qnil, ZV, ZV_BYTE);
10281 /* We don't use SET_PT so that the point-motion hooks don't run. */
10282 TEMP_SET_PT_BOTH (new_pt, new_pt_byte);
10285 /* If any of the character widths specified in the display table
10286 have changed, invalidate the width run cache. It's true that
10287 this may be a bit late to catch such changes, but the rest of
10288 redisplay goes (non-fatally) haywire when the display table is
10289 changed, so why should we worry about doing any better? */
10290 if (current_buffer->width_run_cache)
10292 struct Lisp_Char_Table *disptab = buffer_display_table ();
10294 if (! disptab_matches_widthtab (disptab,
10295 XVECTOR (current_buffer->width_table)))
10297 invalidate_region_cache (current_buffer,
10298 current_buffer->width_run_cache,
10299 BEG, Z);
10300 recompute_width_table (current_buffer, disptab);
10304 /* If window-start is screwed up, choose a new one. */
10305 if (XMARKER (w->start)->buffer != current_buffer)
10306 goto recenter;
10308 SET_TEXT_POS_FROM_MARKER (startp, w->start);
10310 /* If someone specified a new starting point but did not insist,
10311 check whether it can be used. */
10312 if (!NILP (w->optional_new_start)
10313 && CHARPOS (startp) >= BEGV
10314 && CHARPOS (startp) <= ZV)
10316 w->optional_new_start = Qnil;
10317 start_display (&it, w, startp);
10318 move_it_to (&it, PT, 0, it.last_visible_y, -1,
10319 MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y);
10320 if (IT_CHARPOS (it) == PT)
10321 w->force_start = Qt;
10324 /* Handle case where place to start displaying has been specified,
10325 unless the specified location is outside the accessible range. */
10326 if (!NILP (w->force_start)
10327 || w->frozen_window_start_p)
10329 /* We set this later on if we have to adjust point. */
10330 int new_vpos = -1;
10332 w->force_start = Qnil;
10333 w->vscroll = 0;
10334 w->window_end_valid = Qnil;
10336 /* Forget any recorded base line for line number display. */
10337 if (!buffer_unchanged_p)
10338 w->base_line_number = Qnil;
10340 /* Redisplay the mode line. Select the buffer properly for that.
10341 Also, run the hook window-scroll-functions
10342 because we have scrolled. */
10343 /* Note, we do this after clearing force_start because
10344 if there's an error, it is better to forget about force_start
10345 than to get into an infinite loop calling the hook functions
10346 and having them get more errors. */
10347 if (!update_mode_line
10348 || ! NILP (Vwindow_scroll_functions))
10350 update_mode_line = 1;
10351 w->update_mode_line = Qt;
10352 startp = run_window_scroll_functions (window, startp);
10355 w->last_modified = make_number (0);
10356 w->last_overlay_modified = make_number (0);
10357 if (CHARPOS (startp) < BEGV)
10358 SET_TEXT_POS (startp, BEGV, BEGV_BYTE);
10359 else if (CHARPOS (startp) > ZV)
10360 SET_TEXT_POS (startp, ZV, ZV_BYTE);
10362 /* Redisplay, then check if cursor has been set during the
10363 redisplay. Give up if new fonts were loaded. */
10364 if (!try_window (window, startp))
10366 w->force_start = Qt;
10367 clear_glyph_matrix (w->desired_matrix);
10368 goto need_larger_matrices;
10371 if (w->cursor.vpos < 0 && !w->frozen_window_start_p)
10373 /* If point does not appear, try to move point so it does
10374 appear. The desired matrix has been built above, so we
10375 can use it here. */
10376 new_vpos = window_box_height (w) / 2;
10379 if (!make_cursor_line_fully_visible (w))
10381 /* Point does appear, but on a line partly visible at end of window.
10382 Move it back to a fully-visible line. */
10383 new_vpos = window_box_height (w);
10386 /* If we need to move point for either of the above reasons,
10387 now actually do it. */
10388 if (new_vpos >= 0)
10390 struct glyph_row *row;
10392 row = MATRIX_FIRST_TEXT_ROW (w->desired_matrix);
10393 while (MATRIX_ROW_BOTTOM_Y (row) < new_vpos)
10394 ++row;
10396 TEMP_SET_PT_BOTH (MATRIX_ROW_START_CHARPOS (row),
10397 MATRIX_ROW_START_BYTEPOS (row));
10399 if (w != XWINDOW (selected_window))
10400 set_marker_both (w->pointm, Qnil, PT, PT_BYTE);
10401 else if (current_buffer == old)
10402 SET_TEXT_POS (lpoint, PT, PT_BYTE);
10404 set_cursor_from_row (w, row, w->desired_matrix, 0, 0, 0, 0);
10406 /* If we are highlighting the region, then we just changed
10407 the region, so redisplay to show it. */
10408 if (!NILP (Vtransient_mark_mode)
10409 && !NILP (current_buffer->mark_active))
10411 clear_glyph_matrix (w->desired_matrix);
10412 if (!try_window (window, startp))
10413 goto need_larger_matrices;
10417 #if GLYPH_DEBUG
10418 debug_method_add (w, "forced window start");
10419 #endif
10420 goto done;
10423 /* Handle case where text has not changed, only point, and it has
10424 not moved off the frame, and we are not retrying after hscroll.
10425 (current_matrix_up_to_date_p is nonzero when retrying.) */
10426 if (current_matrix_up_to_date_p
10427 && (rc = try_cursor_movement (window, startp, &temp_scroll_step),
10428 rc != CURSOR_MOVEMENT_CANNOT_BE_USED))
10430 switch (rc)
10432 case CURSOR_MOVEMENT_SUCCESS:
10433 goto done;
10435 #if 0 /* try_cursor_movement never returns this value. */
10436 case CURSOR_MOVEMENT_NEED_LARGER_MATRICES:
10437 goto need_larger_matrices;
10438 #endif
10440 case CURSOR_MOVEMENT_MUST_SCROLL:
10441 goto try_to_scroll;
10443 default:
10444 abort ();
10447 /* If current starting point was originally the beginning of a line
10448 but no longer is, find a new starting point. */
10449 else if (!NILP (w->start_at_line_beg)
10450 && !(CHARPOS (startp) <= BEGV
10451 || FETCH_BYTE (BYTEPOS (startp) - 1) == '\n'))
10453 #if GLYPH_DEBUG
10454 debug_method_add (w, "recenter 1");
10455 #endif
10456 goto recenter;
10459 /* Try scrolling with try_window_id. Value is > 0 if update has
10460 been done, it is -1 if we know that the same window start will
10461 not work. It is 0 if unsuccessful for some other reason. */
10462 else if ((tem = try_window_id (w)) != 0)
10464 #if GLYPH_DEBUG
10465 debug_method_add (w, "try_window_id %d", tem);
10466 #endif
10468 if (fonts_changed_p)
10469 goto need_larger_matrices;
10470 if (tem > 0)
10471 goto done;
10473 /* Otherwise try_window_id has returned -1 which means that we
10474 don't want the alternative below this comment to execute. */
10476 else if (CHARPOS (startp) >= BEGV
10477 && CHARPOS (startp) <= ZV
10478 && PT >= CHARPOS (startp)
10479 && (CHARPOS (startp) < ZV
10480 /* Avoid starting at end of buffer. */
10481 || CHARPOS (startp) == BEGV
10482 || (XFASTINT (w->last_modified) >= MODIFF
10483 && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF)))
10485 #if GLYPH_DEBUG
10486 debug_method_add (w, "same window start");
10487 #endif
10489 /* Try to redisplay starting at same place as before.
10490 If point has not moved off frame, accept the results. */
10491 if (!current_matrix_up_to_date_p
10492 /* Don't use try_window_reusing_current_matrix in this case
10493 because a window scroll function can have changed the
10494 buffer. */
10495 || !NILP (Vwindow_scroll_functions)
10496 || MINI_WINDOW_P (w)
10497 || !try_window_reusing_current_matrix (w))
10499 IF_DEBUG (debug_method_add (w, "1"));
10500 try_window (window, startp);
10503 if (fonts_changed_p)
10504 goto need_larger_matrices;
10506 if (w->cursor.vpos >= 0)
10508 if (!just_this_one_p
10509 || current_buffer->clip_changed
10510 || BEG_UNCHANGED < CHARPOS (startp))
10511 /* Forget any recorded base line for line number display. */
10512 w->base_line_number = Qnil;
10514 if (!make_cursor_line_fully_visible (w))
10515 clear_glyph_matrix (w->desired_matrix);
10516 /* Drop through and scroll. */
10517 else
10518 goto done;
10520 else
10521 clear_glyph_matrix (w->desired_matrix);
10524 try_to_scroll:
10526 w->last_modified = make_number (0);
10527 w->last_overlay_modified = make_number (0);
10529 /* Redisplay the mode line. Select the buffer properly for that. */
10530 if (!update_mode_line)
10532 update_mode_line = 1;
10533 w->update_mode_line = Qt;
10536 /* Try to scroll by specified few lines. */
10537 if ((scroll_conservatively
10538 || scroll_step
10539 || temp_scroll_step
10540 || NUMBERP (current_buffer->scroll_up_aggressively)
10541 || NUMBERP (current_buffer->scroll_down_aggressively))
10542 && !current_buffer->clip_changed
10543 && CHARPOS (startp) >= BEGV
10544 && CHARPOS (startp) <= ZV)
10546 /* The function returns -1 if new fonts were loaded, 1 if
10547 successful, 0 if not successful. */
10548 int rc = try_scrolling (window, just_this_one_p,
10549 scroll_conservatively,
10550 scroll_step,
10551 temp_scroll_step);
10552 switch (rc)
10554 case SCROLLING_SUCCESS:
10555 goto done;
10557 case SCROLLING_NEED_LARGER_MATRICES:
10558 goto need_larger_matrices;
10560 case SCROLLING_FAILED:
10561 break;
10563 default:
10564 abort ();
10568 /* Finally, just choose place to start which centers point */
10570 recenter:
10571 centering_position = window_box_height (w) / 2;
10573 point_at_top:
10574 /* Jump here with centering_position already set to 0. */
10576 #if GLYPH_DEBUG
10577 debug_method_add (w, "recenter");
10578 #endif
10580 /* w->vscroll = 0; */
10582 /* Forget any previously recorded base line for line number display. */
10583 if (!buffer_unchanged_p)
10584 w->base_line_number = Qnil;
10586 /* Move backward half the height of the window. */
10587 init_iterator (&it, w, PT, PT_BYTE, NULL, DEFAULT_FACE_ID);
10588 it.current_y = it.last_visible_y;
10589 move_it_vertically_backward (&it, centering_position);
10590 xassert (IT_CHARPOS (it) >= BEGV);
10592 /* The function move_it_vertically_backward may move over more
10593 than the specified y-distance. If it->w is small, e.g. a
10594 mini-buffer window, we may end up in front of the window's
10595 display area. Start displaying at the start of the line
10596 containing PT in this case. */
10597 if (it.current_y <= 0)
10599 init_iterator (&it, w, PT, PT_BYTE, NULL, DEFAULT_FACE_ID);
10600 move_it_vertically (&it, 0);
10601 xassert (IT_CHARPOS (it) <= PT);
10602 it.current_y = 0;
10605 it.current_x = it.hpos = 0;
10607 /* Set startp here explicitly in case that helps avoid an infinite loop
10608 in case the window-scroll-functions functions get errors. */
10609 set_marker_both (w->start, Qnil, IT_CHARPOS (it), IT_BYTEPOS (it));
10611 /* Run scroll hooks. */
10612 startp = run_window_scroll_functions (window, it.current.pos);
10614 /* Redisplay the window. */
10615 if (!current_matrix_up_to_date_p
10616 || windows_or_buffers_changed
10617 || cursor_type_changed
10618 /* Don't use try_window_reusing_current_matrix in this case
10619 because it can have changed the buffer. */
10620 || !NILP (Vwindow_scroll_functions)
10621 || !just_this_one_p
10622 || MINI_WINDOW_P (w)
10623 || !try_window_reusing_current_matrix (w))
10624 try_window (window, startp);
10626 /* If new fonts have been loaded (due to fontsets), give up. We
10627 have to start a new redisplay since we need to re-adjust glyph
10628 matrices. */
10629 if (fonts_changed_p)
10630 goto need_larger_matrices;
10632 /* If cursor did not appear assume that the middle of the window is
10633 in the first line of the window. Do it again with the next line.
10634 (Imagine a window of height 100, displaying two lines of height
10635 60. Moving back 50 from it->last_visible_y will end in the first
10636 line.) */
10637 if (w->cursor.vpos < 0)
10639 if (!NILP (w->window_end_valid)
10640 && PT >= Z - XFASTINT (w->window_end_pos))
10642 clear_glyph_matrix (w->desired_matrix);
10643 move_it_by_lines (&it, 1, 0);
10644 try_window (window, it.current.pos);
10646 else if (PT < IT_CHARPOS (it))
10648 clear_glyph_matrix (w->desired_matrix);
10649 move_it_by_lines (&it, -1, 0);
10650 try_window (window, it.current.pos);
10652 else
10654 /* Not much we can do about it. */
10658 /* Consider the following case: Window starts at BEGV, there is
10659 invisible, intangible text at BEGV, so that display starts at
10660 some point START > BEGV. It can happen that we are called with
10661 PT somewhere between BEGV and START. Try to handle that case. */
10662 if (w->cursor.vpos < 0)
10664 struct glyph_row *row = w->current_matrix->rows;
10665 if (row->mode_line_p)
10666 ++row;
10667 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
10670 if (!make_cursor_line_fully_visible (w))
10672 /* If centering point failed to make the whole line visible,
10673 put point at the top instead. That has to make the whole line
10674 visible, if it can be done. */
10675 centering_position = 0;
10676 goto point_at_top;
10679 done:
10681 SET_TEXT_POS_FROM_MARKER (startp, w->start);
10682 w->start_at_line_beg = ((CHARPOS (startp) == BEGV
10683 || FETCH_BYTE (BYTEPOS (startp) - 1) == '\n')
10684 ? Qt : Qnil);
10686 /* Display the mode line, if we must. */
10687 if ((update_mode_line
10688 /* If window not full width, must redo its mode line
10689 if (a) the window to its side is being redone and
10690 (b) we do a frame-based redisplay. This is a consequence
10691 of how inverted lines are drawn in frame-based redisplay. */
10692 || (!just_this_one_p
10693 && !FRAME_WINDOW_P (f)
10694 && !WINDOW_FULL_WIDTH_P (w))
10695 /* Line number to display. */
10696 || INTEGERP (w->base_line_pos)
10697 /* Column number is displayed and different from the one displayed. */
10698 || (!NILP (w->column_number_displayed)
10699 && (XFASTINT (w->column_number_displayed)
10700 != (int) current_column ()))) /* iftc */
10701 /* This means that the window has a mode line. */
10702 && (WINDOW_WANTS_MODELINE_P (w)
10703 || WINDOW_WANTS_HEADER_LINE_P (w)))
10705 display_mode_lines (w);
10707 /* If mode line height has changed, arrange for a thorough
10708 immediate redisplay using the correct mode line height. */
10709 if (WINDOW_WANTS_MODELINE_P (w)
10710 && CURRENT_MODE_LINE_HEIGHT (w) != DESIRED_MODE_LINE_HEIGHT (w))
10712 fonts_changed_p = 1;
10713 MATRIX_MODE_LINE_ROW (w->current_matrix)->height
10714 = DESIRED_MODE_LINE_HEIGHT (w);
10717 /* If top line height has changed, arrange for a thorough
10718 immediate redisplay using the correct mode line height. */
10719 if (WINDOW_WANTS_HEADER_LINE_P (w)
10720 && CURRENT_HEADER_LINE_HEIGHT (w) != DESIRED_HEADER_LINE_HEIGHT (w))
10722 fonts_changed_p = 1;
10723 MATRIX_HEADER_LINE_ROW (w->current_matrix)->height
10724 = DESIRED_HEADER_LINE_HEIGHT (w);
10727 if (fonts_changed_p)
10728 goto need_larger_matrices;
10731 if (!line_number_displayed
10732 && !BUFFERP (w->base_line_pos))
10734 w->base_line_pos = Qnil;
10735 w->base_line_number = Qnil;
10738 finish_menu_bars:
10740 /* When we reach a frame's selected window, redo the frame's menu bar. */
10741 if (update_mode_line
10742 && EQ (FRAME_SELECTED_WINDOW (f), window))
10744 int redisplay_menu_p = 0;
10746 if (FRAME_WINDOW_P (f))
10748 #if defined (USE_X_TOOLKIT) || defined (HAVE_NTGUI) || defined (MAC_OS)
10749 redisplay_menu_p = FRAME_EXTERNAL_MENU_BAR (f);
10750 #else
10751 redisplay_menu_p = FRAME_MENU_BAR_LINES (f) > 0;
10752 #endif
10754 else
10755 redisplay_menu_p = FRAME_MENU_BAR_LINES (f) > 0;
10757 if (redisplay_menu_p)
10758 display_menu_bar (w);
10760 #ifdef HAVE_WINDOW_SYSTEM
10761 if (WINDOWP (f->tool_bar_window)
10762 && (FRAME_TOOL_BAR_LINES (f) > 0
10763 || auto_resize_tool_bars_p))
10764 redisplay_tool_bar (f);
10765 #endif
10768 /* We go to this label, with fonts_changed_p nonzero,
10769 if it is necessary to try again using larger glyph matrices.
10770 We have to redeem the scroll bar even in this case,
10771 because the loop in redisplay_internal expects that. */
10772 need_larger_matrices:
10774 finish_scroll_bars:
10776 if (FRAME_HAS_VERTICAL_SCROLL_BARS (f))
10778 int start, end, whole;
10780 /* Calculate the start and end positions for the current window.
10781 At some point, it would be nice to choose between scrollbars
10782 which reflect the whole buffer size, with special markers
10783 indicating narrowing, and scrollbars which reflect only the
10784 visible region.
10786 Note that mini-buffers sometimes aren't displaying any text. */
10787 if (!MINI_WINDOW_P (w)
10788 || (w == XWINDOW (minibuf_window)
10789 && NILP (echo_area_buffer[0])))
10791 whole = ZV - BEGV;
10792 start = marker_position (w->start) - BEGV;
10793 /* I don't think this is guaranteed to be right. For the
10794 moment, we'll pretend it is. */
10795 end = (Z - XFASTINT (w->window_end_pos)) - BEGV;
10797 if (end < start)
10798 end = start;
10799 if (whole < (end - start))
10800 whole = end - start;
10802 else
10803 start = end = whole = 0;
10805 /* Indicate what this scroll bar ought to be displaying now. */
10806 set_vertical_scroll_bar_hook (w, end - start, whole, start);
10808 /* Note that we actually used the scroll bar attached to this
10809 window, so it shouldn't be deleted at the end of redisplay. */
10810 redeem_scroll_bar_hook (w);
10813 /* Restore current_buffer and value of point in it. */
10814 TEMP_SET_PT_BOTH (CHARPOS (opoint), BYTEPOS (opoint));
10815 set_buffer_internal_1 (old);
10816 TEMP_SET_PT_BOTH (CHARPOS (lpoint), BYTEPOS (lpoint));
10818 unbind_to (count, Qnil);
10822 /* Build the complete desired matrix of WINDOW with a window start
10823 buffer position POS. Value is non-zero if successful. It is zero
10824 if fonts were loaded during redisplay which makes re-adjusting
10825 glyph matrices necessary. */
10828 try_window (window, pos)
10829 Lisp_Object window;
10830 struct text_pos pos;
10832 struct window *w = XWINDOW (window);
10833 struct it it;
10834 struct glyph_row *last_text_row = NULL;
10836 /* Make POS the new window start. */
10837 set_marker_both (w->start, Qnil, CHARPOS (pos), BYTEPOS (pos));
10839 /* Mark cursor position as unknown. No overlay arrow seen. */
10840 w->cursor.vpos = -1;
10841 overlay_arrow_seen = 0;
10843 /* Initialize iterator and info to start at POS. */
10844 start_display (&it, w, pos);
10846 /* Display all lines of W. */
10847 while (it.current_y < it.last_visible_y)
10849 if (display_line (&it))
10850 last_text_row = it.glyph_row - 1;
10851 if (fonts_changed_p)
10852 return 0;
10855 /* If bottom moved off end of frame, change mode line percentage. */
10856 if (XFASTINT (w->window_end_pos) <= 0
10857 && Z != IT_CHARPOS (it))
10858 w->update_mode_line = Qt;
10860 /* Set window_end_pos to the offset of the last character displayed
10861 on the window from the end of current_buffer. Set
10862 window_end_vpos to its row number. */
10863 if (last_text_row)
10865 xassert (MATRIX_ROW_DISPLAYS_TEXT_P (last_text_row));
10866 w->window_end_bytepos
10867 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_text_row);
10868 w->window_end_pos
10869 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_text_row));
10870 w->window_end_vpos
10871 = make_number (MATRIX_ROW_VPOS (last_text_row, w->desired_matrix));
10872 xassert (MATRIX_ROW (w->desired_matrix, XFASTINT (w->window_end_vpos))
10873 ->displays_text_p);
10875 else
10877 w->window_end_bytepos = 0;
10878 w->window_end_pos = w->window_end_vpos = make_number (0);
10881 /* But that is not valid info until redisplay finishes. */
10882 w->window_end_valid = Qnil;
10883 return 1;
10888 /************************************************************************
10889 Window redisplay reusing current matrix when buffer has not changed
10890 ************************************************************************/
10892 /* Try redisplay of window W showing an unchanged buffer with a
10893 different window start than the last time it was displayed by
10894 reusing its current matrix. Value is non-zero if successful.
10895 W->start is the new window start. */
10897 static int
10898 try_window_reusing_current_matrix (w)
10899 struct window *w;
10901 struct frame *f = XFRAME (w->frame);
10902 struct glyph_row *row, *bottom_row;
10903 struct it it;
10904 struct run run;
10905 struct text_pos start, new_start;
10906 int nrows_scrolled, i;
10907 struct glyph_row *last_text_row;
10908 struct glyph_row *last_reused_text_row;
10909 struct glyph_row *start_row;
10910 int start_vpos, min_y, max_y;
10912 #if GLYPH_DEBUG
10913 if (inhibit_try_window_reusing)
10914 return 0;
10915 #endif
10917 if (/* This function doesn't handle terminal frames. */
10918 !FRAME_WINDOW_P (f)
10919 /* Don't try to reuse the display if windows have been split
10920 or such. */
10921 || windows_or_buffers_changed
10922 || cursor_type_changed)
10923 return 0;
10925 /* Can't do this if region may have changed. */
10926 if ((!NILP (Vtransient_mark_mode)
10927 && !NILP (current_buffer->mark_active))
10928 || !NILP (w->region_showing)
10929 || !NILP (Vshow_trailing_whitespace))
10930 return 0;
10932 /* If top-line visibility has changed, give up. */
10933 if (WINDOW_WANTS_HEADER_LINE_P (w)
10934 != MATRIX_HEADER_LINE_ROW (w->current_matrix)->mode_line_p)
10935 return 0;
10937 /* Give up if old or new display is scrolled vertically. We could
10938 make this function handle this, but right now it doesn't. */
10939 start_row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
10940 if (w->vscroll || MATRIX_ROW_PARTIALLY_VISIBLE_P (start_row))
10941 return 0;
10943 /* The variable new_start now holds the new window start. The old
10944 start `start' can be determined from the current matrix. */
10945 SET_TEXT_POS_FROM_MARKER (new_start, w->start);
10946 start = start_row->start.pos;
10947 start_vpos = MATRIX_ROW_VPOS (start_row, w->current_matrix);
10949 /* Clear the desired matrix for the display below. */
10950 clear_glyph_matrix (w->desired_matrix);
10952 if (CHARPOS (new_start) <= CHARPOS (start))
10954 int first_row_y;
10956 /* Don't use this method if the display starts with an ellipsis
10957 displayed for invisible text. It's not easy to handle that case
10958 below, and it's certainly not worth the effort since this is
10959 not a frequent case. */
10960 if (in_ellipses_for_invisible_text_p (&start_row->start, w))
10961 return 0;
10963 IF_DEBUG (debug_method_add (w, "twu1"));
10965 /* Display up to a row that can be reused. The variable
10966 last_text_row is set to the last row displayed that displays
10967 text. Note that it.vpos == 0 if or if not there is a
10968 header-line; it's not the same as the MATRIX_ROW_VPOS! */
10969 start_display (&it, w, new_start);
10970 first_row_y = it.current_y;
10971 w->cursor.vpos = -1;
10972 last_text_row = last_reused_text_row = NULL;
10974 while (it.current_y < it.last_visible_y
10975 && IT_CHARPOS (it) < CHARPOS (start)
10976 && !fonts_changed_p)
10977 if (display_line (&it))
10978 last_text_row = it.glyph_row - 1;
10980 /* A value of current_y < last_visible_y means that we stopped
10981 at the previous window start, which in turn means that we
10982 have at least one reusable row. */
10983 if (it.current_y < it.last_visible_y)
10985 /* IT.vpos always starts from 0; it counts text lines. */
10986 nrows_scrolled = it.vpos;
10988 /* Find PT if not already found in the lines displayed. */
10989 if (w->cursor.vpos < 0)
10991 int dy = it.current_y - first_row_y;
10993 row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
10994 row = row_containing_pos (w, PT, row, NULL, dy);
10995 if (row)
10996 set_cursor_from_row (w, row, w->current_matrix, 0, 0,
10997 dy, nrows_scrolled);
10998 else
11000 clear_glyph_matrix (w->desired_matrix);
11001 return 0;
11005 /* Scroll the display. Do it before the current matrix is
11006 changed. The problem here is that update has not yet
11007 run, i.e. part of the current matrix is not up to date.
11008 scroll_run_hook will clear the cursor, and use the
11009 current matrix to get the height of the row the cursor is
11010 in. */
11011 run.current_y = first_row_y;
11012 run.desired_y = it.current_y;
11013 run.height = it.last_visible_y - it.current_y;
11015 if (run.height > 0 && run.current_y != run.desired_y)
11017 update_begin (f);
11018 rif->update_window_begin_hook (w);
11019 rif->clear_mouse_face (w);
11020 rif->scroll_run_hook (w, &run);
11021 rif->update_window_end_hook (w, 0, 0);
11022 update_end (f);
11025 /* Shift current matrix down by nrows_scrolled lines. */
11026 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
11027 rotate_matrix (w->current_matrix,
11028 start_vpos,
11029 MATRIX_ROW_VPOS (bottom_row, w->current_matrix),
11030 nrows_scrolled);
11032 /* Disable lines that must be updated. */
11033 for (i = 0; i < it.vpos; ++i)
11034 (start_row + i)->enabled_p = 0;
11036 /* Re-compute Y positions. */
11037 min_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w);
11038 max_y = it.last_visible_y;
11039 for (row = start_row + nrows_scrolled;
11040 row < bottom_row;
11041 ++row)
11043 row->y = it.current_y;
11044 row->visible_height = row->height;
11046 if (row->y < min_y)
11047 row->visible_height -= min_y - row->y;
11048 if (row->y + row->height > max_y)
11049 row->visible_height -= row->y + row->height - max_y;
11051 it.current_y += row->height;
11053 if (MATRIX_ROW_DISPLAYS_TEXT_P (row))
11054 last_reused_text_row = row;
11055 if (MATRIX_ROW_BOTTOM_Y (row) >= it.last_visible_y)
11056 break;
11059 /* Disable lines in the current matrix which are now
11060 below the window. */
11061 for (++row; row < bottom_row; ++row)
11062 row->enabled_p = 0;
11065 /* Update window_end_pos etc.; last_reused_text_row is the last
11066 reused row from the current matrix containing text, if any.
11067 The value of last_text_row is the last displayed line
11068 containing text. */
11069 if (last_reused_text_row)
11071 w->window_end_bytepos
11072 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_reused_text_row);
11073 w->window_end_pos
11074 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_reused_text_row));
11075 w->window_end_vpos
11076 = make_number (MATRIX_ROW_VPOS (last_reused_text_row,
11077 w->current_matrix));
11079 else if (last_text_row)
11081 w->window_end_bytepos
11082 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_text_row);
11083 w->window_end_pos
11084 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_text_row));
11085 w->window_end_vpos
11086 = make_number (MATRIX_ROW_VPOS (last_text_row, w->desired_matrix));
11088 else
11090 /* This window must be completely empty. */
11091 w->window_end_bytepos = 0;
11092 w->window_end_pos = w->window_end_vpos = make_number (0);
11094 w->window_end_valid = Qnil;
11096 /* Update hint: don't try scrolling again in update_window. */
11097 w->desired_matrix->no_scrolling_p = 1;
11099 #if GLYPH_DEBUG
11100 debug_method_add (w, "try_window_reusing_current_matrix 1");
11101 #endif
11102 return 1;
11104 else if (CHARPOS (new_start) > CHARPOS (start))
11106 struct glyph_row *pt_row, *row;
11107 struct glyph_row *first_reusable_row;
11108 struct glyph_row *first_row_to_display;
11109 int dy;
11110 int yb = window_text_bottom_y (w);
11112 /* Find the row starting at new_start, if there is one. Don't
11113 reuse a partially visible line at the end. */
11114 first_reusable_row = start_row;
11115 while (first_reusable_row->enabled_p
11116 && MATRIX_ROW_BOTTOM_Y (first_reusable_row) < yb
11117 && (MATRIX_ROW_START_CHARPOS (first_reusable_row)
11118 < CHARPOS (new_start)))
11119 ++first_reusable_row;
11121 /* Give up if there is no row to reuse. */
11122 if (MATRIX_ROW_BOTTOM_Y (first_reusable_row) >= yb
11123 || !first_reusable_row->enabled_p
11124 || (MATRIX_ROW_START_CHARPOS (first_reusable_row)
11125 != CHARPOS (new_start)))
11126 return 0;
11128 /* We can reuse fully visible rows beginning with
11129 first_reusable_row to the end of the window. Set
11130 first_row_to_display to the first row that cannot be reused.
11131 Set pt_row to the row containing point, if there is any. */
11132 pt_row = NULL;
11133 for (first_row_to_display = first_reusable_row;
11134 MATRIX_ROW_BOTTOM_Y (first_row_to_display) < yb;
11135 ++first_row_to_display)
11137 if (PT >= MATRIX_ROW_START_CHARPOS (first_row_to_display)
11138 && PT < MATRIX_ROW_END_CHARPOS (first_row_to_display))
11139 pt_row = first_row_to_display;
11142 /* Start displaying at the start of first_row_to_display. */
11143 xassert (first_row_to_display->y < yb);
11144 init_to_row_start (&it, w, first_row_to_display);
11146 nrows_scrolled = (MATRIX_ROW_VPOS (first_reusable_row, w->current_matrix)
11147 - start_vpos);
11148 it.vpos = (MATRIX_ROW_VPOS (first_row_to_display, w->current_matrix)
11149 - nrows_scrolled);
11150 it.current_y = (first_row_to_display->y - first_reusable_row->y
11151 + WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w));
11153 /* Display lines beginning with first_row_to_display in the
11154 desired matrix. Set last_text_row to the last row displayed
11155 that displays text. */
11156 it.glyph_row = MATRIX_ROW (w->desired_matrix, it.vpos);
11157 if (pt_row == NULL)
11158 w->cursor.vpos = -1;
11159 last_text_row = NULL;
11160 while (it.current_y < it.last_visible_y && !fonts_changed_p)
11161 if (display_line (&it))
11162 last_text_row = it.glyph_row - 1;
11164 /* Give up If point isn't in a row displayed or reused. */
11165 if (w->cursor.vpos < 0)
11167 clear_glyph_matrix (w->desired_matrix);
11168 return 0;
11171 /* If point is in a reused row, adjust y and vpos of the cursor
11172 position. */
11173 if (pt_row)
11175 w->cursor.vpos -= MATRIX_ROW_VPOS (first_reusable_row,
11176 w->current_matrix);
11177 w->cursor.y -= first_reusable_row->y;
11180 /* Scroll the display. */
11181 run.current_y = first_reusable_row->y;
11182 run.desired_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w);
11183 run.height = it.last_visible_y - run.current_y;
11184 dy = run.current_y - run.desired_y;
11186 if (run.height)
11188 struct frame *f = XFRAME (WINDOW_FRAME (w));
11189 update_begin (f);
11190 rif->update_window_begin_hook (w);
11191 rif->clear_mouse_face (w);
11192 rif->scroll_run_hook (w, &run);
11193 rif->update_window_end_hook (w, 0, 0);
11194 update_end (f);
11197 /* Adjust Y positions of reused rows. */
11198 bottom_row = MATRIX_BOTTOM_TEXT_ROW (w->current_matrix, w);
11199 min_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (w);
11200 max_y = it.last_visible_y;
11201 for (row = first_reusable_row; row < first_row_to_display; ++row)
11203 row->y -= dy;
11204 row->visible_height = row->height;
11205 if (row->y < min_y)
11206 row->visible_height -= min_y - row->y;
11207 if (row->y + row->height > max_y)
11208 row->visible_height -= row->y + row->height - max_y;
11211 /* Scroll the current matrix. */
11212 xassert (nrows_scrolled > 0);
11213 rotate_matrix (w->current_matrix,
11214 start_vpos,
11215 MATRIX_ROW_VPOS (bottom_row, w->current_matrix),
11216 -nrows_scrolled);
11218 /* Disable rows not reused. */
11219 for (row -= nrows_scrolled; row < bottom_row; ++row)
11220 row->enabled_p = 0;
11222 /* Adjust window end. A null value of last_text_row means that
11223 the window end is in reused rows which in turn means that
11224 only its vpos can have changed. */
11225 if (last_text_row)
11227 w->window_end_bytepos
11228 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_text_row);
11229 w->window_end_pos
11230 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_text_row));
11231 w->window_end_vpos
11232 = make_number (MATRIX_ROW_VPOS (last_text_row, w->desired_matrix));
11234 else
11236 w->window_end_vpos
11237 = make_number (XFASTINT (w->window_end_vpos) - nrows_scrolled);
11240 w->window_end_valid = Qnil;
11241 w->desired_matrix->no_scrolling_p = 1;
11243 #if GLYPH_DEBUG
11244 debug_method_add (w, "try_window_reusing_current_matrix 2");
11245 #endif
11246 return 1;
11249 return 0;
11254 /************************************************************************
11255 Window redisplay reusing current matrix when buffer has changed
11256 ************************************************************************/
11258 static struct glyph_row *find_last_unchanged_at_beg_row P_ ((struct window *));
11259 static struct glyph_row *find_first_unchanged_at_end_row P_ ((struct window *,
11260 int *, int *));
11261 static struct glyph_row *
11262 find_last_row_displaying_text P_ ((struct glyph_matrix *, struct it *,
11263 struct glyph_row *));
11266 /* Return the last row in MATRIX displaying text. If row START is
11267 non-null, start searching with that row. IT gives the dimensions
11268 of the display. Value is null if matrix is empty; otherwise it is
11269 a pointer to the row found. */
11271 static struct glyph_row *
11272 find_last_row_displaying_text (matrix, it, start)
11273 struct glyph_matrix *matrix;
11274 struct it *it;
11275 struct glyph_row *start;
11277 struct glyph_row *row, *row_found;
11279 /* Set row_found to the last row in IT->w's current matrix
11280 displaying text. The loop looks funny but think of partially
11281 visible lines. */
11282 row_found = NULL;
11283 row = start ? start : MATRIX_FIRST_TEXT_ROW (matrix);
11284 while (MATRIX_ROW_DISPLAYS_TEXT_P (row))
11286 xassert (row->enabled_p);
11287 row_found = row;
11288 if (MATRIX_ROW_BOTTOM_Y (row) >= it->last_visible_y)
11289 break;
11290 ++row;
11293 return row_found;
11297 /* Return the last row in the current matrix of W that is not affected
11298 by changes at the start of current_buffer that occurred since W's
11299 current matrix was built. Value is null if no such row exists.
11301 BEG_UNCHANGED us the number of characters unchanged at the start of
11302 current_buffer. BEG + BEG_UNCHANGED is the buffer position of the
11303 first changed character in current_buffer. Characters at positions <
11304 BEG + BEG_UNCHANGED are at the same buffer positions as they were
11305 when the current matrix was built. */
11307 static struct glyph_row *
11308 find_last_unchanged_at_beg_row (w)
11309 struct window *w;
11311 int first_changed_pos = BEG + BEG_UNCHANGED;
11312 struct glyph_row *row;
11313 struct glyph_row *row_found = NULL;
11314 int yb = window_text_bottom_y (w);
11316 /* Find the last row displaying unchanged text. */
11317 row = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
11318 while (MATRIX_ROW_DISPLAYS_TEXT_P (row)
11319 && MATRIX_ROW_START_CHARPOS (row) < first_changed_pos)
11321 if (/* If row ends before first_changed_pos, it is unchanged,
11322 except in some case. */
11323 MATRIX_ROW_END_CHARPOS (row) <= first_changed_pos
11324 /* When row ends in ZV and we write at ZV it is not
11325 unchanged. */
11326 && !row->ends_at_zv_p
11327 /* When first_changed_pos is the end of a continued line,
11328 row is not unchanged because it may be no longer
11329 continued. */
11330 && !(MATRIX_ROW_END_CHARPOS (row) == first_changed_pos
11331 && row->continued_p))
11332 row_found = row;
11334 /* Stop if last visible row. */
11335 if (MATRIX_ROW_BOTTOM_Y (row) >= yb)
11336 break;
11338 ++row;
11341 return row_found;
11345 /* Find the first glyph row in the current matrix of W that is not
11346 affected by changes at the end of current_buffer since the
11347 time W's current matrix was built.
11349 Return in *DELTA the number of chars by which buffer positions in
11350 unchanged text at the end of current_buffer must be adjusted.
11352 Return in *DELTA_BYTES the corresponding number of bytes.
11354 Value is null if no such row exists, i.e. all rows are affected by
11355 changes. */
11357 static struct glyph_row *
11358 find_first_unchanged_at_end_row (w, delta, delta_bytes)
11359 struct window *w;
11360 int *delta, *delta_bytes;
11362 struct glyph_row *row;
11363 struct glyph_row *row_found = NULL;
11365 *delta = *delta_bytes = 0;
11367 /* Display must not have been paused, otherwise the current matrix
11368 is not up to date. */
11369 if (NILP (w->window_end_valid))
11370 abort ();
11372 /* A value of window_end_pos >= END_UNCHANGED means that the window
11373 end is in the range of changed text. If so, there is no
11374 unchanged row at the end of W's current matrix. */
11375 if (XFASTINT (w->window_end_pos) >= END_UNCHANGED)
11376 return NULL;
11378 /* Set row to the last row in W's current matrix displaying text. */
11379 row = MATRIX_ROW (w->current_matrix, XFASTINT (w->window_end_vpos));
11381 /* If matrix is entirely empty, no unchanged row exists. */
11382 if (MATRIX_ROW_DISPLAYS_TEXT_P (row))
11384 /* The value of row is the last glyph row in the matrix having a
11385 meaningful buffer position in it. The end position of row
11386 corresponds to window_end_pos. This allows us to translate
11387 buffer positions in the current matrix to current buffer
11388 positions for characters not in changed text. */
11389 int Z_old = MATRIX_ROW_END_CHARPOS (row) + XFASTINT (w->window_end_pos);
11390 int Z_BYTE_old = MATRIX_ROW_END_BYTEPOS (row) + w->window_end_bytepos;
11391 int last_unchanged_pos, last_unchanged_pos_old;
11392 struct glyph_row *first_text_row
11393 = MATRIX_FIRST_TEXT_ROW (w->current_matrix);
11395 *delta = Z - Z_old;
11396 *delta_bytes = Z_BYTE - Z_BYTE_old;
11398 /* Set last_unchanged_pos to the buffer position of the last
11399 character in the buffer that has not been changed. Z is the
11400 index + 1 of the last character in current_buffer, i.e. by
11401 subtracting END_UNCHANGED we get the index of the last
11402 unchanged character, and we have to add BEG to get its buffer
11403 position. */
11404 last_unchanged_pos = Z - END_UNCHANGED + BEG;
11405 last_unchanged_pos_old = last_unchanged_pos - *delta;
11407 /* Search backward from ROW for a row displaying a line that
11408 starts at a minimum position >= last_unchanged_pos_old. */
11409 for (; row > first_text_row; --row)
11411 if (!row->enabled_p || !MATRIX_ROW_DISPLAYS_TEXT_P (row))
11412 abort ();
11414 if (MATRIX_ROW_START_CHARPOS (row) >= last_unchanged_pos_old)
11415 row_found = row;
11419 if (row_found && !MATRIX_ROW_DISPLAYS_TEXT_P (row_found))
11420 abort ();
11422 return row_found;
11426 /* Make sure that glyph rows in the current matrix of window W
11427 reference the same glyph memory as corresponding rows in the
11428 frame's frame matrix. This function is called after scrolling W's
11429 current matrix on a terminal frame in try_window_id and
11430 try_window_reusing_current_matrix. */
11432 static void
11433 sync_frame_with_window_matrix_rows (w)
11434 struct window *w;
11436 struct frame *f = XFRAME (w->frame);
11437 struct glyph_row *window_row, *window_row_end, *frame_row;
11439 /* Preconditions: W must be a leaf window and full-width. Its frame
11440 must have a frame matrix. */
11441 xassert (NILP (w->hchild) && NILP (w->vchild));
11442 xassert (WINDOW_FULL_WIDTH_P (w));
11443 xassert (!FRAME_WINDOW_P (f));
11445 /* If W is a full-width window, glyph pointers in W's current matrix
11446 have, by definition, to be the same as glyph pointers in the
11447 corresponding frame matrix. Note that frame matrices have no
11448 marginal areas (see build_frame_matrix). */
11449 window_row = w->current_matrix->rows;
11450 window_row_end = window_row + w->current_matrix->nrows;
11451 frame_row = f->current_matrix->rows + XFASTINT (w->top);
11452 while (window_row < window_row_end)
11454 struct glyph *start = window_row->glyphs[LEFT_MARGIN_AREA];
11455 struct glyph *end = window_row->glyphs[LAST_AREA];
11457 frame_row->glyphs[LEFT_MARGIN_AREA] = start;
11458 frame_row->glyphs[TEXT_AREA] = start;
11459 frame_row->glyphs[RIGHT_MARGIN_AREA] = end;
11460 frame_row->glyphs[LAST_AREA] = end;
11462 /* Disable frame rows whose corresponding window rows have
11463 been disabled in try_window_id. */
11464 if (!window_row->enabled_p)
11465 frame_row->enabled_p = 0;
11467 ++window_row, ++frame_row;
11472 /* Find the glyph row in window W containing CHARPOS. Consider all
11473 rows between START and END (not inclusive). END null means search
11474 all rows to the end of the display area of W. Value is the row
11475 containing CHARPOS or null. */
11477 struct glyph_row *
11478 row_containing_pos (w, charpos, start, end, dy)
11479 struct window *w;
11480 int charpos;
11481 struct glyph_row *start, *end;
11482 int dy;
11484 struct glyph_row *row = start;
11485 int last_y;
11487 /* If we happen to start on a header-line, skip that. */
11488 if (row->mode_line_p)
11489 ++row;
11491 if ((end && row >= end) || !row->enabled_p)
11492 return NULL;
11494 last_y = window_text_bottom_y (w) - dy;
11496 while ((end == NULL || row < end)
11497 && MATRIX_ROW_BOTTOM_Y (row) < last_y
11498 && (MATRIX_ROW_END_CHARPOS (row) < charpos
11499 || (MATRIX_ROW_END_CHARPOS (row) == charpos
11500 /* The end position of a row equals the start
11501 position of the next row. If CHARPOS is there, we
11502 would rather display it in the next line, except
11503 when this line ends in ZV. */
11504 && !row->ends_at_zv_p
11505 && !MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))))
11506 ++row;
11508 /* Give up if CHARPOS not found. */
11509 if ((end && row >= end)
11510 || charpos < MATRIX_ROW_START_CHARPOS (row)
11511 || charpos > MATRIX_ROW_END_CHARPOS (row))
11512 row = NULL;
11514 return row;
11518 /* Try to redisplay window W by reusing its existing display. W's
11519 current matrix must be up to date when this function is called,
11520 i.e. window_end_valid must not be nil.
11522 Value is
11524 1 if display has been updated
11525 0 if otherwise unsuccessful
11526 -1 if redisplay with same window start is known not to succeed
11528 The following steps are performed:
11530 1. Find the last row in the current matrix of W that is not
11531 affected by changes at the start of current_buffer. If no such row
11532 is found, give up.
11534 2. Find the first row in W's current matrix that is not affected by
11535 changes at the end of current_buffer. Maybe there is no such row.
11537 3. Display lines beginning with the row + 1 found in step 1 to the
11538 row found in step 2 or, if step 2 didn't find a row, to the end of
11539 the window.
11541 4. If cursor is not known to appear on the window, give up.
11543 5. If display stopped at the row found in step 2, scroll the
11544 display and current matrix as needed.
11546 6. Maybe display some lines at the end of W, if we must. This can
11547 happen under various circumstances, like a partially visible line
11548 becoming fully visible, or because newly displayed lines are displayed
11549 in smaller font sizes.
11551 7. Update W's window end information. */
11553 static int
11554 try_window_id (w)
11555 struct window *w;
11557 struct frame *f = XFRAME (w->frame);
11558 struct glyph_matrix *current_matrix = w->current_matrix;
11559 struct glyph_matrix *desired_matrix = w->desired_matrix;
11560 struct glyph_row *last_unchanged_at_beg_row;
11561 struct glyph_row *first_unchanged_at_end_row;
11562 struct glyph_row *row;
11563 struct glyph_row *bottom_row;
11564 int bottom_vpos;
11565 struct it it;
11566 int delta = 0, delta_bytes = 0, stop_pos, dvpos, dy;
11567 struct text_pos start_pos;
11568 struct run run;
11569 int first_unchanged_at_end_vpos = 0;
11570 struct glyph_row *last_text_row, *last_text_row_at_end;
11571 struct text_pos start;
11572 int first_changed_charpos, last_changed_charpos;
11574 #if GLYPH_DEBUG
11575 if (inhibit_try_window_id)
11576 return 0;
11577 #endif
11579 /* This is handy for debugging. */
11580 #if 0
11581 #define GIVE_UP(X) \
11582 do { \
11583 fprintf (stderr, "try_window_id give up %d\n", (X)); \
11584 return 0; \
11585 } while (0)
11586 #else
11587 #define GIVE_UP(X) return 0
11588 #endif
11590 SET_TEXT_POS_FROM_MARKER (start, w->start);
11592 /* Don't use this for mini-windows because these can show
11593 messages and mini-buffers, and we don't handle that here. */
11594 if (MINI_WINDOW_P (w))
11595 GIVE_UP (1);
11597 /* This flag is used to prevent redisplay optimizations. */
11598 if (windows_or_buffers_changed || cursor_type_changed)
11599 GIVE_UP (2);
11601 /* Verify that narrowing has not changed.
11602 Also verify that we were not told to prevent redisplay optimizations.
11603 It would be nice to further
11604 reduce the number of cases where this prevents try_window_id. */
11605 if (current_buffer->clip_changed
11606 || current_buffer->prevent_redisplay_optimizations_p)
11607 GIVE_UP (3);
11609 /* Window must either use window-based redisplay or be full width. */
11610 if (!FRAME_WINDOW_P (f)
11611 && (!line_ins_del_ok
11612 || !WINDOW_FULL_WIDTH_P (w)))
11613 GIVE_UP (4);
11615 /* Give up if point is not known NOT to appear in W. */
11616 if (PT < CHARPOS (start))
11617 GIVE_UP (5);
11619 /* Another way to prevent redisplay optimizations. */
11620 if (XFASTINT (w->last_modified) == 0)
11621 GIVE_UP (6);
11623 /* Verify that window is not hscrolled. */
11624 if (XFASTINT (w->hscroll) != 0)
11625 GIVE_UP (7);
11627 /* Verify that display wasn't paused. */
11628 if (NILP (w->window_end_valid))
11629 GIVE_UP (8);
11631 /* Can't use this if highlighting a region because a cursor movement
11632 will do more than just set the cursor. */
11633 if (!NILP (Vtransient_mark_mode)
11634 && !NILP (current_buffer->mark_active))
11635 GIVE_UP (9);
11637 /* Likewise if highlighting trailing whitespace. */
11638 if (!NILP (Vshow_trailing_whitespace))
11639 GIVE_UP (11);
11641 /* Likewise if showing a region. */
11642 if (!NILP (w->region_showing))
11643 GIVE_UP (10);
11645 /* Can use this if overlay arrow position and or string have changed. */
11646 if (!EQ (last_arrow_position, COERCE_MARKER (Voverlay_arrow_position))
11647 || !EQ (last_arrow_string, Voverlay_arrow_string))
11648 GIVE_UP (12);
11651 /* Make sure beg_unchanged and end_unchanged are up to date. Do it
11652 only if buffer has really changed. The reason is that the gap is
11653 initially at Z for freshly visited files. The code below would
11654 set end_unchanged to 0 in that case. */
11655 if (MODIFF > SAVE_MODIFF
11656 /* This seems to happen sometimes after saving a buffer. */
11657 || BEG_UNCHANGED + END_UNCHANGED > Z_BYTE)
11659 if (GPT - BEG < BEG_UNCHANGED)
11660 BEG_UNCHANGED = GPT - BEG;
11661 if (Z - GPT < END_UNCHANGED)
11662 END_UNCHANGED = Z - GPT;
11665 /* The position of the first and last character that has been changed. */
11666 first_changed_charpos = BEG + BEG_UNCHANGED;
11667 last_changed_charpos = Z - END_UNCHANGED;
11669 /* If window starts after a line end, and the last change is in
11670 front of that newline, then changes don't affect the display.
11671 This case happens with stealth-fontification. Note that although
11672 the display is unchanged, glyph positions in the matrix have to
11673 be adjusted, of course. */
11674 row = MATRIX_ROW (w->current_matrix, XFASTINT (w->window_end_vpos));
11675 if (MATRIX_ROW_DISPLAYS_TEXT_P (row)
11676 && ((last_changed_charpos < CHARPOS (start)
11677 && CHARPOS (start) == BEGV)
11678 || (last_changed_charpos < CHARPOS (start) - 1
11679 && FETCH_BYTE (BYTEPOS (start) - 1) == '\n')))
11681 int Z_old, delta, Z_BYTE_old, delta_bytes;
11682 struct glyph_row *r0;
11684 /* Compute how many chars/bytes have been added to or removed
11685 from the buffer. */
11686 Z_old = MATRIX_ROW_END_CHARPOS (row) + XFASTINT (w->window_end_pos);
11687 Z_BYTE_old = MATRIX_ROW_END_BYTEPOS (row) + w->window_end_bytepos;
11688 delta = Z - Z_old;
11689 delta_bytes = Z_BYTE - Z_BYTE_old;
11691 /* Give up if PT is not in the window. Note that it already has
11692 been checked at the start of try_window_id that PT is not in
11693 front of the window start. */
11694 if (PT >= MATRIX_ROW_END_CHARPOS (row) + delta)
11695 GIVE_UP (13);
11697 /* If window start is unchanged, we can reuse the whole matrix
11698 as is, after adjusting glyph positions. No need to compute
11699 the window end again, since its offset from Z hasn't changed. */
11700 r0 = MATRIX_FIRST_TEXT_ROW (current_matrix);
11701 if (CHARPOS (start) == MATRIX_ROW_START_CHARPOS (r0) + delta
11702 && BYTEPOS (start) == MATRIX_ROW_START_BYTEPOS (r0) + delta_bytes)
11704 /* Adjust positions in the glyph matrix. */
11705 if (delta || delta_bytes)
11707 struct glyph_row *r1
11708 = MATRIX_BOTTOM_TEXT_ROW (current_matrix, w);
11709 increment_matrix_positions (w->current_matrix,
11710 MATRIX_ROW_VPOS (r0, current_matrix),
11711 MATRIX_ROW_VPOS (r1, current_matrix),
11712 delta, delta_bytes);
11715 /* Set the cursor. */
11716 row = row_containing_pos (w, PT, r0, NULL, 0);
11717 set_cursor_from_row (w, row, current_matrix, 0, 0, 0, 0);
11718 return 1;
11722 /* Handle the case that changes are all below what is displayed in
11723 the window, and that PT is in the window. This shortcut cannot
11724 be taken if ZV is visible in the window, and text has been added
11725 there that is visible in the window. */
11726 if (first_changed_charpos >= MATRIX_ROW_END_CHARPOS (row)
11727 /* ZV is not visible in the window, or there are no
11728 changes at ZV, actually. */
11729 && (current_matrix->zv > MATRIX_ROW_END_CHARPOS (row)
11730 || first_changed_charpos == last_changed_charpos))
11732 struct glyph_row *r0;
11734 /* Give up if PT is not in the window. Note that it already has
11735 been checked at the start of try_window_id that PT is not in
11736 front of the window start. */
11737 if (PT >= MATRIX_ROW_END_CHARPOS (row))
11738 GIVE_UP (14);
11740 /* If window start is unchanged, we can reuse the whole matrix
11741 as is, without changing glyph positions since no text has
11742 been added/removed in front of the window end. */
11743 r0 = MATRIX_FIRST_TEXT_ROW (current_matrix);
11744 if (TEXT_POS_EQUAL_P (start, r0->start.pos))
11746 /* We have to compute the window end anew since text
11747 can have been added/removed after it. */
11748 w->window_end_pos
11749 = make_number (Z - MATRIX_ROW_END_CHARPOS (row));
11750 w->window_end_bytepos
11751 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
11753 /* Set the cursor. */
11754 row = row_containing_pos (w, PT, r0, NULL, 0);
11755 set_cursor_from_row (w, row, current_matrix, 0, 0, 0, 0);
11756 return 2;
11760 /* Give up if window start is in the changed area.
11762 The condition used to read
11764 (BEG_UNCHANGED + END_UNCHANGED != Z - BEG && ...)
11766 but why that was tested escapes me at the moment. */
11767 if (CHARPOS (start) >= first_changed_charpos
11768 && CHARPOS (start) <= last_changed_charpos)
11769 GIVE_UP (15);
11771 /* Check that window start agrees with the start of the first glyph
11772 row in its current matrix. Check this after we know the window
11773 start is not in changed text, otherwise positions would not be
11774 comparable. */
11775 row = MATRIX_FIRST_TEXT_ROW (current_matrix);
11776 if (!TEXT_POS_EQUAL_P (start, row->start.pos))
11777 GIVE_UP (16);
11779 /* Give up if the window ends in strings. Overlay strings
11780 at the end are difficult to handle, so don't try. */
11781 row = MATRIX_ROW (current_matrix, XFASTINT (w->window_end_vpos));
11782 if (MATRIX_ROW_START_CHARPOS (row) == MATRIX_ROW_END_CHARPOS (row))
11783 GIVE_UP (20);
11785 /* Compute the position at which we have to start displaying new
11786 lines. Some of the lines at the top of the window might be
11787 reusable because they are not displaying changed text. Find the
11788 last row in W's current matrix not affected by changes at the
11789 start of current_buffer. Value is null if changes start in the
11790 first line of window. */
11791 last_unchanged_at_beg_row = find_last_unchanged_at_beg_row (w);
11792 if (last_unchanged_at_beg_row)
11794 /* Avoid starting to display in the moddle of a character, a TAB
11795 for instance. This is easier than to set up the iterator
11796 exactly, and it's not a frequent case, so the additional
11797 effort wouldn't really pay off. */
11798 while ((MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (last_unchanged_at_beg_row)
11799 || last_unchanged_at_beg_row->ends_in_newline_from_string_p)
11800 && last_unchanged_at_beg_row > w->current_matrix->rows)
11801 --last_unchanged_at_beg_row;
11803 if (MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (last_unchanged_at_beg_row))
11804 GIVE_UP (17);
11806 if (init_to_row_end (&it, w, last_unchanged_at_beg_row) == 0)
11807 GIVE_UP (18);
11808 start_pos = it.current.pos;
11810 /* Start displaying new lines in the desired matrix at the same
11811 vpos we would use in the current matrix, i.e. below
11812 last_unchanged_at_beg_row. */
11813 it.vpos = 1 + MATRIX_ROW_VPOS (last_unchanged_at_beg_row,
11814 current_matrix);
11815 it.glyph_row = MATRIX_ROW (desired_matrix, it.vpos);
11816 it.current_y = MATRIX_ROW_BOTTOM_Y (last_unchanged_at_beg_row);
11818 xassert (it.hpos == 0 && it.current_x == 0);
11820 else
11822 /* There are no reusable lines at the start of the window.
11823 Start displaying in the first line. */
11824 start_display (&it, w, start);
11825 start_pos = it.current.pos;
11828 /* Find the first row that is not affected by changes at the end of
11829 the buffer. Value will be null if there is no unchanged row, in
11830 which case we must redisplay to the end of the window. delta
11831 will be set to the value by which buffer positions beginning with
11832 first_unchanged_at_end_row have to be adjusted due to text
11833 changes. */
11834 first_unchanged_at_end_row
11835 = find_first_unchanged_at_end_row (w, &delta, &delta_bytes);
11836 IF_DEBUG (debug_delta = delta);
11837 IF_DEBUG (debug_delta_bytes = delta_bytes);
11839 /* Set stop_pos to the buffer position up to which we will have to
11840 display new lines. If first_unchanged_at_end_row != NULL, this
11841 is the buffer position of the start of the line displayed in that
11842 row. For first_unchanged_at_end_row == NULL, use 0 to indicate
11843 that we don't stop at a buffer position. */
11844 stop_pos = 0;
11845 if (first_unchanged_at_end_row)
11847 xassert (last_unchanged_at_beg_row == NULL
11848 || first_unchanged_at_end_row >= last_unchanged_at_beg_row);
11850 /* If this is a continuation line, move forward to the next one
11851 that isn't. Changes in lines above affect this line.
11852 Caution: this may move first_unchanged_at_end_row to a row
11853 not displaying text. */
11854 while (MATRIX_ROW_CONTINUATION_LINE_P (first_unchanged_at_end_row)
11855 && MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row)
11856 && (MATRIX_ROW_BOTTOM_Y (first_unchanged_at_end_row)
11857 < it.last_visible_y))
11858 ++first_unchanged_at_end_row;
11860 if (!MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row)
11861 || (MATRIX_ROW_BOTTOM_Y (first_unchanged_at_end_row)
11862 >= it.last_visible_y))
11863 first_unchanged_at_end_row = NULL;
11864 else
11866 stop_pos = (MATRIX_ROW_START_CHARPOS (first_unchanged_at_end_row)
11867 + delta);
11868 first_unchanged_at_end_vpos
11869 = MATRIX_ROW_VPOS (first_unchanged_at_end_row, current_matrix);
11870 xassert (stop_pos >= Z - END_UNCHANGED);
11873 else if (last_unchanged_at_beg_row == NULL)
11874 GIVE_UP (19);
11877 #if GLYPH_DEBUG
11879 /* Either there is no unchanged row at the end, or the one we have
11880 now displays text. This is a necessary condition for the window
11881 end pos calculation at the end of this function. */
11882 xassert (first_unchanged_at_end_row == NULL
11883 || MATRIX_ROW_DISPLAYS_TEXT_P (first_unchanged_at_end_row));
11885 debug_last_unchanged_at_beg_vpos
11886 = (last_unchanged_at_beg_row
11887 ? MATRIX_ROW_VPOS (last_unchanged_at_beg_row, current_matrix)
11888 : -1);
11889 debug_first_unchanged_at_end_vpos = first_unchanged_at_end_vpos;
11891 #endif /* GLYPH_DEBUG != 0 */
11894 /* Display new lines. Set last_text_row to the last new line
11895 displayed which has text on it, i.e. might end up as being the
11896 line where the window_end_vpos is. */
11897 w->cursor.vpos = -1;
11898 last_text_row = NULL;
11899 overlay_arrow_seen = 0;
11900 while (it.current_y < it.last_visible_y
11901 && !fonts_changed_p
11902 && (first_unchanged_at_end_row == NULL
11903 || IT_CHARPOS (it) < stop_pos))
11905 if (display_line (&it))
11906 last_text_row = it.glyph_row - 1;
11909 if (fonts_changed_p)
11910 return -1;
11913 /* Compute differences in buffer positions, y-positions etc. for
11914 lines reused at the bottom of the window. Compute what we can
11915 scroll. */
11916 if (first_unchanged_at_end_row
11917 /* No lines reused because we displayed everything up to the
11918 bottom of the window. */
11919 && it.current_y < it.last_visible_y)
11921 dvpos = (it.vpos
11922 - MATRIX_ROW_VPOS (first_unchanged_at_end_row,
11923 current_matrix));
11924 dy = it.current_y - first_unchanged_at_end_row->y;
11925 run.current_y = first_unchanged_at_end_row->y;
11926 run.desired_y = run.current_y + dy;
11927 run.height = it.last_visible_y - max (run.current_y, run.desired_y);
11929 else
11931 delta = dvpos = dy = run.current_y = run.desired_y = run.height = 0;
11932 first_unchanged_at_end_row = NULL;
11934 IF_DEBUG (debug_dvpos = dvpos; debug_dy = dy);
11937 /* Find the cursor if not already found. We have to decide whether
11938 PT will appear on this window (it sometimes doesn't, but this is
11939 not a very frequent case.) This decision has to be made before
11940 the current matrix is altered. A value of cursor.vpos < 0 means
11941 that PT is either in one of the lines beginning at
11942 first_unchanged_at_end_row or below the window. Don't care for
11943 lines that might be displayed later at the window end; as
11944 mentioned, this is not a frequent case. */
11945 if (w->cursor.vpos < 0)
11947 /* Cursor in unchanged rows at the top? */
11948 if (PT < CHARPOS (start_pos)
11949 && last_unchanged_at_beg_row)
11951 row = row_containing_pos (w, PT,
11952 MATRIX_FIRST_TEXT_ROW (w->current_matrix),
11953 last_unchanged_at_beg_row + 1, 0);
11954 if (row)
11955 set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
11958 /* Start from first_unchanged_at_end_row looking for PT. */
11959 else if (first_unchanged_at_end_row)
11961 row = row_containing_pos (w, PT - delta,
11962 first_unchanged_at_end_row, NULL, 0);
11963 if (row)
11964 set_cursor_from_row (w, row, w->current_matrix, delta,
11965 delta_bytes, dy, dvpos);
11968 /* Give up if cursor was not found. */
11969 if (w->cursor.vpos < 0)
11971 clear_glyph_matrix (w->desired_matrix);
11972 return -1;
11976 /* Don't let the cursor end in the scroll margins. */
11978 int this_scroll_margin, cursor_height;
11980 this_scroll_margin = max (0, scroll_margin);
11981 this_scroll_margin = min (this_scroll_margin,
11982 XFASTINT (w->height) / 4);
11983 this_scroll_margin *= CANON_Y_UNIT (it.f);
11984 cursor_height = MATRIX_ROW (w->desired_matrix, w->cursor.vpos)->height;
11986 if ((w->cursor.y < this_scroll_margin
11987 && CHARPOS (start) > BEGV)
11988 /* Don't take scroll margin into account at the bottom because
11989 old redisplay didn't do it either. */
11990 || w->cursor.y + cursor_height > it.last_visible_y)
11992 w->cursor.vpos = -1;
11993 clear_glyph_matrix (w->desired_matrix);
11994 return -1;
11998 /* Scroll the display. Do it before changing the current matrix so
11999 that xterm.c doesn't get confused about where the cursor glyph is
12000 found. */
12001 if (dy && run.height)
12003 update_begin (f);
12005 if (FRAME_WINDOW_P (f))
12007 rif->update_window_begin_hook (w);
12008 rif->clear_mouse_face (w);
12009 rif->scroll_run_hook (w, &run);
12010 rif->update_window_end_hook (w, 0, 0);
12012 else
12014 /* Terminal frame. In this case, dvpos gives the number of
12015 lines to scroll by; dvpos < 0 means scroll up. */
12016 int first_unchanged_at_end_vpos
12017 = MATRIX_ROW_VPOS (first_unchanged_at_end_row, w->current_matrix);
12018 int from = XFASTINT (w->top) + first_unchanged_at_end_vpos;
12019 int end = (XFASTINT (w->top)
12020 + (WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0)
12021 + window_internal_height (w));
12023 /* Perform the operation on the screen. */
12024 if (dvpos > 0)
12026 /* Scroll last_unchanged_at_beg_row to the end of the
12027 window down dvpos lines. */
12028 set_terminal_window (end);
12030 /* On dumb terminals delete dvpos lines at the end
12031 before inserting dvpos empty lines. */
12032 if (!scroll_region_ok)
12033 ins_del_lines (end - dvpos, -dvpos);
12035 /* Insert dvpos empty lines in front of
12036 last_unchanged_at_beg_row. */
12037 ins_del_lines (from, dvpos);
12039 else if (dvpos < 0)
12041 /* Scroll up last_unchanged_at_beg_vpos to the end of
12042 the window to last_unchanged_at_beg_vpos - |dvpos|. */
12043 set_terminal_window (end);
12045 /* Delete dvpos lines in front of
12046 last_unchanged_at_beg_vpos. ins_del_lines will set
12047 the cursor to the given vpos and emit |dvpos| delete
12048 line sequences. */
12049 ins_del_lines (from + dvpos, dvpos);
12051 /* On a dumb terminal insert dvpos empty lines at the
12052 end. */
12053 if (!scroll_region_ok)
12054 ins_del_lines (end + dvpos, -dvpos);
12057 set_terminal_window (0);
12060 update_end (f);
12063 /* Shift reused rows of the current matrix to the right position.
12064 BOTTOM_ROW is the last + 1 row in the current matrix reserved for
12065 text. */
12066 bottom_row = MATRIX_BOTTOM_TEXT_ROW (current_matrix, w);
12067 bottom_vpos = MATRIX_ROW_VPOS (bottom_row, current_matrix);
12068 if (dvpos < 0)
12070 rotate_matrix (current_matrix, first_unchanged_at_end_vpos + dvpos,
12071 bottom_vpos, dvpos);
12072 enable_glyph_matrix_rows (current_matrix, bottom_vpos + dvpos,
12073 bottom_vpos, 0);
12075 else if (dvpos > 0)
12077 rotate_matrix (current_matrix, first_unchanged_at_end_vpos,
12078 bottom_vpos, dvpos);
12079 enable_glyph_matrix_rows (current_matrix, first_unchanged_at_end_vpos,
12080 first_unchanged_at_end_vpos + dvpos, 0);
12083 /* For frame-based redisplay, make sure that current frame and window
12084 matrix are in sync with respect to glyph memory. */
12085 if (!FRAME_WINDOW_P (f))
12086 sync_frame_with_window_matrix_rows (w);
12088 /* Adjust buffer positions in reused rows. */
12089 if (delta)
12090 increment_matrix_positions (current_matrix,
12091 first_unchanged_at_end_vpos + dvpos,
12092 bottom_vpos, delta, delta_bytes);
12094 /* Adjust Y positions. */
12095 if (dy)
12096 shift_glyph_matrix (w, current_matrix,
12097 first_unchanged_at_end_vpos + dvpos,
12098 bottom_vpos, dy);
12100 if (first_unchanged_at_end_row)
12101 first_unchanged_at_end_row += dvpos;
12103 /* If scrolling up, there may be some lines to display at the end of
12104 the window. */
12105 last_text_row_at_end = NULL;
12106 if (dy < 0)
12108 /* Scrolling up can leave for example a partially visible line
12109 at the end of the window to be redisplayed. */
12110 /* Set last_row to the glyph row in the current matrix where the
12111 window end line is found. It has been moved up or down in
12112 the matrix by dvpos. */
12113 int last_vpos = XFASTINT (w->window_end_vpos) + dvpos;
12114 struct glyph_row *last_row = MATRIX_ROW (current_matrix, last_vpos);
12116 /* If last_row is the window end line, it should display text. */
12117 xassert (last_row->displays_text_p);
12119 /* If window end line was partially visible before, begin
12120 displaying at that line. Otherwise begin displaying with the
12121 line following it. */
12122 if (MATRIX_ROW_BOTTOM_Y (last_row) - dy >= it.last_visible_y)
12124 init_to_row_start (&it, w, last_row);
12125 it.vpos = last_vpos;
12126 it.current_y = last_row->y;
12128 else
12130 init_to_row_end (&it, w, last_row);
12131 it.vpos = 1 + last_vpos;
12132 it.current_y = MATRIX_ROW_BOTTOM_Y (last_row);
12133 ++last_row;
12136 /* We may start in a continuation line. If so, we have to
12137 get the right continuation_lines_width and current_x. */
12138 it.continuation_lines_width = last_row->continuation_lines_width;
12139 it.hpos = it.current_x = 0;
12141 /* Display the rest of the lines at the window end. */
12142 it.glyph_row = MATRIX_ROW (desired_matrix, it.vpos);
12143 while (it.current_y < it.last_visible_y
12144 && !fonts_changed_p)
12146 /* Is it always sure that the display agrees with lines in
12147 the current matrix? I don't think so, so we mark rows
12148 displayed invalid in the current matrix by setting their
12149 enabled_p flag to zero. */
12150 MATRIX_ROW (w->current_matrix, it.vpos)->enabled_p = 0;
12151 if (display_line (&it))
12152 last_text_row_at_end = it.glyph_row - 1;
12156 /* Update window_end_pos and window_end_vpos. */
12157 if (first_unchanged_at_end_row
12158 && first_unchanged_at_end_row->y < it.last_visible_y
12159 && !last_text_row_at_end)
12161 /* Window end line if one of the preserved rows from the current
12162 matrix. Set row to the last row displaying text in current
12163 matrix starting at first_unchanged_at_end_row, after
12164 scrolling. */
12165 xassert (first_unchanged_at_end_row->displays_text_p);
12166 row = find_last_row_displaying_text (w->current_matrix, &it,
12167 first_unchanged_at_end_row);
12168 xassert (row && MATRIX_ROW_DISPLAYS_TEXT_P (row));
12170 w->window_end_pos = make_number (Z - MATRIX_ROW_END_CHARPOS (row));
12171 w->window_end_bytepos = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
12172 w->window_end_vpos
12173 = make_number (MATRIX_ROW_VPOS (row, w->current_matrix));
12174 xassert (w->window_end_bytepos >= 0);
12175 IF_DEBUG (debug_method_add (w, "A"));
12177 else if (last_text_row_at_end)
12179 w->window_end_pos
12180 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_text_row_at_end));
12181 w->window_end_bytepos
12182 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_text_row_at_end);
12183 w->window_end_vpos
12184 = make_number (MATRIX_ROW_VPOS (last_text_row_at_end, desired_matrix));
12185 xassert (w->window_end_bytepos >= 0);
12186 IF_DEBUG (debug_method_add (w, "B"));
12188 else if (last_text_row)
12190 /* We have displayed either to the end of the window or at the
12191 end of the window, i.e. the last row with text is to be found
12192 in the desired matrix. */
12193 w->window_end_pos
12194 = make_number (Z - MATRIX_ROW_END_CHARPOS (last_text_row));
12195 w->window_end_bytepos
12196 = Z_BYTE - MATRIX_ROW_END_BYTEPOS (last_text_row);
12197 w->window_end_vpos
12198 = make_number (MATRIX_ROW_VPOS (last_text_row, desired_matrix));
12199 xassert (w->window_end_bytepos >= 0);
12201 else if (first_unchanged_at_end_row == NULL
12202 && last_text_row == NULL
12203 && last_text_row_at_end == NULL)
12205 /* Displayed to end of window, but no line containing text was
12206 displayed. Lines were deleted at the end of the window. */
12207 int first_vpos = WINDOW_WANTS_HEADER_LINE_P (w) ? 1 : 0;
12208 int vpos = XFASTINT (w->window_end_vpos);
12209 struct glyph_row *current_row = current_matrix->rows + vpos;
12210 struct glyph_row *desired_row = desired_matrix->rows + vpos;
12212 for (row = NULL;
12213 row == NULL && vpos >= first_vpos;
12214 --vpos, --current_row, --desired_row)
12216 if (desired_row->enabled_p)
12218 if (desired_row->displays_text_p)
12219 row = desired_row;
12221 else if (current_row->displays_text_p)
12222 row = current_row;
12225 xassert (row != NULL);
12226 w->window_end_vpos = make_number (vpos + 1);
12227 w->window_end_pos = make_number (Z - MATRIX_ROW_END_CHARPOS (row));
12228 w->window_end_bytepos = Z_BYTE - MATRIX_ROW_END_BYTEPOS (row);
12229 xassert (w->window_end_bytepos >= 0);
12230 IF_DEBUG (debug_method_add (w, "C"));
12232 else
12233 abort ();
12235 #if 0 /* This leads to problems, for instance when the cursor is
12236 at ZV, and the cursor line displays no text. */
12237 /* Disable rows below what's displayed in the window. This makes
12238 debugging easier. */
12239 enable_glyph_matrix_rows (current_matrix,
12240 XFASTINT (w->window_end_vpos) + 1,
12241 bottom_vpos, 0);
12242 #endif
12244 IF_DEBUG (debug_end_pos = XFASTINT (w->window_end_pos);
12245 debug_end_vpos = XFASTINT (w->window_end_vpos));
12247 /* Record that display has not been completed. */
12248 w->window_end_valid = Qnil;
12249 w->desired_matrix->no_scrolling_p = 1;
12250 return 3;
12252 #undef GIVE_UP
12257 /***********************************************************************
12258 More debugging support
12259 ***********************************************************************/
12261 #if GLYPH_DEBUG
12263 void dump_glyph_row P_ ((struct glyph_row *, int, int));
12264 void dump_glyph_matrix P_ ((struct glyph_matrix *, int));
12265 void dump_glyph P_ ((struct glyph_row *, struct glyph *, int));
12268 /* Dump the contents of glyph matrix MATRIX on stderr.
12270 GLYPHS 0 means don't show glyph contents.
12271 GLYPHS 1 means show glyphs in short form
12272 GLYPHS > 1 means show glyphs in long form. */
12274 void
12275 dump_glyph_matrix (matrix, glyphs)
12276 struct glyph_matrix *matrix;
12277 int glyphs;
12279 int i;
12280 for (i = 0; i < matrix->nrows; ++i)
12281 dump_glyph_row (MATRIX_ROW (matrix, i), i, glyphs);
12285 /* Dump contents of glyph GLYPH to stderr. ROW and AREA are
12286 the glyph row and area where the glyph comes from. */
12288 void
12289 dump_glyph (row, glyph, area)
12290 struct glyph_row *row;
12291 struct glyph *glyph;
12292 int area;
12294 if (glyph->type == CHAR_GLYPH)
12296 fprintf (stderr,
12297 " %5d %4c %6d %c %3d 0x%05x %c %4d %1.1d%1.1d\n",
12298 glyph - row->glyphs[TEXT_AREA],
12299 'C',
12300 glyph->charpos,
12301 (BUFFERP (glyph->object)
12302 ? 'B'
12303 : (STRINGP (glyph->object)
12304 ? 'S'
12305 : '-')),
12306 glyph->pixel_width,
12307 glyph->u.ch,
12308 (glyph->u.ch < 0x80 && glyph->u.ch >= ' '
12309 ? glyph->u.ch
12310 : '.'),
12311 glyph->face_id,
12312 glyph->left_box_line_p,
12313 glyph->right_box_line_p);
12315 else if (glyph->type == STRETCH_GLYPH)
12317 fprintf (stderr,
12318 " %5d %4c %6d %c %3d 0x%05x %c %4d %1.1d%1.1d\n",
12319 glyph - row->glyphs[TEXT_AREA],
12320 'S',
12321 glyph->charpos,
12322 (BUFFERP (glyph->object)
12323 ? 'B'
12324 : (STRINGP (glyph->object)
12325 ? 'S'
12326 : '-')),
12327 glyph->pixel_width,
12329 '.',
12330 glyph->face_id,
12331 glyph->left_box_line_p,
12332 glyph->right_box_line_p);
12334 else if (glyph->type == IMAGE_GLYPH)
12336 fprintf (stderr,
12337 " %5d %4c %6d %c %3d 0x%05x %c %4d %1.1d%1.1d\n",
12338 glyph - row->glyphs[TEXT_AREA],
12339 'I',
12340 glyph->charpos,
12341 (BUFFERP (glyph->object)
12342 ? 'B'
12343 : (STRINGP (glyph->object)
12344 ? 'S'
12345 : '-')),
12346 glyph->pixel_width,
12347 glyph->u.img_id,
12348 '.',
12349 glyph->face_id,
12350 glyph->left_box_line_p,
12351 glyph->right_box_line_p);
12356 /* Dump the contents of glyph row at VPOS in MATRIX to stderr.
12357 GLYPHS 0 means don't show glyph contents.
12358 GLYPHS 1 means show glyphs in short form
12359 GLYPHS > 1 means show glyphs in long form. */
12361 void
12362 dump_glyph_row (row, vpos, glyphs)
12363 struct glyph_row *row;
12364 int vpos, glyphs;
12366 if (glyphs != 1)
12368 fprintf (stderr, "Row Start End Used oEI><O\\CTZFesm X Y W H V A P\n");
12369 fprintf (stderr, "=======================================================================\n");
12371 fprintf (stderr, "%3d %5d %5d %4d %1.1d%1.1d%1.1d%1.1d%1.1d\
12372 %1.1d%1.1d%1.1d%1.1d%1.1d%1.1d%1.1d%1.1d %4d %4d %4d %4d %4d %4d %4d\n",
12373 vpos,
12374 MATRIX_ROW_START_CHARPOS (row),
12375 MATRIX_ROW_END_CHARPOS (row),
12376 row->used[TEXT_AREA],
12377 row->contains_overlapping_glyphs_p,
12378 row->enabled_p,
12379 row->truncated_on_left_p,
12380 row->truncated_on_right_p,
12381 row->overlay_arrow_p,
12382 row->continued_p,
12383 MATRIX_ROW_CONTINUATION_LINE_P (row),
12384 row->displays_text_p,
12385 row->ends_at_zv_p,
12386 row->fill_line_p,
12387 row->ends_in_middle_of_char_p,
12388 row->starts_in_middle_of_char_p,
12389 row->mouse_face_p,
12390 row->x,
12391 row->y,
12392 row->pixel_width,
12393 row->height,
12394 row->visible_height,
12395 row->ascent,
12396 row->phys_ascent);
12397 fprintf (stderr, "%9d %5d\t%5d\n", row->start.overlay_string_index,
12398 row->end.overlay_string_index,
12399 row->continuation_lines_width);
12400 fprintf (stderr, "%9d %5d\n",
12401 CHARPOS (row->start.string_pos),
12402 CHARPOS (row->end.string_pos));
12403 fprintf (stderr, "%9d %5d\n", row->start.dpvec_index,
12404 row->end.dpvec_index);
12407 if (glyphs > 1)
12409 int area;
12411 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
12413 struct glyph *glyph = row->glyphs[area];
12414 struct glyph *glyph_end = glyph + row->used[area];
12416 /* Glyph for a line end in text. */
12417 if (area == TEXT_AREA && glyph == glyph_end && glyph->charpos > 0)
12418 ++glyph_end;
12420 if (glyph < glyph_end)
12421 fprintf (stderr, " Glyph Type Pos O W Code C Face LR\n");
12423 for (; glyph < glyph_end; ++glyph)
12424 dump_glyph (row, glyph, area);
12427 else if (glyphs == 1)
12429 int area;
12431 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
12433 char *s = (char *) alloca (row->used[area] + 1);
12434 int i;
12436 for (i = 0; i < row->used[area]; ++i)
12438 struct glyph *glyph = row->glyphs[area] + i;
12439 if (glyph->type == CHAR_GLYPH
12440 && glyph->u.ch < 0x80
12441 && glyph->u.ch >= ' ')
12442 s[i] = glyph->u.ch;
12443 else
12444 s[i] = '.';
12447 s[i] = '\0';
12448 fprintf (stderr, "%3d: (%d) '%s'\n", vpos, row->enabled_p, s);
12454 DEFUN ("dump-glyph-matrix", Fdump_glyph_matrix,
12455 Sdump_glyph_matrix, 0, 1, "p",
12456 doc: /* Dump the current matrix of the selected window to stderr.
12457 Shows contents of glyph row structures. With non-nil
12458 parameter GLYPHS, dump glyphs as well. If GLYPHS is 1 show
12459 glyphs in short form, otherwise show glyphs in long form. */)
12460 (glyphs)
12461 Lisp_Object glyphs;
12463 struct window *w = XWINDOW (selected_window);
12464 struct buffer *buffer = XBUFFER (w->buffer);
12466 fprintf (stderr, "PT = %d, BEGV = %d. ZV = %d\n",
12467 BUF_PT (buffer), BUF_BEGV (buffer), BUF_ZV (buffer));
12468 fprintf (stderr, "Cursor x = %d, y = %d, hpos = %d, vpos = %d\n",
12469 w->cursor.x, w->cursor.y, w->cursor.hpos, w->cursor.vpos);
12470 fprintf (stderr, "=============================================\n");
12471 dump_glyph_matrix (w->current_matrix,
12472 NILP (glyphs) ? 0 : XINT (glyphs));
12473 return Qnil;
12477 DEFUN ("dump-frame-glyph-matrix", Fdump_frame_glyph_matrix,
12478 Sdump_frame_glyph_matrix, 0, 0, "", doc: /* */)
12481 struct frame *f = XFRAME (selected_frame);
12482 dump_glyph_matrix (f->current_matrix, 1);
12483 return Qnil;
12487 DEFUN ("dump-glyph-row", Fdump_glyph_row, Sdump_glyph_row, 1, 2, "",
12488 doc: /* Dump glyph row ROW to stderr.
12489 GLYPH 0 means don't dump glyphs.
12490 GLYPH 1 means dump glyphs in short form.
12491 GLYPH > 1 or omitted means dump glyphs in long form. */)
12492 (row, glyphs)
12493 Lisp_Object row, glyphs;
12495 struct glyph_matrix *matrix;
12496 int vpos;
12498 CHECK_NUMBER (row);
12499 matrix = XWINDOW (selected_window)->current_matrix;
12500 vpos = XINT (row);
12501 if (vpos >= 0 && vpos < matrix->nrows)
12502 dump_glyph_row (MATRIX_ROW (matrix, vpos),
12503 vpos,
12504 INTEGERP (glyphs) ? XINT (glyphs) : 2);
12505 return Qnil;
12509 DEFUN ("dump-tool-bar-row", Fdump_tool_bar_row, Sdump_tool_bar_row, 1, 2, "",
12510 doc: /* Dump glyph row ROW of the tool-bar of the current frame to stderr.
12511 GLYPH 0 means don't dump glyphs.
12512 GLYPH 1 means dump glyphs in short form.
12513 GLYPH > 1 or omitted means dump glyphs in long form. */)
12514 (row, glyphs)
12515 Lisp_Object row, glyphs;
12517 struct frame *sf = SELECTED_FRAME ();
12518 struct glyph_matrix *m = XWINDOW (sf->tool_bar_window)->current_matrix;
12519 int vpos;
12521 CHECK_NUMBER (row);
12522 vpos = XINT (row);
12523 if (vpos >= 0 && vpos < m->nrows)
12524 dump_glyph_row (MATRIX_ROW (m, vpos), vpos,
12525 INTEGERP (glyphs) ? XINT (glyphs) : 2);
12526 return Qnil;
12530 DEFUN ("trace-redisplay", Ftrace_redisplay, Strace_redisplay, 0, 1, "P",
12531 doc: /* Toggle tracing of redisplay.
12532 With ARG, turn tracing on if and only if ARG is positive. */)
12533 (arg)
12534 Lisp_Object arg;
12536 if (NILP (arg))
12537 trace_redisplay_p = !trace_redisplay_p;
12538 else
12540 arg = Fprefix_numeric_value (arg);
12541 trace_redisplay_p = XINT (arg) > 0;
12544 return Qnil;
12548 DEFUN ("trace-to-stderr", Ftrace_to_stderr, Strace_to_stderr, 1, MANY, "",
12549 doc: /* Like `format', but print result to stderr.
12550 usage: (trace-to-stderr STRING &rest OBJECTS) */)
12551 (nargs, args)
12552 int nargs;
12553 Lisp_Object *args;
12555 Lisp_Object s = Fformat (nargs, args);
12556 fprintf (stderr, "%s", SDATA (s));
12557 return Qnil;
12560 #endif /* GLYPH_DEBUG */
12564 /***********************************************************************
12565 Building Desired Matrix Rows
12566 ***********************************************************************/
12568 /* Return a temporary glyph row holding the glyphs of an overlay
12569 arrow. Only used for non-window-redisplay windows. */
12571 static struct glyph_row *
12572 get_overlay_arrow_glyph_row (w)
12573 struct window *w;
12575 struct frame *f = XFRAME (WINDOW_FRAME (w));
12576 struct buffer *buffer = XBUFFER (w->buffer);
12577 struct buffer *old = current_buffer;
12578 const unsigned char *arrow_string = SDATA (Voverlay_arrow_string);
12579 int arrow_len = SCHARS (Voverlay_arrow_string);
12580 const unsigned char *arrow_end = arrow_string + arrow_len;
12581 const unsigned char *p;
12582 struct it it;
12583 int multibyte_p;
12584 int n_glyphs_before;
12586 set_buffer_temp (buffer);
12587 init_iterator (&it, w, -1, -1, &scratch_glyph_row, DEFAULT_FACE_ID);
12588 it.glyph_row->used[TEXT_AREA] = 0;
12589 SET_TEXT_POS (it.position, 0, 0);
12591 multibyte_p = !NILP (buffer->enable_multibyte_characters);
12592 p = arrow_string;
12593 while (p < arrow_end)
12595 Lisp_Object face, ilisp;
12597 /* Get the next character. */
12598 if (multibyte_p)
12599 it.c = string_char_and_length (p, arrow_len, &it.len);
12600 else
12601 it.c = *p, it.len = 1;
12602 p += it.len;
12604 /* Get its face. */
12605 ilisp = make_number (p - arrow_string);
12606 face = Fget_text_property (ilisp, Qface, Voverlay_arrow_string);
12607 it.face_id = compute_char_face (f, it.c, face);
12609 /* Compute its width, get its glyphs. */
12610 n_glyphs_before = it.glyph_row->used[TEXT_AREA];
12611 SET_TEXT_POS (it.position, -1, -1);
12612 PRODUCE_GLYPHS (&it);
12614 /* If this character doesn't fit any more in the line, we have
12615 to remove some glyphs. */
12616 if (it.current_x > it.last_visible_x)
12618 it.glyph_row->used[TEXT_AREA] = n_glyphs_before;
12619 break;
12623 set_buffer_temp (old);
12624 return it.glyph_row;
12628 /* Insert truncation glyphs at the start of IT->glyph_row. Truncation
12629 glyphs are only inserted for terminal frames since we can't really
12630 win with truncation glyphs when partially visible glyphs are
12631 involved. Which glyphs to insert is determined by
12632 produce_special_glyphs. */
12634 static void
12635 insert_left_trunc_glyphs (it)
12636 struct it *it;
12638 struct it truncate_it;
12639 struct glyph *from, *end, *to, *toend;
12641 xassert (!FRAME_WINDOW_P (it->f));
12643 /* Get the truncation glyphs. */
12644 truncate_it = *it;
12645 truncate_it.current_x = 0;
12646 truncate_it.face_id = DEFAULT_FACE_ID;
12647 truncate_it.glyph_row = &scratch_glyph_row;
12648 truncate_it.glyph_row->used[TEXT_AREA] = 0;
12649 CHARPOS (truncate_it.position) = BYTEPOS (truncate_it.position) = -1;
12650 truncate_it.object = make_number (0);
12651 produce_special_glyphs (&truncate_it, IT_TRUNCATION);
12653 /* Overwrite glyphs from IT with truncation glyphs. */
12654 from = truncate_it.glyph_row->glyphs[TEXT_AREA];
12655 end = from + truncate_it.glyph_row->used[TEXT_AREA];
12656 to = it->glyph_row->glyphs[TEXT_AREA];
12657 toend = to + it->glyph_row->used[TEXT_AREA];
12659 while (from < end)
12660 *to++ = *from++;
12662 /* There may be padding glyphs left over. Overwrite them too. */
12663 while (to < toend && CHAR_GLYPH_PADDING_P (*to))
12665 from = truncate_it.glyph_row->glyphs[TEXT_AREA];
12666 while (from < end)
12667 *to++ = *from++;
12670 if (to > toend)
12671 it->glyph_row->used[TEXT_AREA] = to - it->glyph_row->glyphs[TEXT_AREA];
12675 /* Compute the pixel height and width of IT->glyph_row.
12677 Most of the time, ascent and height of a display line will be equal
12678 to the max_ascent and max_height values of the display iterator
12679 structure. This is not the case if
12681 1. We hit ZV without displaying anything. In this case, max_ascent
12682 and max_height will be zero.
12684 2. We have some glyphs that don't contribute to the line height.
12685 (The glyph row flag contributes_to_line_height_p is for future
12686 pixmap extensions).
12688 The first case is easily covered by using default values because in
12689 these cases, the line height does not really matter, except that it
12690 must not be zero. */
12692 static void
12693 compute_line_metrics (it)
12694 struct it *it;
12696 struct glyph_row *row = it->glyph_row;
12697 int area, i;
12699 if (FRAME_WINDOW_P (it->f))
12701 int i, min_y, max_y;
12703 /* The line may consist of one space only, that was added to
12704 place the cursor on it. If so, the row's height hasn't been
12705 computed yet. */
12706 if (row->height == 0)
12708 if (it->max_ascent + it->max_descent == 0)
12709 it->max_descent = it->max_phys_descent = CANON_Y_UNIT (it->f);
12710 row->ascent = it->max_ascent;
12711 row->height = it->max_ascent + it->max_descent;
12712 row->phys_ascent = it->max_phys_ascent;
12713 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
12716 /* Compute the width of this line. */
12717 row->pixel_width = row->x;
12718 for (i = 0; i < row->used[TEXT_AREA]; ++i)
12719 row->pixel_width += row->glyphs[TEXT_AREA][i].pixel_width;
12721 xassert (row->pixel_width >= 0);
12722 xassert (row->ascent >= 0 && row->height > 0);
12724 row->overlapping_p = (MATRIX_ROW_OVERLAPS_SUCC_P (row)
12725 || MATRIX_ROW_OVERLAPS_PRED_P (row));
12727 /* If first line's physical ascent is larger than its logical
12728 ascent, use the physical ascent, and make the row taller.
12729 This makes accented characters fully visible. */
12730 if (row == MATRIX_FIRST_TEXT_ROW (it->w->desired_matrix)
12731 && row->phys_ascent > row->ascent)
12733 row->height += row->phys_ascent - row->ascent;
12734 row->ascent = row->phys_ascent;
12737 /* Compute how much of the line is visible. */
12738 row->visible_height = row->height;
12740 min_y = WINDOW_DISPLAY_HEADER_LINE_HEIGHT (it->w);
12741 max_y = WINDOW_DISPLAY_HEIGHT_NO_MODE_LINE (it->w);
12743 if (row->y < min_y)
12744 row->visible_height -= min_y - row->y;
12745 if (row->y + row->height > max_y)
12746 row->visible_height -= row->y + row->height - max_y;
12748 else
12750 row->pixel_width = row->used[TEXT_AREA];
12751 if (row->continued_p)
12752 row->pixel_width -= it->continuation_pixel_width;
12753 else if (row->truncated_on_right_p)
12754 row->pixel_width -= it->truncation_pixel_width;
12755 row->ascent = row->phys_ascent = 0;
12756 row->height = row->phys_height = row->visible_height = 1;
12759 /* Compute a hash code for this row. */
12760 row->hash = 0;
12761 for (area = LEFT_MARGIN_AREA; area < LAST_AREA; ++area)
12762 for (i = 0; i < row->used[area]; ++i)
12763 row->hash = ((((row->hash << 4) + (row->hash >> 24)) & 0x0fffffff)
12764 + row->glyphs[area][i].u.val
12765 + row->glyphs[area][i].face_id
12766 + row->glyphs[area][i].padding_p
12767 + (row->glyphs[area][i].type << 2));
12769 it->max_ascent = it->max_descent = 0;
12770 it->max_phys_ascent = it->max_phys_descent = 0;
12774 /* Append one space to the glyph row of iterator IT if doing a
12775 window-based redisplay. DEFAULT_FACE_P non-zero means let the
12776 space have the default face, otherwise let it have the same face as
12777 IT->face_id. Value is non-zero if a space was added.
12779 This function is called to make sure that there is always one glyph
12780 at the end of a glyph row that the cursor can be set on under
12781 window-systems. (If there weren't such a glyph we would not know
12782 how wide and tall a box cursor should be displayed).
12784 At the same time this space let's a nicely handle clearing to the
12785 end of the line if the row ends in italic text. */
12787 static int
12788 append_space (it, default_face_p)
12789 struct it *it;
12790 int default_face_p;
12792 if (FRAME_WINDOW_P (it->f))
12794 int n = it->glyph_row->used[TEXT_AREA];
12796 if (it->glyph_row->glyphs[TEXT_AREA] + n
12797 < it->glyph_row->glyphs[1 + TEXT_AREA])
12799 /* Save some values that must not be changed.
12800 Must save IT->c and IT->len because otherwise
12801 ITERATOR_AT_END_P wouldn't work anymore after
12802 append_space has been called. */
12803 enum display_element_type saved_what = it->what;
12804 int saved_c = it->c, saved_len = it->len;
12805 int saved_x = it->current_x;
12806 int saved_face_id = it->face_id;
12807 struct text_pos saved_pos;
12808 Lisp_Object saved_object;
12809 struct face *face;
12811 saved_object = it->object;
12812 saved_pos = it->position;
12814 it->what = IT_CHARACTER;
12815 bzero (&it->position, sizeof it->position);
12816 it->object = make_number (0);
12817 it->c = ' ';
12818 it->len = 1;
12820 if (default_face_p)
12821 it->face_id = DEFAULT_FACE_ID;
12822 else if (it->face_before_selective_p)
12823 it->face_id = it->saved_face_id;
12824 face = FACE_FROM_ID (it->f, it->face_id);
12825 it->face_id = FACE_FOR_CHAR (it->f, face, 0);
12827 PRODUCE_GLYPHS (it);
12829 it->current_x = saved_x;
12830 it->object = saved_object;
12831 it->position = saved_pos;
12832 it->what = saved_what;
12833 it->face_id = saved_face_id;
12834 it->len = saved_len;
12835 it->c = saved_c;
12836 return 1;
12840 return 0;
12844 /* Extend the face of the last glyph in the text area of IT->glyph_row
12845 to the end of the display line. Called from display_line.
12846 If the glyph row is empty, add a space glyph to it so that we
12847 know the face to draw. Set the glyph row flag fill_line_p. */
12849 static void
12850 extend_face_to_end_of_line (it)
12851 struct it *it;
12853 struct face *face;
12854 struct frame *f = it->f;
12856 /* If line is already filled, do nothing. */
12857 if (it->current_x >= it->last_visible_x)
12858 return;
12860 /* Face extension extends the background and box of IT->face_id
12861 to the end of the line. If the background equals the background
12862 of the frame, we don't have to do anything. */
12863 if (it->face_before_selective_p)
12864 face = FACE_FROM_ID (it->f, it->saved_face_id);
12865 else
12866 face = FACE_FROM_ID (f, it->face_id);
12868 if (FRAME_WINDOW_P (f)
12869 && face->box == FACE_NO_BOX
12870 && face->background == FRAME_BACKGROUND_PIXEL (f)
12871 && !face->stipple)
12872 return;
12874 /* Set the glyph row flag indicating that the face of the last glyph
12875 in the text area has to be drawn to the end of the text area. */
12876 it->glyph_row->fill_line_p = 1;
12878 /* If current character of IT is not ASCII, make sure we have the
12879 ASCII face. This will be automatically undone the next time
12880 get_next_display_element returns a multibyte character. Note
12881 that the character will always be single byte in unibyte text. */
12882 if (!SINGLE_BYTE_CHAR_P (it->c))
12884 it->face_id = FACE_FOR_CHAR (f, face, 0);
12887 if (FRAME_WINDOW_P (f))
12889 /* If the row is empty, add a space with the current face of IT,
12890 so that we know which face to draw. */
12891 if (it->glyph_row->used[TEXT_AREA] == 0)
12893 it->glyph_row->glyphs[TEXT_AREA][0] = space_glyph;
12894 it->glyph_row->glyphs[TEXT_AREA][0].face_id = it->face_id;
12895 it->glyph_row->used[TEXT_AREA] = 1;
12898 else
12900 /* Save some values that must not be changed. */
12901 int saved_x = it->current_x;
12902 struct text_pos saved_pos;
12903 Lisp_Object saved_object;
12904 enum display_element_type saved_what = it->what;
12905 int saved_face_id = it->face_id;
12907 saved_object = it->object;
12908 saved_pos = it->position;
12910 it->what = IT_CHARACTER;
12911 bzero (&it->position, sizeof it->position);
12912 it->object = make_number (0);
12913 it->c = ' ';
12914 it->len = 1;
12915 it->face_id = face->id;
12917 PRODUCE_GLYPHS (it);
12919 while (it->current_x <= it->last_visible_x)
12920 PRODUCE_GLYPHS (it);
12922 /* Don't count these blanks really. It would let us insert a left
12923 truncation glyph below and make us set the cursor on them, maybe. */
12924 it->current_x = saved_x;
12925 it->object = saved_object;
12926 it->position = saved_pos;
12927 it->what = saved_what;
12928 it->face_id = saved_face_id;
12933 /* Value is non-zero if text starting at CHARPOS in current_buffer is
12934 trailing whitespace. */
12936 static int
12937 trailing_whitespace_p (charpos)
12938 int charpos;
12940 int bytepos = CHAR_TO_BYTE (charpos);
12941 int c = 0;
12943 while (bytepos < ZV_BYTE
12944 && (c = FETCH_CHAR (bytepos),
12945 c == ' ' || c == '\t'))
12946 ++bytepos;
12948 if (bytepos >= ZV_BYTE || c == '\n' || c == '\r')
12950 if (bytepos != PT_BYTE)
12951 return 1;
12953 return 0;
12957 /* Highlight trailing whitespace, if any, in ROW. */
12959 void
12960 highlight_trailing_whitespace (f, row)
12961 struct frame *f;
12962 struct glyph_row *row;
12964 int used = row->used[TEXT_AREA];
12966 if (used)
12968 struct glyph *start = row->glyphs[TEXT_AREA];
12969 struct glyph *glyph = start + used - 1;
12971 /* Skip over glyphs inserted to display the cursor at the
12972 end of a line, for extending the face of the last glyph
12973 to the end of the line on terminals, and for truncation
12974 and continuation glyphs. */
12975 while (glyph >= start
12976 && glyph->type == CHAR_GLYPH
12977 && INTEGERP (glyph->object))
12978 --glyph;
12980 /* If last glyph is a space or stretch, and it's trailing
12981 whitespace, set the face of all trailing whitespace glyphs in
12982 IT->glyph_row to `trailing-whitespace'. */
12983 if (glyph >= start
12984 && BUFFERP (glyph->object)
12985 && (glyph->type == STRETCH_GLYPH
12986 || (glyph->type == CHAR_GLYPH
12987 && glyph->u.ch == ' '))
12988 && trailing_whitespace_p (glyph->charpos))
12990 int face_id = lookup_named_face (f, Qtrailing_whitespace, 0);
12992 while (glyph >= start
12993 && BUFFERP (glyph->object)
12994 && (glyph->type == STRETCH_GLYPH
12995 || (glyph->type == CHAR_GLYPH
12996 && glyph->u.ch == ' ')))
12997 (glyph--)->face_id = face_id;
13003 /* Value is non-zero if glyph row ROW in window W should be
13004 used to hold the cursor. */
13006 static int
13007 cursor_row_p (w, row)
13008 struct window *w;
13009 struct glyph_row *row;
13011 int cursor_row_p = 1;
13013 if (PT == MATRIX_ROW_END_CHARPOS (row))
13015 /* If the row ends with a newline from a string, we don't want
13016 the cursor there (if the row is continued it doesn't end in a
13017 newline). */
13018 if (CHARPOS (row->end.string_pos) >= 0
13019 || MATRIX_ROW_ENDS_IN_MIDDLE_OF_CHAR_P (row))
13020 cursor_row_p = row->continued_p;
13022 /* If the row ends at ZV, display the cursor at the end of that
13023 row instead of at the start of the row below. */
13024 else if (row->ends_at_zv_p)
13025 cursor_row_p = 1;
13026 else
13027 cursor_row_p = 0;
13030 return cursor_row_p;
13034 /* Construct the glyph row IT->glyph_row in the desired matrix of
13035 IT->w from text at the current position of IT. See dispextern.h
13036 for an overview of struct it. Value is non-zero if
13037 IT->glyph_row displays text, as opposed to a line displaying ZV
13038 only. */
13040 static int
13041 display_line (it)
13042 struct it *it;
13044 struct glyph_row *row = it->glyph_row;
13046 /* We always start displaying at hpos zero even if hscrolled. */
13047 xassert (it->hpos == 0 && it->current_x == 0);
13049 /* We must not display in a row that's not a text row. */
13050 xassert (MATRIX_ROW_VPOS (row, it->w->desired_matrix)
13051 < it->w->desired_matrix->nrows);
13053 /* Is IT->w showing the region? */
13054 it->w->region_showing = it->region_beg_charpos > 0 ? Qt : Qnil;
13056 /* Clear the result glyph row and enable it. */
13057 prepare_desired_row (row);
13059 row->y = it->current_y;
13060 row->start = it->current;
13061 row->continuation_lines_width = it->continuation_lines_width;
13062 row->displays_text_p = 1;
13063 row->starts_in_middle_of_char_p = it->starts_in_middle_of_char_p;
13064 it->starts_in_middle_of_char_p = 0;
13066 /* Arrange the overlays nicely for our purposes. Usually, we call
13067 display_line on only one line at a time, in which case this
13068 can't really hurt too much, or we call it on lines which appear
13069 one after another in the buffer, in which case all calls to
13070 recenter_overlay_lists but the first will be pretty cheap. */
13071 recenter_overlay_lists (current_buffer, IT_CHARPOS (*it));
13073 /* Move over display elements that are not visible because we are
13074 hscrolled. This may stop at an x-position < IT->first_visible_x
13075 if the first glyph is partially visible or if we hit a line end. */
13076 if (it->current_x < it->first_visible_x)
13077 move_it_in_display_line_to (it, ZV, it->first_visible_x,
13078 MOVE_TO_POS | MOVE_TO_X);
13080 /* Get the initial row height. This is either the height of the
13081 text hscrolled, if there is any, or zero. */
13082 row->ascent = it->max_ascent;
13083 row->height = it->max_ascent + it->max_descent;
13084 row->phys_ascent = it->max_phys_ascent;
13085 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
13087 /* Loop generating characters. The loop is left with IT on the next
13088 character to display. */
13089 while (1)
13091 int n_glyphs_before, hpos_before, x_before;
13092 int x, i, nglyphs;
13093 int ascent = 0, descent = 0, phys_ascent = 0, phys_descent = 0;
13095 /* Retrieve the next thing to display. Value is zero if end of
13096 buffer reached. */
13097 if (!get_next_display_element (it))
13099 /* Maybe add a space at the end of this line that is used to
13100 display the cursor there under X. Set the charpos of the
13101 first glyph of blank lines not corresponding to any text
13102 to -1. */
13103 if ((append_space (it, 1) && row->used[TEXT_AREA] == 1)
13104 || row->used[TEXT_AREA] == 0)
13106 row->glyphs[TEXT_AREA]->charpos = -1;
13107 row->displays_text_p = 0;
13109 if (!NILP (XBUFFER (it->w->buffer)->indicate_empty_lines)
13110 && (!MINI_WINDOW_P (it->w)
13111 || (minibuf_level && EQ (it->window, minibuf_window))))
13112 row->indicate_empty_line_p = 1;
13115 it->continuation_lines_width = 0;
13116 row->ends_at_zv_p = 1;
13117 break;
13120 /* Now, get the metrics of what we want to display. This also
13121 generates glyphs in `row' (which is IT->glyph_row). */
13122 n_glyphs_before = row->used[TEXT_AREA];
13123 x = it->current_x;
13125 /* Remember the line height so far in case the next element doesn't
13126 fit on the line. */
13127 if (!it->truncate_lines_p)
13129 ascent = it->max_ascent;
13130 descent = it->max_descent;
13131 phys_ascent = it->max_phys_ascent;
13132 phys_descent = it->max_phys_descent;
13135 PRODUCE_GLYPHS (it);
13137 /* If this display element was in marginal areas, continue with
13138 the next one. */
13139 if (it->area != TEXT_AREA)
13141 row->ascent = max (row->ascent, it->max_ascent);
13142 row->height = max (row->height, it->max_ascent + it->max_descent);
13143 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
13144 row->phys_height = max (row->phys_height,
13145 it->max_phys_ascent + it->max_phys_descent);
13146 set_iterator_to_next (it, 1);
13147 continue;
13150 /* Does the display element fit on the line? If we truncate
13151 lines, we should draw past the right edge of the window. If
13152 we don't truncate, we want to stop so that we can display the
13153 continuation glyph before the right margin. If lines are
13154 continued, there are two possible strategies for characters
13155 resulting in more than 1 glyph (e.g. tabs): Display as many
13156 glyphs as possible in this line and leave the rest for the
13157 continuation line, or display the whole element in the next
13158 line. Original redisplay did the former, so we do it also. */
13159 nglyphs = row->used[TEXT_AREA] - n_glyphs_before;
13160 hpos_before = it->hpos;
13161 x_before = x;
13163 if (/* Not a newline. */
13164 nglyphs > 0
13165 /* Glyphs produced fit entirely in the line. */
13166 && it->current_x < it->last_visible_x)
13168 it->hpos += nglyphs;
13169 row->ascent = max (row->ascent, it->max_ascent);
13170 row->height = max (row->height, it->max_ascent + it->max_descent);
13171 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
13172 row->phys_height = max (row->phys_height,
13173 it->max_phys_ascent + it->max_phys_descent);
13174 if (it->current_x - it->pixel_width < it->first_visible_x)
13175 row->x = x - it->first_visible_x;
13177 else
13179 int new_x;
13180 struct glyph *glyph;
13182 for (i = 0; i < nglyphs; ++i, x = new_x)
13184 glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
13185 new_x = x + glyph->pixel_width;
13187 if (/* Lines are continued. */
13188 !it->truncate_lines_p
13189 && (/* Glyph doesn't fit on the line. */
13190 new_x > it->last_visible_x
13191 /* Or it fits exactly on a window system frame. */
13192 || (new_x == it->last_visible_x
13193 && FRAME_WINDOW_P (it->f))))
13195 /* End of a continued line. */
13197 if (it->hpos == 0
13198 || (new_x == it->last_visible_x
13199 && FRAME_WINDOW_P (it->f)))
13201 /* Current glyph is the only one on the line or
13202 fits exactly on the line. We must continue
13203 the line because we can't draw the cursor
13204 after the glyph. */
13205 row->continued_p = 1;
13206 it->current_x = new_x;
13207 it->continuation_lines_width += new_x;
13208 ++it->hpos;
13209 if (i == nglyphs - 1)
13210 set_iterator_to_next (it, 1);
13212 else if (CHAR_GLYPH_PADDING_P (*glyph)
13213 && !FRAME_WINDOW_P (it->f))
13215 /* A padding glyph that doesn't fit on this line.
13216 This means the whole character doesn't fit
13217 on the line. */
13218 row->used[TEXT_AREA] = n_glyphs_before;
13220 /* Fill the rest of the row with continuation
13221 glyphs like in 20.x. */
13222 while (row->glyphs[TEXT_AREA] + row->used[TEXT_AREA]
13223 < row->glyphs[1 + TEXT_AREA])
13224 produce_special_glyphs (it, IT_CONTINUATION);
13226 row->continued_p = 1;
13227 it->current_x = x_before;
13228 it->continuation_lines_width += x_before;
13230 /* Restore the height to what it was before the
13231 element not fitting on the line. */
13232 it->max_ascent = ascent;
13233 it->max_descent = descent;
13234 it->max_phys_ascent = phys_ascent;
13235 it->max_phys_descent = phys_descent;
13237 else if (it->c == '\t' && FRAME_WINDOW_P (it->f))
13239 /* A TAB that extends past the right edge of the
13240 window. This produces a single glyph on
13241 window system frames. We leave the glyph in
13242 this row and let it fill the row, but don't
13243 consume the TAB. */
13244 it->continuation_lines_width += it->last_visible_x;
13245 row->ends_in_middle_of_char_p = 1;
13246 row->continued_p = 1;
13247 glyph->pixel_width = it->last_visible_x - x;
13248 it->starts_in_middle_of_char_p = 1;
13250 else
13252 /* Something other than a TAB that draws past
13253 the right edge of the window. Restore
13254 positions to values before the element. */
13255 row->used[TEXT_AREA] = n_glyphs_before + i;
13257 /* Display continuation glyphs. */
13258 if (!FRAME_WINDOW_P (it->f))
13259 produce_special_glyphs (it, IT_CONTINUATION);
13260 row->continued_p = 1;
13262 it->continuation_lines_width += x;
13264 if (nglyphs > 1 && i > 0)
13266 row->ends_in_middle_of_char_p = 1;
13267 it->starts_in_middle_of_char_p = 1;
13270 /* Restore the height to what it was before the
13271 element not fitting on the line. */
13272 it->max_ascent = ascent;
13273 it->max_descent = descent;
13274 it->max_phys_ascent = phys_ascent;
13275 it->max_phys_descent = phys_descent;
13278 break;
13280 else if (new_x > it->first_visible_x)
13282 /* Increment number of glyphs actually displayed. */
13283 ++it->hpos;
13285 if (x < it->first_visible_x)
13286 /* Glyph is partially visible, i.e. row starts at
13287 negative X position. */
13288 row->x = x - it->first_visible_x;
13290 else
13292 /* Glyph is completely off the left margin of the
13293 window. This should not happen because of the
13294 move_it_in_display_line at the start of this
13295 function, unless the text display area of the
13296 window is empty. */
13297 xassert (it->first_visible_x <= it->last_visible_x);
13301 row->ascent = max (row->ascent, it->max_ascent);
13302 row->height = max (row->height, it->max_ascent + it->max_descent);
13303 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
13304 row->phys_height = max (row->phys_height,
13305 it->max_phys_ascent + it->max_phys_descent);
13307 /* End of this display line if row is continued. */
13308 if (row->continued_p)
13309 break;
13312 /* Is this a line end? If yes, we're also done, after making
13313 sure that a non-default face is extended up to the right
13314 margin of the window. */
13315 if (ITERATOR_AT_END_OF_LINE_P (it))
13317 int used_before = row->used[TEXT_AREA];
13319 row->ends_in_newline_from_string_p = STRINGP (it->object);
13321 /* Add a space at the end of the line that is used to
13322 display the cursor there. */
13323 append_space (it, 0);
13325 /* Extend the face to the end of the line. */
13326 extend_face_to_end_of_line (it);
13328 /* Make sure we have the position. */
13329 if (used_before == 0)
13330 row->glyphs[TEXT_AREA]->charpos = CHARPOS (it->position);
13332 /* Consume the line end. This skips over invisible lines. */
13333 set_iterator_to_next (it, 1);
13334 it->continuation_lines_width = 0;
13335 break;
13338 /* Proceed with next display element. Note that this skips
13339 over lines invisible because of selective display. */
13340 set_iterator_to_next (it, 1);
13342 /* If we truncate lines, we are done when the last displayed
13343 glyphs reach past the right margin of the window. */
13344 if (it->truncate_lines_p
13345 && (FRAME_WINDOW_P (it->f)
13346 ? (it->current_x >= it->last_visible_x)
13347 : (it->current_x > it->last_visible_x)))
13349 /* Maybe add truncation glyphs. */
13350 if (!FRAME_WINDOW_P (it->f))
13352 int i, n;
13354 for (i = row->used[TEXT_AREA] - 1; i > 0; --i)
13355 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][i]))
13356 break;
13358 for (n = row->used[TEXT_AREA]; i < n; ++i)
13360 row->used[TEXT_AREA] = i;
13361 produce_special_glyphs (it, IT_TRUNCATION);
13365 row->truncated_on_right_p = 1;
13366 it->continuation_lines_width = 0;
13367 reseat_at_next_visible_line_start (it, 0);
13368 row->ends_at_zv_p = FETCH_BYTE (IT_BYTEPOS (*it) - 1) != '\n';
13369 it->hpos = hpos_before;
13370 it->current_x = x_before;
13371 break;
13375 /* If line is not empty and hscrolled, maybe insert truncation glyphs
13376 at the left window margin. */
13377 if (it->first_visible_x
13378 && IT_CHARPOS (*it) != MATRIX_ROW_START_CHARPOS (row))
13380 if (!FRAME_WINDOW_P (it->f))
13381 insert_left_trunc_glyphs (it);
13382 row->truncated_on_left_p = 1;
13385 /* If the start of this line is the overlay arrow-position, then
13386 mark this glyph row as the one containing the overlay arrow.
13387 This is clearly a mess with variable size fonts. It would be
13388 better to let it be displayed like cursors under X. */
13389 if (MARKERP (Voverlay_arrow_position)
13390 && current_buffer == XMARKER (Voverlay_arrow_position)->buffer
13391 && (MATRIX_ROW_START_CHARPOS (row)
13392 == marker_position (Voverlay_arrow_position))
13393 && STRINGP (Voverlay_arrow_string)
13394 && ! overlay_arrow_seen)
13396 /* Overlay arrow in window redisplay is a fringe bitmap. */
13397 if (!FRAME_WINDOW_P (it->f))
13399 struct glyph_row *arrow_row = get_overlay_arrow_glyph_row (it->w);
13400 struct glyph *glyph = arrow_row->glyphs[TEXT_AREA];
13401 struct glyph *arrow_end = glyph + arrow_row->used[TEXT_AREA];
13402 struct glyph *p = row->glyphs[TEXT_AREA];
13403 struct glyph *p2, *end;
13405 /* Copy the arrow glyphs. */
13406 while (glyph < arrow_end)
13407 *p++ = *glyph++;
13409 /* Throw away padding glyphs. */
13410 p2 = p;
13411 end = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA];
13412 while (p2 < end && CHAR_GLYPH_PADDING_P (*p2))
13413 ++p2;
13414 if (p2 > p)
13416 while (p2 < end)
13417 *p++ = *p2++;
13418 row->used[TEXT_AREA] = p2 - row->glyphs[TEXT_AREA];
13422 overlay_arrow_seen = 1;
13423 row->overlay_arrow_p = 1;
13426 /* Compute pixel dimensions of this line. */
13427 compute_line_metrics (it);
13429 /* Remember the position at which this line ends. */
13430 row->end = it->current;
13432 /* Maybe set the cursor. */
13433 if (it->w->cursor.vpos < 0
13434 && PT >= MATRIX_ROW_START_CHARPOS (row)
13435 && PT <= MATRIX_ROW_END_CHARPOS (row)
13436 && cursor_row_p (it->w, row))
13437 set_cursor_from_row (it->w, row, it->w->desired_matrix, 0, 0, 0, 0);
13439 /* Highlight trailing whitespace. */
13440 if (!NILP (Vshow_trailing_whitespace))
13441 highlight_trailing_whitespace (it->f, it->glyph_row);
13443 /* Prepare for the next line. This line starts horizontally at (X
13444 HPOS) = (0 0). Vertical positions are incremented. As a
13445 convenience for the caller, IT->glyph_row is set to the next
13446 row to be used. */
13447 it->current_x = it->hpos = 0;
13448 it->current_y += row->height;
13449 ++it->vpos;
13450 ++it->glyph_row;
13451 return row->displays_text_p;
13456 /***********************************************************************
13457 Menu Bar
13458 ***********************************************************************/
13460 /* Redisplay the menu bar in the frame for window W.
13462 The menu bar of X frames that don't have X toolkit support is
13463 displayed in a special window W->frame->menu_bar_window.
13465 The menu bar of terminal frames is treated specially as far as
13466 glyph matrices are concerned. Menu bar lines are not part of
13467 windows, so the update is done directly on the frame matrix rows
13468 for the menu bar. */
13470 static void
13471 display_menu_bar (w)
13472 struct window *w;
13474 struct frame *f = XFRAME (WINDOW_FRAME (w));
13475 struct it it;
13476 Lisp_Object items;
13477 int i;
13479 /* Don't do all this for graphical frames. */
13480 #ifdef HAVE_NTGUI
13481 if (!NILP (Vwindow_system))
13482 return;
13483 #endif
13484 #ifdef USE_X_TOOLKIT
13485 if (FRAME_X_P (f))
13486 return;
13487 #endif
13488 #ifdef MAC_OS
13489 if (FRAME_MAC_P (f))
13490 return;
13491 #endif
13493 #ifdef USE_X_TOOLKIT
13494 xassert (!FRAME_WINDOW_P (f));
13495 init_iterator (&it, w, -1, -1, f->desired_matrix->rows, MENU_FACE_ID);
13496 it.first_visible_x = 0;
13497 it.last_visible_x = FRAME_WINDOW_WIDTH (f) * CANON_X_UNIT (f);
13498 #else /* not USE_X_TOOLKIT */
13499 if (FRAME_WINDOW_P (f))
13501 /* Menu bar lines are displayed in the desired matrix of the
13502 dummy window menu_bar_window. */
13503 struct window *menu_w;
13504 xassert (WINDOWP (f->menu_bar_window));
13505 menu_w = XWINDOW (f->menu_bar_window);
13506 init_iterator (&it, menu_w, -1, -1, menu_w->desired_matrix->rows,
13507 MENU_FACE_ID);
13508 it.first_visible_x = 0;
13509 it.last_visible_x = FRAME_WINDOW_WIDTH (f) * CANON_X_UNIT (f);
13511 else
13513 /* This is a TTY frame, i.e. character hpos/vpos are used as
13514 pixel x/y. */
13515 init_iterator (&it, w, -1, -1, f->desired_matrix->rows,
13516 MENU_FACE_ID);
13517 it.first_visible_x = 0;
13518 it.last_visible_x = FRAME_WIDTH (f);
13520 #endif /* not USE_X_TOOLKIT */
13522 if (! mode_line_inverse_video)
13523 /* Force the menu-bar to be displayed in the default face. */
13524 it.base_face_id = it.face_id = DEFAULT_FACE_ID;
13526 /* Clear all rows of the menu bar. */
13527 for (i = 0; i < FRAME_MENU_BAR_LINES (f); ++i)
13529 struct glyph_row *row = it.glyph_row + i;
13530 clear_glyph_row (row);
13531 row->enabled_p = 1;
13532 row->full_width_p = 1;
13535 /* Display all items of the menu bar. */
13536 items = FRAME_MENU_BAR_ITEMS (it.f);
13537 for (i = 0; i < XVECTOR (items)->size; i += 4)
13539 Lisp_Object string;
13541 /* Stop at nil string. */
13542 string = AREF (items, i + 1);
13543 if (NILP (string))
13544 break;
13546 /* Remember where item was displayed. */
13547 AREF (items, i + 3) = make_number (it.hpos);
13549 /* Display the item, pad with one space. */
13550 if (it.current_x < it.last_visible_x)
13551 display_string (NULL, string, Qnil, 0, 0, &it,
13552 SCHARS (string) + 1, 0, 0, -1);
13555 /* Fill out the line with spaces. */
13556 if (it.current_x < it.last_visible_x)
13557 display_string ("", Qnil, Qnil, 0, 0, &it, -1, 0, 0, -1);
13559 /* Compute the total height of the lines. */
13560 compute_line_metrics (&it);
13565 /***********************************************************************
13566 Mode Line
13567 ***********************************************************************/
13569 /* Redisplay mode lines in the window tree whose root is WINDOW. If
13570 FORCE is non-zero, redisplay mode lines unconditionally.
13571 Otherwise, redisplay only mode lines that are garbaged. Value is
13572 the number of windows whose mode lines were redisplayed. */
13574 static int
13575 redisplay_mode_lines (window, force)
13576 Lisp_Object window;
13577 int force;
13579 int nwindows = 0;
13581 while (!NILP (window))
13583 struct window *w = XWINDOW (window);
13585 if (WINDOWP (w->hchild))
13586 nwindows += redisplay_mode_lines (w->hchild, force);
13587 else if (WINDOWP (w->vchild))
13588 nwindows += redisplay_mode_lines (w->vchild, force);
13589 else if (force
13590 || FRAME_GARBAGED_P (XFRAME (w->frame))
13591 || !MATRIX_MODE_LINE_ROW (w->current_matrix)->enabled_p)
13593 struct text_pos lpoint;
13594 struct buffer *old = current_buffer;
13596 /* Set the window's buffer for the mode line display. */
13597 SET_TEXT_POS (lpoint, PT, PT_BYTE);
13598 set_buffer_internal_1 (XBUFFER (w->buffer));
13600 /* Point refers normally to the selected window. For any
13601 other window, set up appropriate value. */
13602 if (!EQ (window, selected_window))
13604 struct text_pos pt;
13606 SET_TEXT_POS_FROM_MARKER (pt, w->pointm);
13607 if (CHARPOS (pt) < BEGV)
13608 TEMP_SET_PT_BOTH (BEGV, BEGV_BYTE);
13609 else if (CHARPOS (pt) > (ZV - 1))
13610 TEMP_SET_PT_BOTH (ZV, ZV_BYTE);
13611 else
13612 TEMP_SET_PT_BOTH (CHARPOS (pt), BYTEPOS (pt));
13615 /* Display mode lines. */
13616 clear_glyph_matrix (w->desired_matrix);
13617 if (display_mode_lines (w))
13619 ++nwindows;
13620 w->must_be_updated_p = 1;
13623 /* Restore old settings. */
13624 set_buffer_internal_1 (old);
13625 TEMP_SET_PT_BOTH (CHARPOS (lpoint), BYTEPOS (lpoint));
13628 window = w->next;
13631 return nwindows;
13635 /* Display the mode and/or top line of window W. Value is the number
13636 of mode lines displayed. */
13638 static int
13639 display_mode_lines (w)
13640 struct window *w;
13642 Lisp_Object old_selected_window, old_selected_frame;
13643 int n = 0;
13645 old_selected_frame = selected_frame;
13646 selected_frame = w->frame;
13647 old_selected_window = selected_window;
13648 XSETWINDOW (selected_window, w);
13650 /* These will be set while the mode line specs are processed. */
13651 line_number_displayed = 0;
13652 w->column_number_displayed = Qnil;
13654 if (WINDOW_WANTS_MODELINE_P (w))
13656 struct window *sel_w = XWINDOW (old_selected_window);
13658 /* Select mode line face based on the real selected window. */
13659 display_mode_line (w, CURRENT_MODE_LINE_FACE_ID_3 (sel_w, sel_w, w),
13660 current_buffer->mode_line_format);
13661 ++n;
13664 if (WINDOW_WANTS_HEADER_LINE_P (w))
13666 display_mode_line (w, HEADER_LINE_FACE_ID,
13667 current_buffer->header_line_format);
13668 ++n;
13671 selected_frame = old_selected_frame;
13672 selected_window = old_selected_window;
13673 return n;
13677 /* Display mode or top line of window W. FACE_ID specifies which line
13678 to display; it is either MODE_LINE_FACE_ID or HEADER_LINE_FACE_ID.
13679 FORMAT is the mode line format to display. Value is the pixel
13680 height of the mode line displayed. */
13682 static int
13683 display_mode_line (w, face_id, format)
13684 struct window *w;
13685 enum face_id face_id;
13686 Lisp_Object format;
13688 struct it it;
13689 struct face *face;
13691 init_iterator (&it, w, -1, -1, NULL, face_id);
13692 prepare_desired_row (it.glyph_row);
13694 if (! mode_line_inverse_video)
13695 /* Force the mode-line to be displayed in the default face. */
13696 it.base_face_id = it.face_id = DEFAULT_FACE_ID;
13698 /* Temporarily make frame's keyboard the current kboard so that
13699 kboard-local variables in the mode_line_format will get the right
13700 values. */
13701 push_frame_kboard (it.f);
13702 display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
13703 pop_frame_kboard ();
13705 /* Fill up with spaces. */
13706 display_string (" ", Qnil, Qnil, 0, 0, &it, 10000, -1, -1, 0);
13708 compute_line_metrics (&it);
13709 it.glyph_row->full_width_p = 1;
13710 it.glyph_row->mode_line_p = 1;
13711 it.glyph_row->continued_p = 0;
13712 it.glyph_row->truncated_on_left_p = 0;
13713 it.glyph_row->truncated_on_right_p = 0;
13715 /* Make a 3D mode-line have a shadow at its right end. */
13716 face = FACE_FROM_ID (it.f, face_id);
13717 extend_face_to_end_of_line (&it);
13718 if (face->box != FACE_NO_BOX)
13720 struct glyph *last = (it.glyph_row->glyphs[TEXT_AREA]
13721 + it.glyph_row->used[TEXT_AREA] - 1);
13722 last->right_box_line_p = 1;
13725 return it.glyph_row->height;
13728 /* Alist that caches the results of :propertize.
13729 Each element is (PROPERTIZED-STRING . PROPERTY-LIST). */
13730 Lisp_Object mode_line_proptrans_alist;
13732 /* List of strings making up the mode-line. */
13733 Lisp_Object mode_line_string_list;
13735 /* Base face property when building propertized mode line string. */
13736 static Lisp_Object mode_line_string_face;
13737 static Lisp_Object mode_line_string_face_prop;
13740 /* Contribute ELT to the mode line for window IT->w. How it
13741 translates into text depends on its data type.
13743 IT describes the display environment in which we display, as usual.
13745 DEPTH is the depth in recursion. It is used to prevent
13746 infinite recursion here.
13748 FIELD_WIDTH is the number of characters the display of ELT should
13749 occupy in the mode line, and PRECISION is the maximum number of
13750 characters to display from ELT's representation. See
13751 display_string for details.
13753 Returns the hpos of the end of the text generated by ELT.
13755 PROPS is a property list to add to any string we encounter.
13757 If RISKY is nonzero, remove (disregard) any properties in any string
13758 we encounter, and ignore :eval and :propertize.
13760 If the global variable `frame_title_ptr' is non-NULL, then the output
13761 is passed to `store_frame_title' instead of `display_string'. */
13763 static int
13764 display_mode_element (it, depth, field_width, precision, elt, props, risky)
13765 struct it *it;
13766 int depth;
13767 int field_width, precision;
13768 Lisp_Object elt, props;
13769 int risky;
13771 int n = 0, field, prec;
13772 int literal = 0;
13774 tail_recurse:
13775 if (depth > 10)
13776 goto invalid;
13778 depth++;
13780 switch (SWITCH_ENUM_CAST (XTYPE (elt)))
13782 case Lisp_String:
13784 /* A string: output it and check for %-constructs within it. */
13785 unsigned char c;
13786 const unsigned char *this, *lisp_string;
13788 if (!NILP (props) || risky)
13790 Lisp_Object oprops, aelt;
13791 oprops = Ftext_properties_at (make_number (0), elt);
13793 if (NILP (Fequal (props, oprops)) || risky)
13795 /* If the starting string has properties,
13796 merge the specified ones onto the existing ones. */
13797 if (! NILP (oprops) && !risky)
13799 Lisp_Object tem;
13801 oprops = Fcopy_sequence (oprops);
13802 tem = props;
13803 while (CONSP (tem))
13805 oprops = Fplist_put (oprops, XCAR (tem),
13806 XCAR (XCDR (tem)));
13807 tem = XCDR (XCDR (tem));
13809 props = oprops;
13812 aelt = Fassoc (elt, mode_line_proptrans_alist);
13813 if (! NILP (aelt) && !NILP (Fequal (props, XCDR (aelt))))
13815 mode_line_proptrans_alist
13816 = Fcons (aelt, Fdelq (aelt, mode_line_proptrans_alist));
13817 elt = XCAR (aelt);
13819 else
13821 Lisp_Object tem;
13823 elt = Fcopy_sequence (elt);
13824 Fset_text_properties (make_number (0), Flength (elt),
13825 props, elt);
13826 /* Add this item to mode_line_proptrans_alist. */
13827 mode_line_proptrans_alist
13828 = Fcons (Fcons (elt, props),
13829 mode_line_proptrans_alist);
13830 /* Truncate mode_line_proptrans_alist
13831 to at most 50 elements. */
13832 tem = Fnthcdr (make_number (50),
13833 mode_line_proptrans_alist);
13834 if (! NILP (tem))
13835 XSETCDR (tem, Qnil);
13840 this = SDATA (elt);
13841 lisp_string = this;
13843 if (literal)
13845 prec = precision - n;
13846 if (frame_title_ptr)
13847 n += store_frame_title (SDATA (elt), -1, prec);
13848 else if (!NILP (mode_line_string_list))
13849 n += store_mode_line_string (NULL, elt, 1, 0, prec, Qnil);
13850 else
13851 n += display_string (NULL, elt, Qnil, 0, 0, it,
13852 0, prec, 0, STRING_MULTIBYTE (elt));
13854 break;
13857 while ((precision <= 0 || n < precision)
13858 && *this
13859 && (frame_title_ptr
13860 || !NILP (mode_line_string_list)
13861 || it->current_x < it->last_visible_x))
13863 const unsigned char *last = this;
13865 /* Advance to end of string or next format specifier. */
13866 while ((c = *this++) != '\0' && c != '%')
13869 if (this - 1 != last)
13871 /* Output to end of string or up to '%'. Field width
13872 is length of string. Don't output more than
13873 PRECISION allows us. */
13874 --this;
13876 prec = chars_in_text (last, this - last);
13877 if (precision > 0 && prec > precision - n)
13878 prec = precision - n;
13880 if (frame_title_ptr)
13881 n += store_frame_title (last, 0, prec);
13882 else if (!NILP (mode_line_string_list))
13884 int bytepos = last - lisp_string;
13885 int charpos = string_byte_to_char (elt, bytepos);
13886 n += store_mode_line_string (NULL,
13887 Fsubstring (elt, make_number (charpos),
13888 make_number (charpos + prec)),
13889 0, 0, 0, Qnil);
13891 else
13893 int bytepos = last - lisp_string;
13894 int charpos = string_byte_to_char (elt, bytepos);
13895 n += display_string (NULL, elt, Qnil, 0, charpos,
13896 it, 0, prec, 0,
13897 STRING_MULTIBYTE (elt));
13900 else /* c == '%' */
13902 const unsigned char *percent_position = this;
13904 /* Get the specified minimum width. Zero means
13905 don't pad. */
13906 field = 0;
13907 while ((c = *this++) >= '0' && c <= '9')
13908 field = field * 10 + c - '0';
13910 /* Don't pad beyond the total padding allowed. */
13911 if (field_width - n > 0 && field > field_width - n)
13912 field = field_width - n;
13914 /* Note that either PRECISION <= 0 or N < PRECISION. */
13915 prec = precision - n;
13917 if (c == 'M')
13918 n += display_mode_element (it, depth, field, prec,
13919 Vglobal_mode_string, props,
13920 risky);
13921 else if (c != 0)
13923 int multibyte;
13924 int bytepos, charpos;
13925 unsigned char *spec;
13927 bytepos = percent_position - lisp_string;
13928 charpos = (STRING_MULTIBYTE (elt)
13929 ? string_byte_to_char (elt, bytepos)
13930 : bytepos);
13932 spec
13933 = decode_mode_spec (it->w, c, field, prec, &multibyte);
13935 if (frame_title_ptr)
13936 n += store_frame_title (spec, field, prec);
13937 else if (!NILP (mode_line_string_list))
13939 int len = strlen (spec);
13940 Lisp_Object tem = make_string (spec, len);
13941 props = Ftext_properties_at (make_number (charpos), elt);
13942 /* Should only keep face property in props */
13943 n += store_mode_line_string (NULL, tem, 0, field, prec, props);
13945 else
13947 int nglyphs_before, nwritten;
13949 nglyphs_before = it->glyph_row->used[TEXT_AREA];
13950 nwritten = display_string (spec, Qnil, elt,
13951 charpos, 0, it,
13952 field, prec, 0,
13953 multibyte);
13955 /* Assign to the glyphs written above the
13956 string where the `%x' came from, position
13957 of the `%'. */
13958 if (nwritten > 0)
13960 struct glyph *glyph
13961 = (it->glyph_row->glyphs[TEXT_AREA]
13962 + nglyphs_before);
13963 int i;
13965 for (i = 0; i < nwritten; ++i)
13967 glyph[i].object = elt;
13968 glyph[i].charpos = charpos;
13971 n += nwritten;
13975 else /* c == 0 */
13976 break;
13980 break;
13982 case Lisp_Symbol:
13983 /* A symbol: process the value of the symbol recursively
13984 as if it appeared here directly. Avoid error if symbol void.
13985 Special case: if value of symbol is a string, output the string
13986 literally. */
13988 register Lisp_Object tem;
13990 /* If the variable is not marked as risky to set
13991 then its contents are risky to use. */
13992 if (NILP (Fget (elt, Qrisky_local_variable)))
13993 risky = 1;
13995 tem = Fboundp (elt);
13996 if (!NILP (tem))
13998 tem = Fsymbol_value (elt);
13999 /* If value is a string, output that string literally:
14000 don't check for % within it. */
14001 if (STRINGP (tem))
14002 literal = 1;
14004 if (!EQ (tem, elt))
14006 /* Give up right away for nil or t. */
14007 elt = tem;
14008 goto tail_recurse;
14012 break;
14014 case Lisp_Cons:
14016 register Lisp_Object car, tem;
14018 /* A cons cell: five distinct cases.
14019 If first element is :eval or :propertize, do something special.
14020 If first element is a string or a cons, process all the elements
14021 and effectively concatenate them.
14022 If first element is a negative number, truncate displaying cdr to
14023 at most that many characters. If positive, pad (with spaces)
14024 to at least that many characters.
14025 If first element is a symbol, process the cadr or caddr recursively
14026 according to whether the symbol's value is non-nil or nil. */
14027 car = XCAR (elt);
14028 if (EQ (car, QCeval))
14030 /* An element of the form (:eval FORM) means evaluate FORM
14031 and use the result as mode line elements. */
14033 if (risky)
14034 break;
14036 if (CONSP (XCDR (elt)))
14038 Lisp_Object spec;
14039 spec = safe_eval (XCAR (XCDR (elt)));
14040 n += display_mode_element (it, depth, field_width - n,
14041 precision - n, spec, props,
14042 risky);
14045 else if (EQ (car, QCpropertize))
14047 /* An element of the form (:propertize ELT PROPS...)
14048 means display ELT but applying properties PROPS. */
14050 if (risky)
14051 break;
14053 if (CONSP (XCDR (elt)))
14054 n += display_mode_element (it, depth, field_width - n,
14055 precision - n, XCAR (XCDR (elt)),
14056 XCDR (XCDR (elt)), risky);
14058 else if (SYMBOLP (car))
14060 tem = Fboundp (car);
14061 elt = XCDR (elt);
14062 if (!CONSP (elt))
14063 goto invalid;
14064 /* elt is now the cdr, and we know it is a cons cell.
14065 Use its car if CAR has a non-nil value. */
14066 if (!NILP (tem))
14068 tem = Fsymbol_value (car);
14069 if (!NILP (tem))
14071 elt = XCAR (elt);
14072 goto tail_recurse;
14075 /* Symbol's value is nil (or symbol is unbound)
14076 Get the cddr of the original list
14077 and if possible find the caddr and use that. */
14078 elt = XCDR (elt);
14079 if (NILP (elt))
14080 break;
14081 else if (!CONSP (elt))
14082 goto invalid;
14083 elt = XCAR (elt);
14084 goto tail_recurse;
14086 else if (INTEGERP (car))
14088 register int lim = XINT (car);
14089 elt = XCDR (elt);
14090 if (lim < 0)
14092 /* Negative int means reduce maximum width. */
14093 if (precision <= 0)
14094 precision = -lim;
14095 else
14096 precision = min (precision, -lim);
14098 else if (lim > 0)
14100 /* Padding specified. Don't let it be more than
14101 current maximum. */
14102 if (precision > 0)
14103 lim = min (precision, lim);
14105 /* If that's more padding than already wanted, queue it.
14106 But don't reduce padding already specified even if
14107 that is beyond the current truncation point. */
14108 field_width = max (lim, field_width);
14110 goto tail_recurse;
14112 else if (STRINGP (car) || CONSP (car))
14114 register int limit = 50;
14115 /* Limit is to protect against circular lists. */
14116 while (CONSP (elt)
14117 && --limit > 0
14118 && (precision <= 0 || n < precision))
14120 n += display_mode_element (it, depth, field_width - n,
14121 precision - n, XCAR (elt),
14122 props, risky);
14123 elt = XCDR (elt);
14127 break;
14129 default:
14130 invalid:
14131 if (frame_title_ptr)
14132 n += store_frame_title ("*invalid*", 0, precision - n);
14133 else if (!NILP (mode_line_string_list))
14134 n += store_mode_line_string ("*invalid*", Qnil, 0, 0, precision - n, Qnil);
14135 else
14136 n += display_string ("*invalid*", Qnil, Qnil, 0, 0, it, 0,
14137 precision - n, 0, 0);
14138 return n;
14141 /* Pad to FIELD_WIDTH. */
14142 if (field_width > 0 && n < field_width)
14144 if (frame_title_ptr)
14145 n += store_frame_title ("", field_width - n, 0);
14146 else if (!NILP (mode_line_string_list))
14147 n += store_mode_line_string ("", Qnil, 0, field_width - n, 0, Qnil);
14148 else
14149 n += display_string ("", Qnil, Qnil, 0, 0, it, field_width - n,
14150 0, 0, 0);
14153 return n;
14156 /* Store a mode-line string element in mode_line_string_list.
14158 If STRING is non-null, display that C string. Otherwise, the Lisp
14159 string LISP_STRING is displayed.
14161 FIELD_WIDTH is the minimum number of output glyphs to produce.
14162 If STRING has fewer characters than FIELD_WIDTH, pad to the right
14163 with spaces. FIELD_WIDTH <= 0 means don't pad.
14165 PRECISION is the maximum number of characters to output from
14166 STRING. PRECISION <= 0 means don't truncate the string.
14168 If COPY_STRING is non-zero, make a copy of LISP_STRING before adding
14169 properties to the string.
14171 PROPS are the properties to add to the string.
14172 The mode_line_string_face face property is always added to the string.
14175 static int store_mode_line_string (string, lisp_string, copy_string, field_width, precision, props)
14176 char *string;
14177 Lisp_Object lisp_string;
14178 int copy_string;
14179 int field_width;
14180 int precision;
14181 Lisp_Object props;
14183 int len;
14184 int n = 0;
14186 if (string != NULL)
14188 len = strlen (string);
14189 if (precision > 0 && len > precision)
14190 len = precision;
14191 lisp_string = make_string (string, len);
14192 if (NILP (props))
14193 props = mode_line_string_face_prop;
14194 else if (!NILP (mode_line_string_face))
14196 Lisp_Object face = Fplist_get (props, Qface);
14197 props = Fcopy_sequence (props);
14198 if (NILP (face))
14199 face = mode_line_string_face;
14200 else
14201 face = Fcons (face, Fcons (mode_line_string_face, Qnil));
14202 props = Fplist_put (props, Qface, face);
14204 Fadd_text_properties (make_number (0), make_number (len),
14205 props, lisp_string);
14207 else
14209 len = XFASTINT (Flength (lisp_string));
14210 if (precision > 0 && len > precision)
14212 len = precision;
14213 lisp_string = Fsubstring (lisp_string, make_number (0), make_number (len));
14214 precision = -1;
14216 if (!NILP (mode_line_string_face))
14218 Lisp_Object face;
14219 if (NILP (props))
14220 props = Ftext_properties_at (make_number (0), lisp_string);
14221 face = Fplist_get (props, Qface);
14222 if (NILP (face))
14223 face = mode_line_string_face;
14224 else
14225 face = Fcons (face, Fcons (mode_line_string_face, Qnil));
14226 props = Fcons (Qface, Fcons (face, Qnil));
14227 if (copy_string)
14228 lisp_string = Fcopy_sequence (lisp_string);
14230 if (!NILP (props))
14231 Fadd_text_properties (make_number (0), make_number (len),
14232 props, lisp_string);
14235 if (len > 0)
14237 mode_line_string_list = Fcons (lisp_string, mode_line_string_list);
14238 n += len;
14241 if (field_width > len)
14243 field_width -= len;
14244 lisp_string = Fmake_string (make_number (field_width), make_number (' '));
14245 if (!NILP (props))
14246 Fadd_text_properties (make_number (0), make_number (field_width),
14247 props, lisp_string);
14248 mode_line_string_list = Fcons (lisp_string, mode_line_string_list);
14249 n += field_width;
14252 return n;
14256 DEFUN ("format-mode-line", Fformat_mode_line, Sformat_mode_line,
14257 0, 3, 0,
14258 doc: /* Return the mode-line of selected window as a string.
14259 First optional arg FORMAT specifies a different format string (see
14260 `mode-line-format' for details) to use. If FORMAT is t, return
14261 the buffer's header-line. Second optional arg WINDOW specifies a
14262 different window to use as the context for the formatting.
14263 If third optional arg NO-PROPS is non-nil, string is not propertized. */)
14264 (format, window, no_props)
14265 Lisp_Object format, window, no_props;
14267 struct it it;
14268 int len;
14269 struct window *w;
14270 struct buffer *old_buffer = NULL;
14271 enum face_id face_id = DEFAULT_FACE_ID;
14273 if (NILP (window))
14274 window = selected_window;
14275 CHECK_WINDOW (window);
14276 w = XWINDOW (window);
14277 CHECK_BUFFER (w->buffer);
14279 if (XBUFFER (w->buffer) != current_buffer)
14281 old_buffer = current_buffer;
14282 set_buffer_internal_1 (XBUFFER (w->buffer));
14285 if (NILP (format) || EQ (format, Qt))
14287 face_id = NILP (format)
14288 ? CURRENT_MODE_LINE_FACE_ID (w) :
14289 HEADER_LINE_FACE_ID;
14290 format = NILP (format)
14291 ? current_buffer->mode_line_format
14292 : current_buffer->header_line_format;
14295 init_iterator (&it, w, -1, -1, NULL, face_id);
14297 if (NILP (no_props))
14299 mode_line_string_face =
14300 (face_id == MODE_LINE_FACE_ID ? Qmode_line :
14301 face_id == MODE_LINE_INACTIVE_FACE_ID ? Qmode_line_inactive :
14302 face_id == HEADER_LINE_FACE_ID ? Qheader_line : Qnil);
14304 mode_line_string_face_prop =
14305 NILP (mode_line_string_face) ? Qnil :
14306 Fcons (Qface, Fcons (mode_line_string_face, Qnil));
14308 /* We need a dummy last element in mode_line_string_list to
14309 indicate we are building the propertized mode-line string.
14310 Using mode_line_string_face_prop here GC protects it. */
14311 mode_line_string_list =
14312 Fcons (mode_line_string_face_prop, Qnil);
14313 frame_title_ptr = NULL;
14315 else
14317 mode_line_string_face_prop = Qnil;
14318 mode_line_string_list = Qnil;
14319 frame_title_ptr = frame_title_buf;
14322 push_frame_kboard (it.f);
14323 display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
14324 pop_frame_kboard ();
14326 if (old_buffer)
14327 set_buffer_internal_1 (old_buffer);
14329 if (NILP (no_props))
14331 Lisp_Object str;
14332 mode_line_string_list = Fnreverse (mode_line_string_list);
14333 str = Fmapconcat (intern ("identity"), XCDR (mode_line_string_list),
14334 make_string ("", 0));
14335 mode_line_string_face_prop = Qnil;
14336 mode_line_string_list = Qnil;
14337 return str;
14340 len = frame_title_ptr - frame_title_buf;
14341 if (len > 0 && frame_title_ptr[-1] == '-')
14343 /* Mode lines typically ends with numerous dashes; reduce to two dashes. */
14344 while (frame_title_ptr > frame_title_buf && *--frame_title_ptr == '-')
14346 frame_title_ptr += 3; /* restore last non-dash + two dashes */
14347 if (len > frame_title_ptr - frame_title_buf)
14348 len = frame_title_ptr - frame_title_buf;
14351 frame_title_ptr = NULL;
14352 return make_string (frame_title_buf, len);
14355 /* Write a null-terminated, right justified decimal representation of
14356 the positive integer D to BUF using a minimal field width WIDTH. */
14358 static void
14359 pint2str (buf, width, d)
14360 register char *buf;
14361 register int width;
14362 register int d;
14364 register char *p = buf;
14366 if (d <= 0)
14367 *p++ = '0';
14368 else
14370 while (d > 0)
14372 *p++ = d % 10 + '0';
14373 d /= 10;
14377 for (width -= (int) (p - buf); width > 0; --width)
14378 *p++ = ' ';
14379 *p-- = '\0';
14380 while (p > buf)
14382 d = *buf;
14383 *buf++ = *p;
14384 *p-- = d;
14388 /* Set a mnemonic character for coding_system (Lisp symbol) in BUF.
14389 If EOL_FLAG is 1, set also a mnemonic character for end-of-line
14390 type of CODING_SYSTEM. Return updated pointer into BUF. */
14392 static unsigned char invalid_eol_type[] = "(*invalid*)";
14394 static char *
14395 decode_mode_spec_coding (coding_system, buf, eol_flag)
14396 Lisp_Object coding_system;
14397 register char *buf;
14398 int eol_flag;
14400 Lisp_Object val;
14401 int multibyte = !NILP (current_buffer->enable_multibyte_characters);
14402 const unsigned char *eol_str;
14403 int eol_str_len;
14404 /* The EOL conversion we are using. */
14405 Lisp_Object eoltype;
14407 val = Fget (coding_system, Qcoding_system);
14408 eoltype = Qnil;
14410 if (!VECTORP (val)) /* Not yet decided. */
14412 if (multibyte)
14413 *buf++ = '-';
14414 if (eol_flag)
14415 eoltype = eol_mnemonic_undecided;
14416 /* Don't mention EOL conversion if it isn't decided. */
14418 else
14420 Lisp_Object eolvalue;
14422 eolvalue = Fget (coding_system, Qeol_type);
14424 if (multibyte)
14425 *buf++ = XFASTINT (AREF (val, 1));
14427 if (eol_flag)
14429 /* The EOL conversion that is normal on this system. */
14431 if (NILP (eolvalue)) /* Not yet decided. */
14432 eoltype = eol_mnemonic_undecided;
14433 else if (VECTORP (eolvalue)) /* Not yet decided. */
14434 eoltype = eol_mnemonic_undecided;
14435 else /* INTEGERP (eolvalue) -- 0:LF, 1:CRLF, 2:CR */
14436 eoltype = (XFASTINT (eolvalue) == 0
14437 ? eol_mnemonic_unix
14438 : (XFASTINT (eolvalue) == 1
14439 ? eol_mnemonic_dos : eol_mnemonic_mac));
14443 if (eol_flag)
14445 /* Mention the EOL conversion if it is not the usual one. */
14446 if (STRINGP (eoltype))
14448 eol_str = SDATA (eoltype);
14449 eol_str_len = SBYTES (eoltype);
14451 else if (INTEGERP (eoltype)
14452 && CHAR_VALID_P (XINT (eoltype), 0))
14454 unsigned char *tmp = (unsigned char *) alloca (MAX_MULTIBYTE_LENGTH);
14455 eol_str_len = CHAR_STRING (XINT (eoltype), tmp);
14456 eol_str = tmp;
14458 else
14460 eol_str = invalid_eol_type;
14461 eol_str_len = sizeof (invalid_eol_type) - 1;
14463 bcopy (eol_str, buf, eol_str_len);
14464 buf += eol_str_len;
14467 return buf;
14470 /* Return a string for the output of a mode line %-spec for window W,
14471 generated by character C. PRECISION >= 0 means don't return a
14472 string longer than that value. FIELD_WIDTH > 0 means pad the
14473 string returned with spaces to that value. Return 1 in *MULTIBYTE
14474 if the result is multibyte text. */
14476 static char lots_of_dashes[] = "--------------------------------------------------------------------------------------------------------------------------------------------";
14478 static char *
14479 decode_mode_spec (w, c, field_width, precision, multibyte)
14480 struct window *w;
14481 register int c;
14482 int field_width, precision;
14483 int *multibyte;
14485 Lisp_Object obj;
14486 struct frame *f = XFRAME (WINDOW_FRAME (w));
14487 char *decode_mode_spec_buf = f->decode_mode_spec_buffer;
14488 struct buffer *b = XBUFFER (w->buffer);
14490 obj = Qnil;
14491 *multibyte = 0;
14493 switch (c)
14495 case '*':
14496 if (!NILP (b->read_only))
14497 return "%";
14498 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
14499 return "*";
14500 return "-";
14502 case '+':
14503 /* This differs from %* only for a modified read-only buffer. */
14504 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
14505 return "*";
14506 if (!NILP (b->read_only))
14507 return "%";
14508 return "-";
14510 case '&':
14511 /* This differs from %* in ignoring read-only-ness. */
14512 if (BUF_MODIFF (b) > BUF_SAVE_MODIFF (b))
14513 return "*";
14514 return "-";
14516 case '%':
14517 return "%";
14519 case '[':
14521 int i;
14522 char *p;
14524 if (command_loop_level > 5)
14525 return "[[[... ";
14526 p = decode_mode_spec_buf;
14527 for (i = 0; i < command_loop_level; i++)
14528 *p++ = '[';
14529 *p = 0;
14530 return decode_mode_spec_buf;
14533 case ']':
14535 int i;
14536 char *p;
14538 if (command_loop_level > 5)
14539 return " ...]]]";
14540 p = decode_mode_spec_buf;
14541 for (i = 0; i < command_loop_level; i++)
14542 *p++ = ']';
14543 *p = 0;
14544 return decode_mode_spec_buf;
14547 case '-':
14549 register int i;
14551 /* Let lots_of_dashes be a string of infinite length. */
14552 if (!NILP (mode_line_string_list))
14553 return "--";
14554 if (field_width <= 0
14555 || field_width > sizeof (lots_of_dashes))
14557 for (i = 0; i < FRAME_MESSAGE_BUF_SIZE (f) - 1; ++i)
14558 decode_mode_spec_buf[i] = '-';
14559 decode_mode_spec_buf[i] = '\0';
14560 return decode_mode_spec_buf;
14562 else
14563 return lots_of_dashes;
14566 case 'b':
14567 obj = b->name;
14568 break;
14570 case 'c':
14572 int col = (int) current_column (); /* iftc */
14573 w->column_number_displayed = make_number (col);
14574 pint2str (decode_mode_spec_buf, field_width, col);
14575 return decode_mode_spec_buf;
14578 case 'F':
14579 /* %F displays the frame name. */
14580 if (!NILP (f->title))
14581 return (char *) SDATA (f->title);
14582 if (f->explicit_name || ! FRAME_WINDOW_P (f))
14583 return (char *) SDATA (f->name);
14584 return "Emacs";
14586 case 'f':
14587 obj = b->filename;
14588 break;
14590 case 'l':
14592 int startpos = XMARKER (w->start)->charpos;
14593 int startpos_byte = marker_byte_position (w->start);
14594 int line, linepos, linepos_byte, topline;
14595 int nlines, junk;
14596 int height = XFASTINT (w->height);
14598 /* If we decided that this buffer isn't suitable for line numbers,
14599 don't forget that too fast. */
14600 if (EQ (w->base_line_pos, w->buffer))
14601 goto no_value;
14602 /* But do forget it, if the window shows a different buffer now. */
14603 else if (BUFFERP (w->base_line_pos))
14604 w->base_line_pos = Qnil;
14606 /* If the buffer is very big, don't waste time. */
14607 if (INTEGERP (Vline_number_display_limit)
14608 && BUF_ZV (b) - BUF_BEGV (b) > XINT (Vline_number_display_limit))
14610 w->base_line_pos = Qnil;
14611 w->base_line_number = Qnil;
14612 goto no_value;
14615 if (!NILP (w->base_line_number)
14616 && !NILP (w->base_line_pos)
14617 && XFASTINT (w->base_line_pos) <= startpos)
14619 line = XFASTINT (w->base_line_number);
14620 linepos = XFASTINT (w->base_line_pos);
14621 linepos_byte = buf_charpos_to_bytepos (b, linepos);
14623 else
14625 line = 1;
14626 linepos = BUF_BEGV (b);
14627 linepos_byte = BUF_BEGV_BYTE (b);
14630 /* Count lines from base line to window start position. */
14631 nlines = display_count_lines (linepos, linepos_byte,
14632 startpos_byte,
14633 startpos, &junk);
14635 topline = nlines + line;
14637 /* Determine a new base line, if the old one is too close
14638 or too far away, or if we did not have one.
14639 "Too close" means it's plausible a scroll-down would
14640 go back past it. */
14641 if (startpos == BUF_BEGV (b))
14643 w->base_line_number = make_number (topline);
14644 w->base_line_pos = make_number (BUF_BEGV (b));
14646 else if (nlines < height + 25 || nlines > height * 3 + 50
14647 || linepos == BUF_BEGV (b))
14649 int limit = BUF_BEGV (b);
14650 int limit_byte = BUF_BEGV_BYTE (b);
14651 int position;
14652 int distance = (height * 2 + 30) * line_number_display_limit_width;
14654 if (startpos - distance > limit)
14656 limit = startpos - distance;
14657 limit_byte = CHAR_TO_BYTE (limit);
14660 nlines = display_count_lines (startpos, startpos_byte,
14661 limit_byte,
14662 - (height * 2 + 30),
14663 &position);
14664 /* If we couldn't find the lines we wanted within
14665 line_number_display_limit_width chars per line,
14666 give up on line numbers for this window. */
14667 if (position == limit_byte && limit == startpos - distance)
14669 w->base_line_pos = w->buffer;
14670 w->base_line_number = Qnil;
14671 goto no_value;
14674 w->base_line_number = make_number (topline - nlines);
14675 w->base_line_pos = make_number (BYTE_TO_CHAR (position));
14678 /* Now count lines from the start pos to point. */
14679 nlines = display_count_lines (startpos, startpos_byte,
14680 PT_BYTE, PT, &junk);
14682 /* Record that we did display the line number. */
14683 line_number_displayed = 1;
14685 /* Make the string to show. */
14686 pint2str (decode_mode_spec_buf, field_width, topline + nlines);
14687 return decode_mode_spec_buf;
14688 no_value:
14690 char* p = decode_mode_spec_buf;
14691 int pad = field_width - 2;
14692 while (pad-- > 0)
14693 *p++ = ' ';
14694 *p++ = '?';
14695 *p++ = '?';
14696 *p = '\0';
14697 return decode_mode_spec_buf;
14700 break;
14702 case 'm':
14703 obj = b->mode_name;
14704 break;
14706 case 'n':
14707 if (BUF_BEGV (b) > BUF_BEG (b) || BUF_ZV (b) < BUF_Z (b))
14708 return " Narrow";
14709 break;
14711 case 'p':
14713 int pos = marker_position (w->start);
14714 int total = BUF_ZV (b) - BUF_BEGV (b);
14716 if (XFASTINT (w->window_end_pos) <= BUF_Z (b) - BUF_ZV (b))
14718 if (pos <= BUF_BEGV (b))
14719 return "All";
14720 else
14721 return "Bottom";
14723 else if (pos <= BUF_BEGV (b))
14724 return "Top";
14725 else
14727 if (total > 1000000)
14728 /* Do it differently for a large value, to avoid overflow. */
14729 total = ((pos - BUF_BEGV (b)) + (total / 100) - 1) / (total / 100);
14730 else
14731 total = ((pos - BUF_BEGV (b)) * 100 + total - 1) / total;
14732 /* We can't normally display a 3-digit number,
14733 so get us a 2-digit number that is close. */
14734 if (total == 100)
14735 total = 99;
14736 sprintf (decode_mode_spec_buf, "%2d%%", total);
14737 return decode_mode_spec_buf;
14741 /* Display percentage of size above the bottom of the screen. */
14742 case 'P':
14744 int toppos = marker_position (w->start);
14745 int botpos = BUF_Z (b) - XFASTINT (w->window_end_pos);
14746 int total = BUF_ZV (b) - BUF_BEGV (b);
14748 if (botpos >= BUF_ZV (b))
14750 if (toppos <= BUF_BEGV (b))
14751 return "All";
14752 else
14753 return "Bottom";
14755 else
14757 if (total > 1000000)
14758 /* Do it differently for a large value, to avoid overflow. */
14759 total = ((botpos - BUF_BEGV (b)) + (total / 100) - 1) / (total / 100);
14760 else
14761 total = ((botpos - BUF_BEGV (b)) * 100 + total - 1) / total;
14762 /* We can't normally display a 3-digit number,
14763 so get us a 2-digit number that is close. */
14764 if (total == 100)
14765 total = 99;
14766 if (toppos <= BUF_BEGV (b))
14767 sprintf (decode_mode_spec_buf, "Top%2d%%", total);
14768 else
14769 sprintf (decode_mode_spec_buf, "%2d%%", total);
14770 return decode_mode_spec_buf;
14774 case 's':
14775 /* status of process */
14776 obj = Fget_buffer_process (w->buffer);
14777 if (NILP (obj))
14778 return "no process";
14779 #ifdef subprocesses
14780 obj = Fsymbol_name (Fprocess_status (obj));
14781 #endif
14782 break;
14784 case 't': /* indicate TEXT or BINARY */
14785 #ifdef MODE_LINE_BINARY_TEXT
14786 return MODE_LINE_BINARY_TEXT (b);
14787 #else
14788 return "T";
14789 #endif
14791 case 'z':
14792 /* coding-system (not including end-of-line format) */
14793 case 'Z':
14794 /* coding-system (including end-of-line type) */
14796 int eol_flag = (c == 'Z');
14797 char *p = decode_mode_spec_buf;
14799 if (! FRAME_WINDOW_P (f))
14801 /* No need to mention EOL here--the terminal never needs
14802 to do EOL conversion. */
14803 p = decode_mode_spec_coding (keyboard_coding.symbol, p, 0);
14804 p = decode_mode_spec_coding (terminal_coding.symbol, p, 0);
14806 p = decode_mode_spec_coding (b->buffer_file_coding_system,
14807 p, eol_flag);
14809 #if 0 /* This proves to be annoying; I think we can do without. -- rms. */
14810 #ifdef subprocesses
14811 obj = Fget_buffer_process (Fcurrent_buffer ());
14812 if (PROCESSP (obj))
14814 p = decode_mode_spec_coding (XPROCESS (obj)->decode_coding_system,
14815 p, eol_flag);
14816 p = decode_mode_spec_coding (XPROCESS (obj)->encode_coding_system,
14817 p, eol_flag);
14819 #endif /* subprocesses */
14820 #endif /* 0 */
14821 *p = 0;
14822 return decode_mode_spec_buf;
14826 if (STRINGP (obj))
14828 *multibyte = STRING_MULTIBYTE (obj);
14829 return (char *) SDATA (obj);
14831 else
14832 return "";
14836 /* Count up to COUNT lines starting from START / START_BYTE.
14837 But don't go beyond LIMIT_BYTE.
14838 Return the number of lines thus found (always nonnegative).
14840 Set *BYTE_POS_PTR to 1 if we found COUNT lines, 0 if we hit LIMIT. */
14842 static int
14843 display_count_lines (start, start_byte, limit_byte, count, byte_pos_ptr)
14844 int start, start_byte, limit_byte, count;
14845 int *byte_pos_ptr;
14847 register unsigned char *cursor;
14848 unsigned char *base;
14850 register int ceiling;
14851 register unsigned char *ceiling_addr;
14852 int orig_count = count;
14854 /* If we are not in selective display mode,
14855 check only for newlines. */
14856 int selective_display = (!NILP (current_buffer->selective_display)
14857 && !INTEGERP (current_buffer->selective_display));
14859 if (count > 0)
14861 while (start_byte < limit_byte)
14863 ceiling = BUFFER_CEILING_OF (start_byte);
14864 ceiling = min (limit_byte - 1, ceiling);
14865 ceiling_addr = BYTE_POS_ADDR (ceiling) + 1;
14866 base = (cursor = BYTE_POS_ADDR (start_byte));
14867 while (1)
14869 if (selective_display)
14870 while (*cursor != '\n' && *cursor != 015 && ++cursor != ceiling_addr)
14872 else
14873 while (*cursor != '\n' && ++cursor != ceiling_addr)
14876 if (cursor != ceiling_addr)
14878 if (--count == 0)
14880 start_byte += cursor - base + 1;
14881 *byte_pos_ptr = start_byte;
14882 return orig_count;
14884 else
14885 if (++cursor == ceiling_addr)
14886 break;
14888 else
14889 break;
14891 start_byte += cursor - base;
14894 else
14896 while (start_byte > limit_byte)
14898 ceiling = BUFFER_FLOOR_OF (start_byte - 1);
14899 ceiling = max (limit_byte, ceiling);
14900 ceiling_addr = BYTE_POS_ADDR (ceiling) - 1;
14901 base = (cursor = BYTE_POS_ADDR (start_byte - 1) + 1);
14902 while (1)
14904 if (selective_display)
14905 while (--cursor != ceiling_addr
14906 && *cursor != '\n' && *cursor != 015)
14908 else
14909 while (--cursor != ceiling_addr && *cursor != '\n')
14912 if (cursor != ceiling_addr)
14914 if (++count == 0)
14916 start_byte += cursor - base + 1;
14917 *byte_pos_ptr = start_byte;
14918 /* When scanning backwards, we should
14919 not count the newline posterior to which we stop. */
14920 return - orig_count - 1;
14923 else
14924 break;
14926 /* Here we add 1 to compensate for the last decrement
14927 of CURSOR, which took it past the valid range. */
14928 start_byte += cursor - base + 1;
14932 *byte_pos_ptr = limit_byte;
14934 if (count < 0)
14935 return - orig_count + count;
14936 return orig_count - count;
14942 /***********************************************************************
14943 Displaying strings
14944 ***********************************************************************/
14946 /* Display a NUL-terminated string, starting with index START.
14948 If STRING is non-null, display that C string. Otherwise, the Lisp
14949 string LISP_STRING is displayed.
14951 If FACE_STRING is not nil, FACE_STRING_POS is a position in
14952 FACE_STRING. Display STRING or LISP_STRING with the face at
14953 FACE_STRING_POS in FACE_STRING:
14955 Display the string in the environment given by IT, but use the
14956 standard display table, temporarily.
14958 FIELD_WIDTH is the minimum number of output glyphs to produce.
14959 If STRING has fewer characters than FIELD_WIDTH, pad to the right
14960 with spaces. If STRING has more characters, more than FIELD_WIDTH
14961 glyphs will be produced. FIELD_WIDTH <= 0 means don't pad.
14963 PRECISION is the maximum number of characters to output from
14964 STRING. PRECISION < 0 means don't truncate the string.
14966 This is roughly equivalent to printf format specifiers:
14968 FIELD_WIDTH PRECISION PRINTF
14969 ----------------------------------------
14970 -1 -1 %s
14971 -1 10 %.10s
14972 10 -1 %10s
14973 20 10 %20.10s
14975 MULTIBYTE zero means do not display multibyte chars, > 0 means do
14976 display them, and < 0 means obey the current buffer's value of
14977 enable_multibyte_characters.
14979 Value is the number of glyphs produced. */
14981 static int
14982 display_string (string, lisp_string, face_string, face_string_pos,
14983 start, it, field_width, precision, max_x, multibyte)
14984 unsigned char *string;
14985 Lisp_Object lisp_string;
14986 Lisp_Object face_string;
14987 int face_string_pos;
14988 int start;
14989 struct it *it;
14990 int field_width, precision, max_x;
14991 int multibyte;
14993 int hpos_at_start = it->hpos;
14994 int saved_face_id = it->face_id;
14995 struct glyph_row *row = it->glyph_row;
14997 /* Initialize the iterator IT for iteration over STRING beginning
14998 with index START. */
14999 reseat_to_string (it, string, lisp_string, start,
15000 precision, field_width, multibyte);
15002 /* If displaying STRING, set up the face of the iterator
15003 from LISP_STRING, if that's given. */
15004 if (STRINGP (face_string))
15006 int endptr;
15007 struct face *face;
15009 it->face_id
15010 = face_at_string_position (it->w, face_string, face_string_pos,
15011 0, it->region_beg_charpos,
15012 it->region_end_charpos,
15013 &endptr, it->base_face_id, 0);
15014 face = FACE_FROM_ID (it->f, it->face_id);
15015 it->face_box_p = face->box != FACE_NO_BOX;
15018 /* Set max_x to the maximum allowed X position. Don't let it go
15019 beyond the right edge of the window. */
15020 if (max_x <= 0)
15021 max_x = it->last_visible_x;
15022 else
15023 max_x = min (max_x, it->last_visible_x);
15025 /* Skip over display elements that are not visible. because IT->w is
15026 hscrolled. */
15027 if (it->current_x < it->first_visible_x)
15028 move_it_in_display_line_to (it, 100000, it->first_visible_x,
15029 MOVE_TO_POS | MOVE_TO_X);
15031 row->ascent = it->max_ascent;
15032 row->height = it->max_ascent + it->max_descent;
15033 row->phys_ascent = it->max_phys_ascent;
15034 row->phys_height = it->max_phys_ascent + it->max_phys_descent;
15036 /* This condition is for the case that we are called with current_x
15037 past last_visible_x. */
15038 while (it->current_x < max_x)
15040 int x_before, x, n_glyphs_before, i, nglyphs;
15042 /* Get the next display element. */
15043 if (!get_next_display_element (it))
15044 break;
15046 /* Produce glyphs. */
15047 x_before = it->current_x;
15048 n_glyphs_before = it->glyph_row->used[TEXT_AREA];
15049 PRODUCE_GLYPHS (it);
15051 nglyphs = it->glyph_row->used[TEXT_AREA] - n_glyphs_before;
15052 i = 0;
15053 x = x_before;
15054 while (i < nglyphs)
15056 struct glyph *glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
15058 if (!it->truncate_lines_p
15059 && x + glyph->pixel_width > max_x)
15061 /* End of continued line or max_x reached. */
15062 if (CHAR_GLYPH_PADDING_P (*glyph))
15064 /* A wide character is unbreakable. */
15065 it->glyph_row->used[TEXT_AREA] = n_glyphs_before;
15066 it->current_x = x_before;
15068 else
15070 it->glyph_row->used[TEXT_AREA] = n_glyphs_before + i;
15071 it->current_x = x;
15073 break;
15075 else if (x + glyph->pixel_width > it->first_visible_x)
15077 /* Glyph is at least partially visible. */
15078 ++it->hpos;
15079 if (x < it->first_visible_x)
15080 it->glyph_row->x = x - it->first_visible_x;
15082 else
15084 /* Glyph is off the left margin of the display area.
15085 Should not happen. */
15086 abort ();
15089 row->ascent = max (row->ascent, it->max_ascent);
15090 row->height = max (row->height, it->max_ascent + it->max_descent);
15091 row->phys_ascent = max (row->phys_ascent, it->max_phys_ascent);
15092 row->phys_height = max (row->phys_height,
15093 it->max_phys_ascent + it->max_phys_descent);
15094 x += glyph->pixel_width;
15095 ++i;
15098 /* Stop if max_x reached. */
15099 if (i < nglyphs)
15100 break;
15102 /* Stop at line ends. */
15103 if (ITERATOR_AT_END_OF_LINE_P (it))
15105 it->continuation_lines_width = 0;
15106 break;
15109 set_iterator_to_next (it, 1);
15111 /* Stop if truncating at the right edge. */
15112 if (it->truncate_lines_p
15113 && it->current_x >= it->last_visible_x)
15115 /* Add truncation mark, but don't do it if the line is
15116 truncated at a padding space. */
15117 if (IT_CHARPOS (*it) < it->string_nchars)
15119 if (!FRAME_WINDOW_P (it->f))
15121 int i, n;
15123 if (it->current_x > it->last_visible_x)
15125 for (i = row->used[TEXT_AREA] - 1; i > 0; --i)
15126 if (!CHAR_GLYPH_PADDING_P (row->glyphs[TEXT_AREA][i]))
15127 break;
15128 for (n = row->used[TEXT_AREA]; i < n; ++i)
15130 row->used[TEXT_AREA] = i;
15131 produce_special_glyphs (it, IT_TRUNCATION);
15134 produce_special_glyphs (it, IT_TRUNCATION);
15136 it->glyph_row->truncated_on_right_p = 1;
15138 break;
15142 /* Maybe insert a truncation at the left. */
15143 if (it->first_visible_x
15144 && IT_CHARPOS (*it) > 0)
15146 if (!FRAME_WINDOW_P (it->f))
15147 insert_left_trunc_glyphs (it);
15148 it->glyph_row->truncated_on_left_p = 1;
15151 it->face_id = saved_face_id;
15153 /* Value is number of columns displayed. */
15154 return it->hpos - hpos_at_start;
15159 /* This is like a combination of memq and assq. Return 1/2 if PROPVAL
15160 appears as an element of LIST or as the car of an element of LIST.
15161 If PROPVAL is a list, compare each element against LIST in that
15162 way, and return 1/2 if any element of PROPVAL is found in LIST.
15163 Otherwise return 0. This function cannot quit.
15164 The return value is 2 if the text is invisible but with an ellipsis
15165 and 1 if it's invisible and without an ellipsis. */
15168 invisible_p (propval, list)
15169 register Lisp_Object propval;
15170 Lisp_Object list;
15172 register Lisp_Object tail, proptail;
15174 for (tail = list; CONSP (tail); tail = XCDR (tail))
15176 register Lisp_Object tem;
15177 tem = XCAR (tail);
15178 if (EQ (propval, tem))
15179 return 1;
15180 if (CONSP (tem) && EQ (propval, XCAR (tem)))
15181 return NILP (XCDR (tem)) ? 1 : 2;
15184 if (CONSP (propval))
15186 for (proptail = propval; CONSP (proptail); proptail = XCDR (proptail))
15188 Lisp_Object propelt;
15189 propelt = XCAR (proptail);
15190 for (tail = list; CONSP (tail); tail = XCDR (tail))
15192 register Lisp_Object tem;
15193 tem = XCAR (tail);
15194 if (EQ (propelt, tem))
15195 return 1;
15196 if (CONSP (tem) && EQ (propelt, XCAR (tem)))
15197 return NILP (XCDR (tem)) ? 1 : 2;
15202 return 0;
15206 /***********************************************************************
15207 Cursor types
15208 ***********************************************************************/
15210 /* Value is the internal representation of the specified cursor type
15211 ARG. If type is BAR_CURSOR, return in *WIDTH the specified width
15212 of the bar cursor. */
15214 enum text_cursor_kinds
15215 get_specified_cursor_type (arg, width)
15216 Lisp_Object arg;
15217 int *width;
15219 enum text_cursor_kinds type;
15221 if (NILP (arg))
15222 return NO_CURSOR;
15224 if (EQ (arg, Qbox))
15225 return FILLED_BOX_CURSOR;
15227 if (EQ (arg, Qhollow))
15228 return HOLLOW_BOX_CURSOR;
15230 if (EQ (arg, Qbar))
15232 *width = 2;
15233 return BAR_CURSOR;
15236 if (CONSP (arg)
15237 && EQ (XCAR (arg), Qbar)
15238 && INTEGERP (XCDR (arg))
15239 && XINT (XCDR (arg)) >= 0)
15241 *width = XINT (XCDR (arg));
15242 return BAR_CURSOR;
15245 if (EQ (arg, Qhbar))
15247 *width = 2;
15248 return HBAR_CURSOR;
15251 if (CONSP (arg)
15252 && EQ (XCAR (arg), Qhbar)
15253 && INTEGERP (XCDR (arg))
15254 && XINT (XCDR (arg)) >= 0)
15256 *width = XINT (XCDR (arg));
15257 return HBAR_CURSOR;
15260 /* Treat anything unknown as "hollow box cursor".
15261 It was bad to signal an error; people have trouble fixing
15262 .Xdefaults with Emacs, when it has something bad in it. */
15263 type = HOLLOW_BOX_CURSOR;
15265 return type;
15268 /* Set the default cursor types for specified frame. */
15269 void
15270 set_frame_cursor_types (f, arg)
15271 struct frame *f;
15272 Lisp_Object arg;
15274 int width;
15275 Lisp_Object tem;
15277 FRAME_DESIRED_CURSOR (f) = get_specified_cursor_type (arg, &width);
15278 FRAME_CURSOR_WIDTH (f) = width;
15280 /* By default, set up the blink-off state depending on the on-state. */
15282 tem = Fassoc (arg, Vblink_cursor_alist);
15283 if (!NILP (tem))
15285 FRAME_BLINK_OFF_CURSOR (f)
15286 = get_specified_cursor_type (XCDR (tem), &width);
15287 FRAME_BLINK_OFF_CURSOR_WIDTH (f) = width;
15289 else
15290 FRAME_BLINK_OFF_CURSOR (f) = DEFAULT_CURSOR;
15294 /* Return the cursor we want to be displayed in window W. Return
15295 width of bar/hbar cursor through WIDTH arg. Return with
15296 ACTIVE_CURSOR arg set to 1 if cursor in window W is `active'
15297 (i.e. if the `system caret' should track this cursor).
15299 In a mini-buffer window, we want the cursor only to appear if we
15300 are reading input from this window. For the selected window, we
15301 want the cursor type given by the frame parameter or buffer local
15302 setting of cursor-type. If explicitly marked off, draw no cursor.
15303 In all other cases, we want a hollow box cursor. */
15305 enum text_cursor_kinds
15306 get_window_cursor_type (w, width, active_cursor)
15307 struct window *w;
15308 int *width;
15309 int *active_cursor;
15311 struct frame *f = XFRAME (w->frame);
15312 struct buffer *b = XBUFFER (w->buffer);
15313 int cursor_type = DEFAULT_CURSOR;
15314 Lisp_Object alt_cursor;
15315 int non_selected = 0;
15317 *active_cursor = 1;
15319 /* Echo area */
15320 if (cursor_in_echo_area
15321 && FRAME_HAS_MINIBUF_P (f)
15322 && EQ (FRAME_MINIBUF_WINDOW (f), echo_area_window))
15324 if (w == XWINDOW (echo_area_window))
15326 *width = FRAME_CURSOR_WIDTH (f);
15327 return FRAME_DESIRED_CURSOR (f);
15330 *active_cursor = 0;
15331 non_selected = 1;
15334 /* Nonselected window or nonselected frame. */
15335 else if (w != XWINDOW (f->selected_window)
15336 #ifdef HAVE_WINDOW_SYSTEM
15337 || f != FRAME_X_DISPLAY_INFO (f)->x_highlight_frame
15338 #endif
15341 *active_cursor = 0;
15343 if (MINI_WINDOW_P (w) && minibuf_level == 0)
15344 return NO_CURSOR;
15346 non_selected = 1;
15349 /* Never display a cursor in a window in which cursor-type is nil. */
15350 if (NILP (b->cursor_type))
15351 return NO_CURSOR;
15353 /* Use cursor-in-non-selected-windows for non-selected window or frame. */
15354 if (non_selected)
15356 alt_cursor = Fbuffer_local_value (Qcursor_in_non_selected_windows, w->buffer);
15357 return get_specified_cursor_type (alt_cursor, width);
15360 /* Get the normal cursor type for this window. */
15361 if (EQ (b->cursor_type, Qt))
15363 cursor_type = FRAME_DESIRED_CURSOR (f);
15364 *width = FRAME_CURSOR_WIDTH (f);
15366 else
15367 cursor_type = get_specified_cursor_type (b->cursor_type, width);
15369 /* Use normal cursor if not blinked off. */
15370 if (!w->cursor_off_p)
15371 return cursor_type;
15373 /* Cursor is blinked off, so determine how to "toggle" it. */
15375 /* First look for an entry matching the buffer's cursor-type in blink-cursor-alist. */
15376 if ((alt_cursor = Fassoc (b->cursor_type, Vblink_cursor_alist), !NILP (alt_cursor)))
15377 return get_specified_cursor_type (XCDR (alt_cursor), width);
15379 /* Then see if frame has specified a specific blink off cursor type. */
15380 if (FRAME_BLINK_OFF_CURSOR (f) != DEFAULT_CURSOR)
15382 *width = FRAME_BLINK_OFF_CURSOR_WIDTH (f);
15383 return FRAME_BLINK_OFF_CURSOR (f);
15386 /* Finally perform built-in cursor blinking:
15387 filled box <-> hollow box
15388 wide [h]bar <-> narrow [h]bar
15389 narrow [h]bar <-> no cursor
15390 other type <-> no cursor */
15392 if (cursor_type == FILLED_BOX_CURSOR)
15393 return HOLLOW_BOX_CURSOR;
15395 if ((cursor_type == BAR_CURSOR || cursor_type == HBAR_CURSOR) && *width > 1)
15397 *width = 1;
15398 return cursor_type;
15401 return NO_CURSOR;
15405 /***********************************************************************
15406 Initialization
15407 ***********************************************************************/
15409 void
15410 syms_of_xdisp ()
15412 Vwith_echo_area_save_vector = Qnil;
15413 staticpro (&Vwith_echo_area_save_vector);
15415 Vmessage_stack = Qnil;
15416 staticpro (&Vmessage_stack);
15418 Qinhibit_redisplay = intern ("inhibit-redisplay");
15419 staticpro (&Qinhibit_redisplay);
15421 message_dolog_marker1 = Fmake_marker ();
15422 staticpro (&message_dolog_marker1);
15423 message_dolog_marker2 = Fmake_marker ();
15424 staticpro (&message_dolog_marker2);
15425 message_dolog_marker3 = Fmake_marker ();
15426 staticpro (&message_dolog_marker3);
15428 #if GLYPH_DEBUG
15429 defsubr (&Sdump_frame_glyph_matrix);
15430 defsubr (&Sdump_glyph_matrix);
15431 defsubr (&Sdump_glyph_row);
15432 defsubr (&Sdump_tool_bar_row);
15433 defsubr (&Strace_redisplay);
15434 defsubr (&Strace_to_stderr);
15435 #endif
15436 #ifdef HAVE_WINDOW_SYSTEM
15437 defsubr (&Stool_bar_lines_needed);
15438 #endif
15439 defsubr (&Sformat_mode_line);
15441 staticpro (&Qmenu_bar_update_hook);
15442 Qmenu_bar_update_hook = intern ("menu-bar-update-hook");
15444 staticpro (&Qoverriding_terminal_local_map);
15445 Qoverriding_terminal_local_map = intern ("overriding-terminal-local-map");
15447 staticpro (&Qoverriding_local_map);
15448 Qoverriding_local_map = intern ("overriding-local-map");
15450 staticpro (&Qwindow_scroll_functions);
15451 Qwindow_scroll_functions = intern ("window-scroll-functions");
15453 staticpro (&Qredisplay_end_trigger_functions);
15454 Qredisplay_end_trigger_functions = intern ("redisplay-end-trigger-functions");
15456 staticpro (&Qinhibit_point_motion_hooks);
15457 Qinhibit_point_motion_hooks = intern ("inhibit-point-motion-hooks");
15459 QCdata = intern (":data");
15460 staticpro (&QCdata);
15461 Qdisplay = intern ("display");
15462 staticpro (&Qdisplay);
15463 Qspace_width = intern ("space-width");
15464 staticpro (&Qspace_width);
15465 Qraise = intern ("raise");
15466 staticpro (&Qraise);
15467 Qspace = intern ("space");
15468 staticpro (&Qspace);
15469 Qmargin = intern ("margin");
15470 staticpro (&Qmargin);
15471 Qleft_margin = intern ("left-margin");
15472 staticpro (&Qleft_margin);
15473 Qright_margin = intern ("right-margin");
15474 staticpro (&Qright_margin);
15475 Qalign_to = intern ("align-to");
15476 staticpro (&Qalign_to);
15477 QCalign_to = intern (":align-to");
15478 staticpro (&QCalign_to);
15479 Qrelative_width = intern ("relative-width");
15480 staticpro (&Qrelative_width);
15481 QCrelative_width = intern (":relative-width");
15482 staticpro (&QCrelative_width);
15483 QCrelative_height = intern (":relative-height");
15484 staticpro (&QCrelative_height);
15485 QCeval = intern (":eval");
15486 staticpro (&QCeval);
15487 QCpropertize = intern (":propertize");
15488 staticpro (&QCpropertize);
15489 Qwhen = intern ("when");
15490 staticpro (&Qwhen);
15491 QCfile = intern (":file");
15492 staticpro (&QCfile);
15493 Qfontified = intern ("fontified");
15494 staticpro (&Qfontified);
15495 Qfontification_functions = intern ("fontification-functions");
15496 staticpro (&Qfontification_functions);
15497 Qtrailing_whitespace = intern ("trailing-whitespace");
15498 staticpro (&Qtrailing_whitespace);
15499 Qimage = intern ("image");
15500 staticpro (&Qimage);
15501 Qmessage_truncate_lines = intern ("message-truncate-lines");
15502 staticpro (&Qmessage_truncate_lines);
15503 Qcursor_in_non_selected_windows = intern ("cursor-in-non-selected-windows");
15504 staticpro (&Qcursor_in_non_selected_windows);
15505 Qgrow_only = intern ("grow-only");
15506 staticpro (&Qgrow_only);
15507 Qinhibit_menubar_update = intern ("inhibit-menubar-update");
15508 staticpro (&Qinhibit_menubar_update);
15509 Qinhibit_eval_during_redisplay = intern ("inhibit-eval-during-redisplay");
15510 staticpro (&Qinhibit_eval_during_redisplay);
15511 Qposition = intern ("position");
15512 staticpro (&Qposition);
15513 Qbuffer_position = intern ("buffer-position");
15514 staticpro (&Qbuffer_position);
15515 Qobject = intern ("object");
15516 staticpro (&Qobject);
15517 Qbar = intern ("bar");
15518 staticpro (&Qbar);
15519 Qhbar = intern ("hbar");
15520 staticpro (&Qhbar);
15521 Qbox = intern ("box");
15522 staticpro (&Qbox);
15523 Qhollow = intern ("hollow");
15524 staticpro (&Qhollow);
15525 Qrisky_local_variable = intern ("risky-local-variable");
15526 staticpro (&Qrisky_local_variable);
15527 Qinhibit_free_realized_faces = intern ("inhibit-free-realized-faces");
15528 staticpro (&Qinhibit_free_realized_faces);
15530 list_of_error = Fcons (intern ("error"), Qnil);
15531 staticpro (&list_of_error);
15533 last_arrow_position = Qnil;
15534 last_arrow_string = Qnil;
15535 staticpro (&last_arrow_position);
15536 staticpro (&last_arrow_string);
15538 echo_buffer[0] = echo_buffer[1] = Qnil;
15539 staticpro (&echo_buffer[0]);
15540 staticpro (&echo_buffer[1]);
15542 echo_area_buffer[0] = echo_area_buffer[1] = Qnil;
15543 staticpro (&echo_area_buffer[0]);
15544 staticpro (&echo_area_buffer[1]);
15546 Vmessages_buffer_name = build_string ("*Messages*");
15547 staticpro (&Vmessages_buffer_name);
15549 mode_line_proptrans_alist = Qnil;
15550 staticpro (&mode_line_proptrans_alist);
15552 mode_line_string_list = Qnil;
15553 staticpro (&mode_line_string_list);
15555 DEFVAR_LISP ("show-trailing-whitespace", &Vshow_trailing_whitespace,
15556 doc: /* Non-nil means highlight trailing whitespace.
15557 The face used for trailing whitespace is `trailing-whitespace'. */);
15558 Vshow_trailing_whitespace = Qnil;
15560 DEFVAR_LISP ("inhibit-redisplay", &Vinhibit_redisplay,
15561 doc: /* Non-nil means don't actually do any redisplay.
15562 This is used for internal purposes. */);
15563 Vinhibit_redisplay = Qnil;
15565 DEFVAR_LISP ("global-mode-string", &Vglobal_mode_string,
15566 doc: /* String (or mode line construct) included (normally) in `mode-line-format'. */);
15567 Vglobal_mode_string = Qnil;
15569 DEFVAR_LISP ("overlay-arrow-position", &Voverlay_arrow_position,
15570 doc: /* Marker for where to display an arrow on top of the buffer text.
15571 This must be the beginning of a line in order to work.
15572 See also `overlay-arrow-string'. */);
15573 Voverlay_arrow_position = Qnil;
15575 DEFVAR_LISP ("overlay-arrow-string", &Voverlay_arrow_string,
15576 doc: /* String to display as an arrow. See also `overlay-arrow-position'. */);
15577 Voverlay_arrow_string = Qnil;
15579 DEFVAR_INT ("scroll-step", &scroll_step,
15580 doc: /* *The number of lines to try scrolling a window by when point moves out.
15581 If that fails to bring point back on frame, point is centered instead.
15582 If this is zero, point is always centered after it moves off frame.
15583 If you want scrolling to always be a line at a time, you should set
15584 `scroll-conservatively' to a large value rather than set this to 1. */);
15586 DEFVAR_INT ("scroll-conservatively", &scroll_conservatively,
15587 doc: /* *Scroll up to this many lines, to bring point back on screen.
15588 A value of zero means to scroll the text to center point vertically
15589 in the window. */);
15590 scroll_conservatively = 0;
15592 DEFVAR_INT ("scroll-margin", &scroll_margin,
15593 doc: /* *Number of lines of margin at the top and bottom of a window.
15594 Recenter the window whenever point gets within this many lines
15595 of the top or bottom of the window. */);
15596 scroll_margin = 0;
15598 #if GLYPH_DEBUG
15599 DEFVAR_INT ("debug-end-pos", &debug_end_pos, doc: /* Don't ask. */);
15600 #endif
15602 DEFVAR_BOOL ("truncate-partial-width-windows",
15603 &truncate_partial_width_windows,
15604 doc: /* *Non-nil means truncate lines in all windows less than full frame wide. */);
15605 truncate_partial_width_windows = 1;
15607 DEFVAR_BOOL ("mode-line-inverse-video", &mode_line_inverse_video,
15608 doc: /* nil means display the mode-line/header-line/menu-bar in the default face.
15609 Any other value means to use the appropriate face, `mode-line',
15610 `header-line', or `menu' respectively. */);
15611 mode_line_inverse_video = 1;
15613 DEFVAR_LISP ("line-number-display-limit", &Vline_number_display_limit,
15614 doc: /* *Maximum buffer size for which line number should be displayed.
15615 If the buffer is bigger than this, the line number does not appear
15616 in the mode line. A value of nil means no limit. */);
15617 Vline_number_display_limit = Qnil;
15619 DEFVAR_INT ("line-number-display-limit-width",
15620 &line_number_display_limit_width,
15621 doc: /* *Maximum line width (in characters) for line number display.
15622 If the average length of the lines near point is bigger than this, then the
15623 line number may be omitted from the mode line. */);
15624 line_number_display_limit_width = 200;
15626 DEFVAR_BOOL ("highlight-nonselected-windows", &highlight_nonselected_windows,
15627 doc: /* *Non-nil means highlight region even in nonselected windows. */);
15628 highlight_nonselected_windows = 0;
15630 DEFVAR_BOOL ("multiple-frames", &multiple_frames,
15631 doc: /* Non-nil if more than one frame is visible on this display.
15632 Minibuffer-only frames don't count, but iconified frames do.
15633 This variable is not guaranteed to be accurate except while processing
15634 `frame-title-format' and `icon-title-format'. */);
15636 DEFVAR_LISP ("frame-title-format", &Vframe_title_format,
15637 doc: /* Template for displaying the title bar of visible frames.
15638 \(Assuming the window manager supports this feature.)
15639 This variable has the same structure as `mode-line-format' (which see),
15640 and is used only on frames for which no explicit name has been set
15641 \(see `modify-frame-parameters'). */);
15642 DEFVAR_LISP ("icon-title-format", &Vicon_title_format,
15643 doc: /* Template for displaying the title bar of an iconified frame.
15644 \(Assuming the window manager supports this feature.)
15645 This variable has the same structure as `mode-line-format' (which see),
15646 and is used only on frames for which no explicit name has been set
15647 \(see `modify-frame-parameters'). */);
15648 Vicon_title_format
15649 = Vframe_title_format
15650 = Fcons (intern ("multiple-frames"),
15651 Fcons (build_string ("%b"),
15652 Fcons (Fcons (empty_string,
15653 Fcons (intern ("invocation-name"),
15654 Fcons (build_string ("@"),
15655 Fcons (intern ("system-name"),
15656 Qnil)))),
15657 Qnil)));
15659 DEFVAR_LISP ("message-log-max", &Vmessage_log_max,
15660 doc: /* Maximum number of lines to keep in the message log buffer.
15661 If nil, disable message logging. If t, log messages but don't truncate
15662 the buffer when it becomes large. */);
15663 Vmessage_log_max = make_number (50);
15665 DEFVAR_LISP ("window-size-change-functions", &Vwindow_size_change_functions,
15666 doc: /* Functions called before redisplay, if window sizes have changed.
15667 The value should be a list of functions that take one argument.
15668 Just before redisplay, for each frame, if any of its windows have changed
15669 size since the last redisplay, or have been split or deleted,
15670 all the functions in the list are called, with the frame as argument. */);
15671 Vwindow_size_change_functions = Qnil;
15673 DEFVAR_LISP ("window-scroll-functions", &Vwindow_scroll_functions,
15674 doc: /* List of Functions to call before redisplaying a window with scrolling.
15675 Each function is called with two arguments, the window
15676 and its new display-start position. Note that the value of `window-end'
15677 is not valid when these functions are called. */);
15678 Vwindow_scroll_functions = Qnil;
15680 DEFVAR_BOOL ("auto-resize-tool-bars", &auto_resize_tool_bars_p,
15681 doc: /* *Non-nil means automatically resize tool-bars.
15682 This increases a tool-bar's height if not all tool-bar items are visible.
15683 It decreases a tool-bar's height when it would display blank lines
15684 otherwise. */);
15685 auto_resize_tool_bars_p = 1;
15687 DEFVAR_BOOL ("auto-raise-tool-bar-buttons", &auto_raise_tool_bar_buttons_p,
15688 doc: /* *Non-nil means raise tool-bar buttons when the mouse moves over them. */);
15689 auto_raise_tool_bar_buttons_p = 1;
15691 DEFVAR_LISP ("tool-bar-button-margin", &Vtool_bar_button_margin,
15692 doc: /* *Margin around tool-bar buttons in pixels.
15693 If an integer, use that for both horizontal and vertical margins.
15694 Otherwise, value should be a pair of integers `(HORZ . VERT)' with
15695 HORZ specifying the horizontal margin, and VERT specifying the
15696 vertical margin. */);
15697 Vtool_bar_button_margin = make_number (DEFAULT_TOOL_BAR_BUTTON_MARGIN);
15699 DEFVAR_INT ("tool-bar-button-relief", &tool_bar_button_relief,
15700 doc: /* *Relief thickness of tool-bar buttons. */);
15701 tool_bar_button_relief = DEFAULT_TOOL_BAR_BUTTON_RELIEF;
15703 DEFVAR_LISP ("fontification-functions", &Vfontification_functions,
15704 doc: /* List of functions to call to fontify regions of text.
15705 Each function is called with one argument POS. Functions must
15706 fontify a region starting at POS in the current buffer, and give
15707 fontified regions the property `fontified'. */);
15708 Vfontification_functions = Qnil;
15709 Fmake_variable_buffer_local (Qfontification_functions);
15711 DEFVAR_BOOL ("unibyte-display-via-language-environment",
15712 &unibyte_display_via_language_environment,
15713 doc: /* *Non-nil means display unibyte text according to language environment.
15714 Specifically this means that unibyte non-ASCII characters
15715 are displayed by converting them to the equivalent multibyte characters
15716 according to the current language environment. As a result, they are
15717 displayed according to the current fontset. */);
15718 unibyte_display_via_language_environment = 0;
15720 DEFVAR_LISP ("max-mini-window-height", &Vmax_mini_window_height,
15721 doc: /* *Maximum height for resizing mini-windows.
15722 If a float, it specifies a fraction of the mini-window frame's height.
15723 If an integer, it specifies a number of lines. */);
15724 Vmax_mini_window_height = make_float (0.25);
15726 DEFVAR_LISP ("resize-mini-windows", &Vresize_mini_windows,
15727 doc: /* *How to resize mini-windows.
15728 A value of nil means don't automatically resize mini-windows.
15729 A value of t means resize them to fit the text displayed in them.
15730 A value of `grow-only', the default, means let mini-windows grow
15731 only, until their display becomes empty, at which point the windows
15732 go back to their normal size. */);
15733 Vresize_mini_windows = Qgrow_only;
15735 DEFVAR_LISP ("cursor-in-non-selected-windows",
15736 &Vcursor_in_non_selected_windows,
15737 doc: /* *Cursor type to display in non-selected windows.
15738 t means to use hollow box cursor. See `cursor-type' for other values. */);
15739 Vcursor_in_non_selected_windows = Qt;
15741 DEFVAR_LISP ("blink-cursor-alist", &Vblink_cursor_alist,
15742 doc: /* Alist specifying how to blink the cursor off.
15743 Each element has the form (ON-STATE . OFF-STATE). Whenever the
15744 `cursor-type' frame-parameter or variable equals ON-STATE,
15745 comparing using `equal', Emacs uses OFF-STATE to specify
15746 how to blink it off. */);
15747 Vblink_cursor_alist = Qnil;
15749 DEFVAR_BOOL ("auto-hscroll-mode", &automatic_hscrolling_p,
15750 doc: /* *Non-nil means scroll the display automatically to make point visible. */);
15751 automatic_hscrolling_p = 1;
15753 DEFVAR_INT ("hscroll-margin", &hscroll_margin,
15754 doc: /* *How many columns away from the window edge point is allowed to get
15755 before automatic hscrolling will horizontally scroll the window. */);
15756 hscroll_margin = 5;
15758 DEFVAR_LISP ("hscroll-step", &Vhscroll_step,
15759 doc: /* *How many columns to scroll the window when point gets too close to the edge.
15760 When point is less than `automatic-hscroll-margin' columns from the window
15761 edge, automatic hscrolling will scroll the window by the amount of columns
15762 determined by this variable. If its value is a positive integer, scroll that
15763 many columns. If it's a positive floating-point number, it specifies the
15764 fraction of the window's width to scroll. If it's nil or zero, point will be
15765 centered horizontally after the scroll. Any other value, including negative
15766 numbers, are treated as if the value were zero.
15768 Automatic hscrolling always moves point outside the scroll margin, so if
15769 point was more than scroll step columns inside the margin, the window will
15770 scroll more than the value given by the scroll step.
15772 Note that the lower bound for automatic hscrolling specified by `scroll-left'
15773 and `scroll-right' overrides this variable's effect. */);
15774 Vhscroll_step = make_number (0);
15776 DEFVAR_LISP ("image-types", &Vimage_types,
15777 doc: /* List of supported image types.
15778 Each element of the list is a symbol for a supported image type. */);
15779 Vimage_types = Qnil;
15781 DEFVAR_BOOL ("message-truncate-lines", &message_truncate_lines,
15782 doc: /* If non-nil, messages are truncated instead of resizing the echo area.
15783 Bind this around calls to `message' to let it take effect. */);
15784 message_truncate_lines = 0;
15786 DEFVAR_LISP ("menu-bar-update-hook", &Vmenu_bar_update_hook,
15787 doc: /* Normal hook run for clicks on menu bar, before displaying a submenu.
15788 Can be used to update submenus whose contents should vary. */);
15789 Vmenu_bar_update_hook = Qnil;
15791 DEFVAR_BOOL ("inhibit-menubar-update", &inhibit_menubar_update,
15792 doc: /* Non-nil means don't update menu bars. Internal use only. */);
15793 inhibit_menubar_update = 0;
15795 DEFVAR_BOOL ("inhibit-eval-during-redisplay", &inhibit_eval_during_redisplay,
15796 doc: /* Non-nil means don't eval Lisp during redisplay. */);
15797 inhibit_eval_during_redisplay = 0;
15799 DEFVAR_BOOL ("inhibit-free-realized-faces", &inhibit_free_realized_faces,
15800 doc: /* Non-nil means don't free realized faces. Internal use only. */);
15801 inhibit_free_realized_faces = 0;
15803 #if GLYPH_DEBUG
15804 DEFVAR_BOOL ("inhibit-try-window-id", &inhibit_try_window_id,
15805 doc: /* Inhibit try_window_id display optimization. */);
15806 inhibit_try_window_id = 0;
15808 DEFVAR_BOOL ("inhibit-try-window-reusing", &inhibit_try_window_reusing,
15809 doc: /* Inhibit try_window_reusing display optimization. */);
15810 inhibit_try_window_reusing = 0;
15812 DEFVAR_BOOL ("inhibit-try-cursor-movement", &inhibit_try_cursor_movement,
15813 doc: /* Inhibit try_cursor_movement display optimization. */);
15814 inhibit_try_cursor_movement = 0;
15815 #endif /* GLYPH_DEBUG */
15819 /* Initialize this module when Emacs starts. */
15821 void
15822 init_xdisp ()
15824 Lisp_Object root_window;
15825 struct window *mini_w;
15827 current_header_line_height = current_mode_line_height = -1;
15829 CHARPOS (this_line_start_pos) = 0;
15831 mini_w = XWINDOW (minibuf_window);
15832 root_window = FRAME_ROOT_WINDOW (XFRAME (WINDOW_FRAME (mini_w)));
15834 if (!noninteractive)
15836 struct frame *f = XFRAME (WINDOW_FRAME (XWINDOW (root_window)));
15837 int i;
15839 XWINDOW (root_window)->top = make_number (FRAME_TOP_MARGIN (f));
15840 set_window_height (root_window,
15841 FRAME_HEIGHT (f) - 1 - FRAME_TOP_MARGIN (f),
15843 mini_w->top = make_number (FRAME_HEIGHT (f) - 1);
15844 set_window_height (minibuf_window, 1, 0);
15846 XWINDOW (root_window)->width = make_number (FRAME_WIDTH (f));
15847 mini_w->width = make_number (FRAME_WIDTH (f));
15849 scratch_glyph_row.glyphs[TEXT_AREA] = scratch_glyphs;
15850 scratch_glyph_row.glyphs[TEXT_AREA + 1]
15851 = scratch_glyphs + MAX_SCRATCH_GLYPHS;
15853 /* The default ellipsis glyphs `...'. */
15854 for (i = 0; i < 3; ++i)
15855 default_invis_vector[i] = make_number ('.');
15859 /* Allocate the buffer for frame titles.
15860 Also used for `format-mode-line'. */
15861 int size = 100;
15862 frame_title_buf = (char *) xmalloc (size);
15863 frame_title_buf_end = frame_title_buf + size;
15864 frame_title_ptr = NULL;
15867 help_echo_showing_p = 0;