#include <config.h>
#include "lisp.h"
-#include <limits.h>
#include "buffer.h"
#include "commands.h"
#include "file-coding.h"
#endif
+#include "sysfile.h"
+
#ifdef HAVE_TTY
#include "console-tty.h"
-#ifdef HAVE_UNISTD_H
-#include <unistd.h> /* for isatty() */
-#endif
#endif /* HAVE_TTY */
/* Note: We have to be careful throughout this code to properly handle
#define LEFT_GLYPHS 2
#define RIGHT_GLYPHS 3
-/* Set the vertical clip to 0 if we are currently updating the line
- start cache. Otherwise for buffers of line height 1 it may fail to
- be able to work properly because regenerate_window will not layout
- a single line. */
#define VERTICAL_CLIP(w, display) \
- (updating_line_start_cache \
- ? 0 \
- : ((WINDOW_TTY_P (w) | (!display && scroll_on_clipped_lines)) \
+ ((WINDOW_TTY_P (w) | (!display && scroll_on_clipped_lines)) \
? INT_MAX \
- : vertical_clip))
+ : vertical_clip)
/* The following structures are completely private to redisplay.c so
we put them here instead of in a header file, for modularity. */
/* Minimum visible pixel width of clipped glyphs at right margin. */
int horizontal_clip;
-/* Set if currently inside update_line_start_cache. */
-static int updating_line_start_cache;
-
/* Nonzero means reading single-character input with prompt
so put cursor on minibuffer after the prompt. */
int cursor_in_echo_area;
Lisp_Object Vwindow_scroll_functions;
Lisp_Object Qredisplay_end_trigger_functions, Vredisplay_end_trigger_functions;
+Lisp_Object Qbuffer_list_changed_hook, Vbuffer_list_changed_hook;
+
+
#define INHIBIT_REDISPLAY_HOOKS /* #### Until we've thought about
this more. */
#ifndef INHIBIT_REDISPLAY_HOOKS
Lisp_Object Qtop_bottom;
-#define WINDOW_SCROLLED(w) \
-(w->hscroll > 0 || w->left_xoffset)
+#define WINDOW_SCROLLED(w) ((w)->hscroll > 0 || (w)->left_xoffset)
\f
/***************************************************************************/
/***************************************************************************/
static int
-redisplay_text_width_emchar_string (struct window *w, int findex,
- Emchar *str, Charcount len)
+redisplay_text_width_charc_string (struct window *w, int findex,
+ Charc *str, Charcount len)
{
- unsigned char charsets[NUM_LEADING_BYTES];
+ Charset_ID charsets[NUM_LEADING_BYTES];
Lisp_Object window;
- find_charsets_in_emchar_string (charsets, str, len);
+ find_charsets_in_charc_string (charsets, str, len);
XSETWINDOW (window, w);
ensure_face_cachel_complete (WINDOW_FACE_CACHEL (w, findex), window,
charsets);
WINDOW_FACE_CACHEL (w, findex), str, len));
}
-static Emchar_dynarr *rtw_emchar_dynarr;
+static Charc_dynarr *rtw_charc_dynarr;
int
redisplay_text_width_string (struct window *w, int findex,
Bufbyte *nonreloc, Lisp_Object reloc,
Bytecount offset, Bytecount len)
{
- if (!rtw_emchar_dynarr)
- rtw_emchar_dynarr = Dynarr_new (Emchar);
- Dynarr_reset (rtw_emchar_dynarr);
+ if (!rtw_charc_dynarr)
+ rtw_charc_dynarr = Dynarr_new (Charc);
+ Dynarr_reset (rtw_charc_dynarr);
fixup_internal_substring (nonreloc, reloc, offset, &len);
if (STRINGP (reloc))
nonreloc = XSTRING_DATA (reloc);
- convert_bufbyte_string_into_emchar_dynarr (nonreloc, len, rtw_emchar_dynarr);
- return redisplay_text_width_emchar_string
- (w, findex, Dynarr_atp (rtw_emchar_dynarr, 0),
- Dynarr_length (rtw_emchar_dynarr));
+ convert_bufbyte_string_into_charc_dynarr (nonreloc, len, rtw_charc_dynarr);
+ return redisplay_text_width_charc_string
+ (w, findex, Dynarr_atp (rtw_charc_dynarr, 0),
+ Dynarr_length (rtw_charc_dynarr));
}
int
Bufbyte *nonreloc, Lisp_Object reloc,
Bytecount offset, Bytecount len)
{
- unsigned char charsets[NUM_LEADING_BYTES];
+ Charset_ID charsets[NUM_LEADING_BYTES];
Lisp_Object frame;
struct face_cachel cachel;
- if (!rtw_emchar_dynarr)
- rtw_emchar_dynarr = Dynarr_new (Emchar);
- Dynarr_reset (rtw_emchar_dynarr);
+ if (!rtw_charc_dynarr)
+ rtw_charc_dynarr = Dynarr_new (Charc);
+ Dynarr_reset (rtw_charc_dynarr);
fixup_internal_substring (nonreloc, reloc, offset, &len);
if (STRINGP (reloc))
nonreloc = XSTRING_DATA (reloc);
- convert_bufbyte_string_into_emchar_dynarr (nonreloc, len, rtw_emchar_dynarr);
+ convert_bufbyte_string_into_charc_dynarr (nonreloc, len, rtw_charc_dynarr);
find_charsets_in_bufbyte_string (charsets, nonreloc, len);
reset_face_cachel (&cachel);
cachel.face = face;
XSETFRAME (frame, f);
ensure_face_cachel_complete (&cachel, frame, charsets);
return DEVMETH (XDEVICE (FRAME_DEVICE (f)),
- text_width, (f, &cachel, Dynarr_atp (rtw_emchar_dynarr, 0),
- Dynarr_length (rtw_emchar_dynarr)));
+ text_width, (f, &cachel, Dynarr_atp (rtw_charc_dynarr, 0),
+ Dynarr_length (rtw_charc_dynarr)));
}
/* Return the display block from DL of the given TYPE. A display line
gb.glyph = Vhscroll_glyph;
{
int oldpixpos = data->pixpos;
- retval = add_glyph_rune (data, &gb, BEGIN_GLYPHS, 1,
+ retval = add_glyph_rune (data, &gb, BEGIN_GLYPHS, 0,
GLYPH_CACHEL (XWINDOW (data->window),
HSCROLL_GLYPH_INDEX));
data->hscroll_glyph_width_adjust =
{
struct rune rb, *crb;
int width, local;
+ Charc char_glyph;
if (data->start_col)
{
if (data->ch == '\n')
{
+ char_glyph = ASCII_TO_CHARC ('\n');
data->font_is_bogus = 0;
/* Cheesy end-of-line pseudo-character. */
width = data->blank_width;
}
else
{
- Lisp_Object charset = CHAR_CHARSET (data->ch);
+ Lisp_Object charset;
+
+ char_glyph = CHAR_TO_CHARC (data->ch);
+ charset = CHARC_CHARSET (char_glyph);
if (!EQ (charset, data->last_charset) ||
data->findex != data->last_findex)
{
if (width < 0)
{
/* bummer. Proportional fonts. */
- width = redisplay_text_width_emchar_string (XWINDOW (data->window),
- data->findex,
- &data->ch, 1);
+ width = redisplay_text_width_charc_string (XWINDOW (data->window),
+ data->findex,
+ &char_glyph, 1);
}
}
data->bi_bufpos);
else
crb->bufpos =
- bytecount_to_charcount (XSTRING_DATA (data->string), data->bi_bufpos);
+ bytecount_to_charcount (XSTRING_DATA (data->string),
+ data->bi_bufpos);
}
else if (data->is_modeline)
crb->bufpos = data->modeline_charpos;
else
- /* fuckme if this shouldn't be an abort. */
- /* abort (); fuckme harder, this abort gets tripped quite often,
- in propagation and whatnot. #### fixme */
+ /* Text but not in buffer */
crb->bufpos = 0;
crb->type = RUNE_CHAR;
- crb->object.chr.ch = data->font_is_bogus ? '~' : data->ch;
+ crb->object.cglyph = data->font_is_bogus
+ ? ASCII_TO_CHARC ('~')
+ : char_glyph;
crb->endpos = 0;
if (data->cursor_type == CURSOR_ON)
case '%':
dst += set_charptr_emchar (dst, '%');
break;
+ /* #### unimplemented */
}
}
}
|| (pos_type == BEGIN_GLYPHS &&
extent_begin_glyph_layout (XEXTENT (gb->extent)) == GL_TEXT)
|| (pos_type == END_GLYPHS &&
- extent_end_glyph_layout (XEXTENT (gb->extent)) == GL_TEXT))
+ extent_end_glyph_layout (XEXTENT (gb->extent)) == GL_TEXT)
+ || pos_type == LEFT_GLYPHS || pos_type == RIGHT_GLYPHS)
{
struct rune rb;
int width;
int ascent, descent;
Lisp_Object baseline;
Lisp_Object face;
+ Lisp_Object instance;
+ face_index findex;
if (cachel)
width = cachel->width;
face = glyph_face (gb->glyph, data->window);
if (NILP (face))
- rb.findex = data->findex;
+ findex = data->findex;
else
- rb.findex = get_builtin_face_cache_index (w, face);
+ findex = get_builtin_face_cache_index (w, face);
+ instance = glyph_image_instance (gb->glyph, data->window,
+ ERROR_ME_NOT, 1);
+ if (TEXT_IMAGE_INSTANCEP (instance))
+ {
+ Lisp_Object string = XIMAGE_INSTANCE_TEXT_STRING (instance);
+ face_index orig_findex = data->findex;
+ Bytind orig_bufpos = data->bi_bufpos;
+ Bytind orig_start_col_enabled = data->bi_start_col_enabled;
+
+ data->findex = findex;
+ data->bi_start_col_enabled = 0;
+ if (!allow_cursor)
+ data->bi_bufpos = 0;
+ add_bufbyte_string_runes (data, XSTRING_DATA (string),
+ XSTRING_LENGTH (string), 0);
+ data->findex = orig_findex;
+ data->bi_bufpos = orig_bufpos;
+ data->bi_start_col_enabled = orig_start_col_enabled;
+ return NULL;
+ }
+
+ rb.findex = findex;
rb.xpos = data->pixpos;
rb.width = width;
rb.bufpos = 0; /* glyphs are never "at" anywhere */
else
rb.endpos = 0;
rb.type = RUNE_DGLYPH;
- /* #### Ben sez: this is way bogus if the glyph is a string.
- You should not make the output routines have to cope with
- this. The string could contain Mule characters, or non-
- printable characters, or characters to be passed through
- the display table, or non-character objects (when this gets
- implemented), etc. Instead, this routine here should parse
- the string into a series of runes. */
rb.object.dglyph.glyph = gb->glyph;
rb.object.dglyph.extent = gb->extent;
rb.object.dglyph.xoffset = xoffset;
dl->used_prop_data = 0;
dl->num_chars = 0;
+ dl->line_continuation = 0;
xzero (data);
data.ef = extent_fragment_new (w->buffer, f);
/* data.bi_bufpos is already at the start of the next line. */
+ dl->line_continuation = 1;
gb.glyph = Vcontinuation_glyph;
cachel = GLYPH_CACHEL (w, CONT_GLYPH_INDEX);
}
- add_glyph_rune (&data, &gb, BEGIN_GLYPHS, 1, cachel);
+ add_glyph_rune (&data, &gb, BEGIN_GLYPHS, 0, cachel);
if (truncate_win && data.bi_bufpos == BI_BUF_ZV (b)
&& BI_BUF_FETCH_CHAR (b, prev_bytind (b, BI_BUF_ZV (b))) != '\n')
{
struct rune *rb = Dynarr_atp (db->runes, elt);
- if ((rb->type == RUNE_CHAR && rb->object.chr.ch == ' ')
+ if ((rb->type == RUNE_CHAR && CHARC_ASCII_EQ (rb->object.cglyph, ' '))
|| rb->type == RUNE_BLANK)
{
dl->bounds.left_white += rb->width;
{
struct rune *rb = Dynarr_atp (db->runes, elt);
- if (!(rb->type == RUNE_CHAR && rb->object.chr.ch < 0x100
- && isspace (rb->object.chr.ch))
+ if (!(rb->type == RUNE_CHAR && CHARC_IS_SPACE (rb->object.cglyph))
&& !rb->type == RUNE_BLANK)
{
dl->bounds.right_white = rb->xpos + rb->width;
? dl->left_glyphs
: dl->right_glyphs);
int elt, end;
- int xpos = start;
int reverse;
+ struct window *w = XWINDOW (window);
+ struct frame *f = XFRAME (w->frame);
+ struct device *d = XDEVICE (f->device);
+ pos_data data;
+
+ xzero (data);
+ data.d = d;
+ data.window = window;
+ data.db = db;
+ data.dl = dl;
+ data.pixpos = start;
+ data.cursor_type = NO_CURSOR;
+ data.cursor_x = -1;
+ data.last_charset = Qunbound;
+ data.last_findex = DEFAULT_INDEX;
+ data.result_str = Qnil;
+ data.string = Qnil;
+ data.new_ascent = dl->ascent;
+ data.new_descent = dl->descent;
if ((layout == GL_WHITESPACE && side == LEFT_GLYPHS)
|| (layout == GL_INSIDE_MARGIN && side == RIGHT_GLYPHS))
|| (side == RIGHT_GLYPHS &&
extent_end_glyph_layout (XEXTENT (gb->extent)) == layout)))
{
- struct rune rb;
-
- rb.width = gb->width;
- rb.findex = gb->findex;
- rb.xpos = xpos;
- rb.bufpos = -1;
- rb.endpos = 0;
- rb.type = RUNE_DGLYPH;
- rb.object.dglyph.glyph = gb->glyph;
- rb.object.dglyph.extent = gb->extent;
- rb.object.dglyph.xoffset = 0;
- rb.cursor_type = CURSOR_OFF;
-
- Dynarr_add (db->runes, rb);
- xpos += rb.width;
+ data.findex = gb->findex;
+ data.max_pixpos = data.pixpos + gb->width;
+ add_glyph_rune (&data, gb, side, 0, NULL);
count--;
gb->active = 0;
-
- if (glyph_contrib_p (gb->glyph, window))
- {
- unsigned short ascent, descent;
- Lisp_Object baseline = glyph_baseline (gb->glyph, window);
-
- ascent = glyph_ascent (gb->glyph, window);
- descent = glyph_descent (gb->glyph, window);
-
- /* A pixmap that has not had a baseline explicitly set.
- We use the existing ascent / descent ratio of the
- line. */
- if (NILP (baseline))
- {
- int gheight = ascent + descent;
- int line_height = dl->ascent + dl->descent;
- int pix_ascent, pix_descent;
-
- pix_descent = (int) (gheight * dl->descent) / line_height;
- pix_ascent = gheight - pix_descent;
-
- dl->ascent = max ((int) dl->ascent, pix_ascent);
- dl->descent = max ((int) dl->descent, pix_descent);
- }
-
- /* A string so determine contribution normally. */
- else if (EQ (baseline, Qt))
- {
- dl->ascent = max (dl->ascent, ascent);
- dl->descent = max (dl->descent, descent);
- }
-
- /* A pixmap with an explicitly set baseline. We determine the
- contribution here. */
- else if (INTP (baseline))
- {
- int height = ascent + descent;
- int pix_ascent, pix_descent;
-
- pix_ascent = height * XINT (baseline) / 100;
- pix_descent = height - pix_ascent;
-
- dl->ascent = max ((int) dl->ascent, pix_ascent);
- dl->descent = max ((int) dl->descent, pix_descent);
- }
-
- /* Otherwise something is screwed up. */
- else
- abort ();
- }
}
(reverse ? elt-- : elt++);
}
- return xpos;
+ if (data.max_pixmap_height)
+ {
+ int height = data.new_ascent + data.new_descent;
+ int pix_ascent, pix_descent;
+
+ pix_descent = data.max_pixmap_height * data.new_descent / height;
+ pix_ascent = data.max_pixmap_height - pix_descent;
+ data.new_ascent = max (data.new_ascent, pix_ascent);
+ data.new_descent = max (data.new_descent, pix_descent);
+ }
+
+ dl->ascent = data.new_ascent;
+ dl->descent = data.new_descent;
+
+ return data.pixpos;
}
/* Add a blank to a margin display block. */
/* result_str is nil when we're building a frame or icon title. Otherwise,
we're building a modeline, so the offset starts at the modeline
- horizontal scrolling ammount */
+ horizontal scrolling amount */
if (! NILP (result_str))
offset = w->modeline_hscroll;
generate_fstring_runes (w, &data, 0, 0, -1, format_str, 0,
Bufbyte *strdata;
struct buffer *buf = XBUFFER (WINDOW_BUFFER (w));
+ in_modeline_generation = 1;
+
detach_all_extents (result_str);
resize_string (XSTRING (result_str), -1,
data.bytepos - XSTRING_LENGTH (result_str));
if (Dynarr_atp (db->runes, elt)->type == RUNE_CHAR)
{
len += (set_charptr_emchar
- (strdata + len, Dynarr_atp (db->runes,
- elt)->object.chr.ch));
+ (strdata + len,
+ CHARC_TO_CHAR (Dynarr_atp (db->runes,
+ elt)->object.cglyph)));
}
}
Dynarr_at (formatted_string_extent_end_dynarr, elt),
result_str);
}
+
+ in_modeline_generation = 0;
}
}
* - If first element is another symbol, process the cadr or caddr
* recursively according to whether the symbol's value is non-nil or
* nil.
- * - If first element is a face, process the cdr recursively
- * without altering the depth.
+ * - If first element is an extent, process the cdr recursively
+ * and handle the extent's face.
*/
Lisp_Object car, tem;
int truncate_win = b ? window_truncation_on (w) : 0;
int end_glyph_width = 0;
- /* we're going to ditch selective display for static text, its an
- FSF thing and invisble extents are the way to go
- here. Implementing it also relies on a number of buffer-specific
+ /* We're going to ditch selective display for static text, it's an
+ FSF thing and invisible extents are the way to go here.
+ Implementing it also relies on a number of buffer-specific
functions that we don't have the luxury of being able to use
here. */
dl->used_prop_data = 0;
dl->num_chars = 0;
+ dl->line_continuation = 0;
/* set up faces to use for clearing areas, used by
output_display_line */
/* data.bi_bufpos is already at the start of the next line. */
+ dl->line_continuation = 1;
gb.glyph = Vcontinuation_glyph;
cachel = GLYPH_CACHEL (w, CONT_GLYPH_INDEX);
}
{
struct rune *rb = Dynarr_atp (db->runes, elt);
- if ((rb->type == RUNE_CHAR && rb->object.chr.ch == ' ')
+ if ((rb->type == RUNE_CHAR && CHARC_ASCII_EQ (rb->object.cglyph, ' '))
|| rb->type == RUNE_BLANK)
{
dl->bounds.left_white += rb->width;
{
struct rune *rb = Dynarr_atp (db->runes, elt);
- if (!(rb->type == RUNE_CHAR && rb->object.chr.ch < 0x100
- && isspace (rb->object.chr.ch))
+ if (!(rb->type == RUNE_CHAR && CHARC_IS_SPACE (rb->object.cglyph))
&& !rb->type == RUNE_BLANK)
{
dl->bounds.right_white = rb->xpos + rb->width;
int ypos = WINDOW_TEXT_TOP (w);
int yend; /* set farther down */
int yclip = WINDOW_TEXT_TOP_CLIP (w);
+ int force;
prop_block_dynarr *prop;
layout_bounds bounds;
else
prop = 0;
+ /* When we are computing things for scrolling purposes, make
+ sure at least one line is always generated */
+ force = (type == CMOTION_DISP);
+
/* Make sure this is set always */
/* Note the conversion at end */
w->window_end_pos[type] = start_pos;
- while (ypos < yend)
+ while (ypos < yend || force)
{
struct display_line dl;
struct display_line *dlp;
the top clip and the bottom clip. */
visible_height -= (dlp->clip + dlp->top_clip);
- if (visible_height < VERTICAL_CLIP (w, 1))
+ if (visible_height < VERTICAL_CLIP (w, 1) && !force)
{
if (local)
free_display_line (dlp);
generate_display_line call. */
if (start_pos > BUF_ZV (b))
break;
+
+ force = 0;
}
if (prop)
assert (cdl->end_bufpos == ddl->end_bufpos);
assert (cdl->offset == ddl->offset);
- /* If the last rune is already a continuation glyph, fail.
- #### We should be able to handle this better. */
- {
- struct display_block *db = get_display_block_from_line (ddl, TEXT);
- if (Dynarr_length (db->runes))
- {
- struct rune *rb =
- Dynarr_atp (db->runes, Dynarr_length (db->runes) - 1);
-
- if (rb->type == RUNE_DGLYPH
- && EQ (rb->object.dglyph.glyph, Vcontinuation_glyph))
- return 0;
- }
- }
+ /* If the line continues to next display line, fail. */
+ if (ddl->line_continuation)
+ return 0;
/* If the line was generated using propagation data, fail. */
if (ddl->used_prop_data)
return 0;
}
- /* If the last rune is now a continuation glyph, fail. */
- {
- struct display_block *db = get_display_block_from_line (ddl, TEXT);
- if (Dynarr_length (db->runes))
- {
- struct rune *rb =
- Dynarr_atp (db->runes, Dynarr_length (db->runes) - 1);
-
- if (rb->type == RUNE_DGLYPH
- && EQ (rb->object.dglyph.glyph, Vcontinuation_glyph))
- return 0;
- }
- }
+ /* If the line continues to next display line, fail. */
+ if (ddl->line_continuation)
+ return 0;
/* If any line position parameters have changed or a
cursor has disappeared or disappeared, fail. */
&& !(MINI_WINDOW_P (w) && f->buffers_changed)
&& !f->frame_changed
&& !truncation_changed
- /* check whether start is really at the begining of a line GE */
+ /* check whether start is really at the beginning of a line GE */
&& (!w->start_at_line_beg || beginning_of_line_p (b, startp))
)
{
return 1;
}
+ if (!internal_equal (f->old_buffer_alist, f->buffer_alist, 0))
+ {
+ Lisp_Object frame;
+
+ f->old_buffer_alist = Freplace_list (f->old_buffer_alist,
+ f->buffer_alist);
+ XSETFRAME (frame, f);
+ va_run_hook_with_args (Qbuffer_list_changed_hook, 1, frame);
+ }
+
/* Before we put a hold on frame size changes, attempt to process
any which are already pending. */
if (f->size_change_pending)
if (f->clear)
f->frame_changed = 1;
- /* Invalidate the subwindow cache. We use subwindows_changed here to
- cause subwindows to get instantiated. This is because
+ /* Invalidate the subwindow caches. We use subwindows_changed here
+ to cause subwindows to get instantiated. This is because
subwindows_state_changed is less strict - dealing with things
like the clicked state of button. We have to do this before
redisplaying the gutters as subwindows get unmapped in the
process.*/
+ if (f->frame_changed)
+ reset_frame_subwindow_instance_cache (f);
+
if (f->frame_changed || f->subwindows_changed)
{
- reset_subwindow_cachels (f);
/* we have to do this so the gutter gets regenerated. */
reset_gutter_display_lines (f);
}
- else
- mark_subwindow_cachels_as_not_updated (f);
hold_frame_size_changes ();
#### If a frame-size change does occur we should probably
actually be preempting redisplay. */
+ MAYBE_DEVMETH (d, frame_output_begin, (f));
+
/* We can now update the gutters, safe in the knowledge that our
efforts won't get undone. */
/* Erase the frame before outputting its contents. */
if (f->clear)
{
- DEVMETH (d, clear_frame, (f));
+ MAYBE_DEVMETH (d, clear_frame, (f));
}
/* Do the selected window first. */
/* Then do the rest. */
redisplay_windows (f->root_window, 1);
- /* We now call the output_end routine for tty frames. We delay
- doing so in order to avoid cursor flicker. So much for 100%
- encapsulation. */
- if (FRAME_TTY_P (f))
- DEVMETH (d, output_end, (d));
+ MAYBE_DEVMETH (d, frame_output_end, (f));
update_frame_title (f);
displayed. The end of the last line is also know as the window end
position.
- WARNING: It is possible that rediplay failed to layout any lines for the
+ WARNING: It is possible that redisplay failed to layout any lines for the
windows. Under normal circumstances this is rare. However it seems that it
does occur in the following situation: A mouse event has come in and we
need to compute its location in a window. That code (in
validate_line_start_cache (w);
w->line_cache_validation_override++;
- updating_line_start_cache = 1;
if (from < BUF_BEGV (b))
from = BUF_BEGV (b);
if (from > to)
{
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
/* Check to see if the desired range is already in the cache. */
if (from >= low_bound && to <= high_bound)
{
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
update_internal_cache_list (w, DESIRED_DISP);
if (!Dynarr_length (internal_cache))
{
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
{
Dynarr_add_many (cache, Dynarr_atp (internal_cache, 0),
Dynarr_length (internal_cache));
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
the bounds of the DESIRED structs in the first place. */
if (start >= low_bound && end <= high_bound)
{
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
Dynarr_reset (cache);
Dynarr_add_many (cache, Dynarr_atp (internal_cache, 0),
Dynarr_length (internal_cache));
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
Dynarr_reset (cache);
Dynarr_add_many (cache, Dynarr_atp (internal_cache, 0),
Dynarr_length (internal_cache));
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
Dynarr_length (internal_cache) - ic_elt);
}
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
update_internal_cache_list (w, CMOTION_DISP);
/* If this assert is triggered then regenerate_window failed
- to layout a single line. That is not supposed to be
- possible because we impose a minimum height on the buffer
- and override vertical clip when we are in here. */
- /* #### Ah, but it is because the window may temporarily
- exist but not have any lines at all if the minibuffer is
- real big. Look into that situation better. */
- if (!Dynarr_length (internal_cache))
- {
- if (old_lb == -1 && low_bound == -1)
- {
- updating_line_start_cache = 0;
- w->line_cache_validation_override--;
- return;
- }
-
- assert (Dynarr_length (internal_cache));
- }
+ to layout a single line. This is not possible since we
+ force at least a single line to be layout for CMOTION_DISP */
+ assert (Dynarr_length (internal_cache));
assert (startp == Dynarr_atp (internal_cache, 0)->start);
ic_elt = Dynarr_length (internal_cache) - 1;
startp = new_startp;
if (startp > BUF_ZV (b))
{
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
return;
}
while (to > high_bound);
}
- updating_line_start_cache = 0;
w->line_cache_validation_override--;
assert (to <= high_bound);
}
}
else if (past_end
|| (rb->type == RUNE_CHAR
- && rb->object.chr.ch == '\n'))
+ && CHARC_ASCII_EQ (rb->object.cglyph, '\n')))
{
(*row)--;
/* At this point we may have glyphs in the right
if (FRAME_REPAINT_P (f) && FRAME_HAS_MINIBUF_P (f))
{
Lisp_Object window = FRAME_MINIBUF_WINDOW (f);
+
+ MAYBE_DEVMETH (d, frame_output_begin, (f));
+
/*
* If the frame size has changed, there may be random
* chud on the screen left from previous messages
*/
if (f->echo_area_garbaged)
{
- DEVMETH (d, clear_frame, (f));
+ MAYBE_DEVMETH (d, clear_frame, (f));
f->echo_area_garbaged = 0;
}
redisplay_window (window, 0);
+ MAYBE_DEVMETH (d, frame_output_end, (f));
+
call_redisplay_end_triggers (XWINDOW (window), 0);
}
}
-
- /* We now call the output_end routine for tty frames. We delay
- doing so in order to avoid cursor flicker. So much for 100%
- encapsulation. */
- if (DEVICE_TTY_P (d))
- DEVMETH (d, output_end, (d));
}
return Qnil;
redisplay_frame (f, 1);
- /* If we don't reset the global redisplay flafs here, subsequent
+ /* If we don't reset the global redisplay flags here, subsequent
changes to the display will not get registered by redisplay
because it thinks it already has registered changes. If you
really knew what you were doing you could confuse redisplay by
defsymbol (&Qredisplay_end_trigger_functions,
"redisplay-end-trigger-functions");
defsymbol (&Qtop_bottom, "top-bottom");
+ defsymbol (&Qbuffer_list_changed_hook, "buffer-list-changed-hook");
DEFSUBR (Fredisplay_echo_area);
DEFSUBR (Fredraw_frame);
}
void
-reinit_vars_of_redisplay (void)
-{
- updating_line_start_cache = 0;
-}
-
-void
vars_of_redisplay (void)
{
- reinit_vars_of_redisplay ();
#if 0
staticpro (&last_arrow_position);
Voverlay_arrow_position = Qnil;
DEFVAR_LISP_MAGIC ("overlay-arrow-string", &Voverlay_arrow_string /*
-String to display as an arrow. See also `overlay-arrow-position'.
+String or glyph to display as an arrow. See also `overlay-arrow-position'.
+\(Note that despite the name of this variable, it can be set to a glyph as
+well as a string.)
*/ ,
redisplay_variable_changed);
Voverlay_arrow_string = Qnil;
#ifndef INHIBIT_REDISPLAY_HOOKS
xxDEFVAR_LISP ("pre-redisplay-hook", &Vpre_redisplay_hook /*
Function or functions to run before every redisplay.
-Functions on this hook must be careful to avoid signalling errors!
*/ );
Vpre_redisplay_hook = Qnil;
xxDEFVAR_LISP ("post-redisplay-hook", &Vpost_redisplay_hook /*
Function or functions to run after every redisplay.
-Functions on this hook must be careful to avoid signalling errors!
*/ );
Vpost_redisplay_hook = Qnil;
#endif /* INHIBIT_REDISPLAY_HOOKS */
+ DEFVAR_LISP ("buffer-list-changed-hook", &Vbuffer_list_changed_hook /*
+Function or functions to call when a frame's buffer list has changed.
+This is called during redisplay, before redisplaying each frame.
+Functions on this hook are called with one argument, the frame.
+*/ );
+ Vbuffer_list_changed_hook = Qnil;
+
DEFVAR_INT ("display-warning-tick", &display_warning_tick /*
Bump this to tell the C code to call `display-warning-buffer'
at next redisplay. You should not normally change this; the function
offsetof (struct window, left_margin_width),
some_window_value_changed,
offsetof (struct frame, left_margin_width),
- margin_width_changed_in_frame);
+ margin_width_changed_in_frame, 0);
DEFVAR_SPECIFIER ("right-margin-width", &Vright_margin_width /*
*Width of right margin.
offsetof (struct window, right_margin_width),
some_window_value_changed,
offsetof (struct frame, right_margin_width),
- margin_width_changed_in_frame);
+ margin_width_changed_in_frame, 0);
DEFVAR_SPECIFIER ("minimum-line-ascent", &Vminimum_line_ascent /*
*Minimum ascent height of lines.
set_specifier_caching (Vminimum_line_ascent,
offsetof (struct window, minimum_line_ascent),
some_window_value_changed,
- 0, 0);
+ 0, 0, 0);
DEFVAR_SPECIFIER ("minimum-line-descent", &Vminimum_line_descent /*
*Minimum descent height of lines.
set_specifier_caching (Vminimum_line_descent,
offsetof (struct window, minimum_line_descent),
some_window_value_changed,
- 0, 0);
+ 0, 0, 0);
DEFVAR_SPECIFIER ("use-left-overflow", &Vuse_left_overflow /*
*Non-nil means use the left outside margin as extra whitespace when
set_specifier_caching (Vuse_left_overflow,
offsetof (struct window, use_left_overflow),
some_window_value_changed,
- 0, 0);
+ 0, 0, 0);
DEFVAR_SPECIFIER ("use-right-overflow", &Vuse_right_overflow /*
*Non-nil means use the right outside margin as extra whitespace when
set_specifier_caching (Vuse_right_overflow,
offsetof (struct window, use_right_overflow),
some_window_value_changed,
- 0, 0);
+ 0, 0, 0);
DEFVAR_SPECIFIER ("text-cursor-visible-p", &Vtext_cursor_visible_p /*
*Non-nil means the text cursor is visible (this is usually the case).
set_specifier_caching (Vtext_cursor_visible_p,
offsetof (struct window, text_cursor_visible_p),
text_cursor_visible_p_changed,
- 0, 0);
+ 0, 0, 0);
}