From: Alan Mackenzie <acm@muc.de>
To: Eli Zaretskii <eliz@gnu.org>
Cc: emacs-devel@gnu.org
Subject: Re: Aborting display. Is this possible?
Date: Mon, 20 Oct 2014 18:57:57 +0000 [thread overview]
Message-ID: <20141020185757.GD2947@acm.acm> (raw)
In-Reply-To: <8338aidbcq.fsf@gnu.org>
Hello, Eli.
On Mon, Oct 20, 2014 at 06:12:05PM +0300, Eli Zaretskii wrote:
> > Date: Mon, 20 Oct 2014 11:09:49 +0000
> > Cc: emacs-devel@gnu.org
> > From: Alan Mackenzie <acm@muc.de
> > On a large C Mode buffer (such as xdisp.c), hold down the PageDown key
> > for, say, 10 seconds.
> > What is seen: The screen freezes. After releasing the key, it takes many
> > seconds (~10) before the current buffer position is displayed on the
> > screen.
Incidentally, I saw this happening today in emacs-lisp-mode, on my
terminal with a 3 column follow-mode.
> > What I'd like to see: The screen continuously updating with (not
> > necessarily contiguous) parts of the buffer, the updating being frequent
> > enough to give the illusion of continuous scrolling. On releasing the
> > key, the screen "instantly" displaying the new buffer position.
> I understand the desire, and I'm not saying it isn't reasonable. So
> please don't take what's below as a rebuttal; I'm just trying to
> explain how the current Emacs design works against your wishes, and
> what could/should be changed for your wishes to maybe become reality.
> I will probably say some (or many) things that you already know, so
> please bear with me.
Thanks for such a clear exposition.
> First, Emacs's basic design is that it processes all the available
> input before it enters redisplay. As long as there's input in the
> input queue, Emacs will not call redisplay. (There are 2 exceptions
> to this rule: processing input could indirectly call the 'redisplay'
> function; and messages in the echo area produced while processing
> input require a kind of "partial" redisplay to show the echo area.)
> Why? because processing input allows to avoid showing the user a
> screen that is outdated from the user's POV, given that input more
> often than not changes what should be displayed.
Up to now, I think I've been confusing display with font-locking.
Obviously f-l has to happen when d is being done, but not all
font-locking is caused by display.
> Another part of this puzzle is that redisplay includes fontification
> of the visible portion of the buffer. Emacs applies the font-lock
> faces (and any other faces) during the 1st stage of its redisplay
> cycle, when it computes the so-called "glyph matrices", which are data
> structures maintained for each window that describe what the updated
> screen should look like. As David points out, it is impossible to
> compute the glyph matrices without applying the faces, because faces
> change the metrics of each character, and thus affect the layout,
> which is what glyph matrices are all about.
> The final part of the puzzle is what the scroll-up-command does when
> Emacs processes a single PageDown keypress. It computes the new
> starting point for the window, which (if we neglect complications) is
> simply the beginning of line N screen lines below the original window
> start, where N is almost the height of the window. (Note that I wrote
> "screen lines", not "physical lines", so this is not entirely trivial
> when there are continuation lines and variable-size fonts.) Then it
> determines whether this change of the window-start requires to move
> point to bring it into the view, and if so, moves point as well.
On a PageDown, Emacs needs to do font-locking just to work out how far
awy the next page is, like David said. There is a comment in
window_scroll_line_based: "Fvertical_motion enters redisplay, which can
trigger fontification...". This is the killer: scrolling a screen of
xdisp.c is taking, on average, ~0.09s, the bulk of this time being
fontification, whereas the key events are coming in every ~0.03s.
Some way has to be found to scroll with only every third screen (at most)
getting font-locked.
If every glyph were assumed to be the same size, the calculation of the
window-start position for the current scroll operation would be _much_
faster: display would still have to account for text lines overflowing
screen lines, and invisible text, and so on,
So, how about the following strategy: when the (new) variable
`face-instead-of-fontifying' is bound to a face, AND the input queue is
non-empty (or, perhaps, very non-empty), the appropriate subroutine of
window-scroll should deem characters without a `face' (or `fontified' ?)
property to have face `face-instead-of-fontifying'.
This should empty the input queue pretty quickly, enabling a current
buffer portion to get displayed frequently enough.
> So, after processing a single PageDown key, the window has a new
> starting point, and point in that window's buffer has been moved.
> If, after processing this single PageDown key, the input queue is
> empty (as it is when you lean on the key, because Emacs finishes the
> above processing in less time than the auto-repeat interval), Emacs
> enters redisplay. Redisplay computes the glyph matrix of the window
> given its start point as set by scroll-up-command; as part of this
> matrix computation, the display engine applies all the font-lock
> properties to the text, and sets the 'fontified' property on that
> text. Then, just before it is about to redraw the window given the
> new glyph matrix, it checks for input. If there's input available,
> and redisplay-dont-pause is nil, the window will not be redrawn,
> i.e. this redisplay cycle will be aborted.
But in the default situation (redisplay-dont-pause is non-nil), once the
calculation of the glyph matrix has begun, the redrawing necessarily
takes place. This is good. :-)
> Then the same will happen again for the next PageDown key. The result
> is a frozen window display, because all the attempts to redisplay are
> aborted due to input rate that is high enough to preempt redisplay,
> but not high enough to prevent Emacs from entering redisplay after
> every (or almost every) PageDown key. To see more frequent updates
> that give an illusion of scrolling, we would need a feature that
> ignores the input availability, or maybe dynamically changes the
> number of input events that could be ignored when redisplay falls
> behind. We don't have such a feature.
Is this really the case? Is it not that the font-locking caused by
scrolling is slow enough, that the input queue is never empty, hence
redisplay doesn't get a look in?
> Now, what happens when you release the key? The input queue is still
> full of unprocessed PageDown keys. As I explained above, Emacs will
> drain the entire input queue before it enters redisplay; thus the long
> delay you see after releasing the key.
And each such PageDown key will necessitate full font-locking for its
never-to-be-displayed screen.
> You want Emacs to "immediately" display the new buffer position, but
> this is impossible without some code that would quickly scan the input
> queue, analyze what's there, and "understand" that 100 PageDown
> keystrokes can be "optimized" by executing a single scroll-up-command
> with a suitable argument. IOW, we would need some input preprocessing
> stage that could "optimize" input by replacing a series of commands
> with a single command, and do that cheaply. We don't have such a
> feature; patches to add it will probably be welcome.
:-). If my analysis is right, this wouldn't help. A single mega-scroll
would still be font-locking the entire intermediate buffer region.
--
Alan Mackenzie (Nuremberg, Germany).
next prev parent reply other threads:[~2014-10-20 18:57 UTC|newest]
Thread overview: 82+ messages / expand[flat|nested] mbox.gz Atom feed top
2014-10-19 14:17 Aborting display. Is this possible? Alan Mackenzie
2014-10-19 14:32 ` David Kastrup
2014-10-19 14:54 ` Eli Zaretskii
2014-10-19 14:50 ` Eli Zaretskii
2014-10-19 15:42 ` Alan Mackenzie
2014-10-19 18:09 ` Eli Zaretskii
2014-10-20 11:09 ` Alan Mackenzie
2014-10-20 11:30 ` David Kastrup
2014-10-20 12:00 ` Alan Mackenzie
2014-10-20 15:15 ` Eli Zaretskii
2014-10-20 15:12 ` Eli Zaretskii
2014-10-20 16:56 ` Stefan Monnier
2014-10-20 17:10 ` Eli Zaretskii
2014-10-20 17:40 ` Eli Zaretskii
2014-10-20 18:57 ` Alan Mackenzie [this message]
2014-10-20 19:24 ` Eli Zaretskii
2014-10-20 21:08 ` Alan Mackenzie
2014-10-21 8:09 ` David Kastrup
2014-10-21 10:58 ` Alan Mackenzie
2014-10-21 11:04 ` David Kastrup
2014-10-21 14:25 ` Stefan Monnier
2014-10-21 14:01 ` Stefan Monnier
2014-10-21 15:35 ` Eli Zaretskii
2014-10-21 16:27 ` Stefan Monnier
2014-10-22 18:28 ` Stephen Leake
2014-10-22 20:10 ` Stefan Monnier
2014-10-21 17:14 ` Alan Mackenzie
2014-10-21 18:00 ` Eli Zaretskii
2014-10-21 18:38 ` Alan Mackenzie
2014-10-21 18:43 ` Eli Zaretskii
2014-10-21 19:42 ` Eli Zaretskii
2014-10-26 12:43 ` Unfreezing the display during auto-repeated scrolling. [ Was: Aborting display. Is this possible? ] Alan Mackenzie
2014-10-26 16:45 ` Eli Zaretskii
2014-10-26 20:03 ` Alan Mackenzie
2014-10-26 20:20 ` Eli Zaretskii
2014-10-26 20:42 ` Stefan Monnier
2014-10-26 22:15 ` Unfreezing the display during auto-repeated scrolling Alan Mackenzie
2014-10-27 1:03 ` Stefan Monnier
2014-10-27 14:28 ` Unfreezing the display during auto-repeated scrolling. Simpler approach Alan Mackenzie
2014-10-27 16:51 ` Eli Zaretskii
2014-10-27 19:13 ` David Engster
2014-10-27 19:26 ` Eli Zaretskii
2014-10-27 19:36 ` David Engster
2014-10-27 19:38 ` Alan Mackenzie
2014-10-27 21:38 ` Stefan Monnier
2014-10-28 18:10 ` Alan Mackenzie
2014-10-29 0:57 ` Stefan Monnier
2014-10-29 14:14 ` Eli Zaretskii
2014-10-29 14:52 ` Alan Mackenzie
2014-10-29 15:37 ` Eli Zaretskii
2014-10-29 16:59 ` Stefan Monnier
2014-10-29 21:25 ` Alan Mackenzie
2014-10-30 1:49 ` Stefan Monnier
2014-10-30 22:09 ` Alan Mackenzie
2014-10-31 3:06 ` Stefan Monnier
2014-10-31 7:55 ` Eli Zaretskii
2014-10-31 14:04 ` Stefan Monnier
2014-11-21 15:44 ` Alan Mackenzie
2014-11-23 9:51 ` Tassilo Horn
2014-11-23 10:40 ` Alan Mackenzie
2014-11-23 19:44 ` Tassilo Horn
2014-11-23 22:04 ` Alan Mackenzie
2014-11-24 11:34 ` Tassilo Horn
2014-11-24 11:53 ` David Kastrup
2014-11-24 16:00 ` Alan Mackenzie
2014-11-24 14:37 ` Stefan Monnier
2014-11-24 16:08 ` Alan Mackenzie
2014-11-24 17:44 ` Stefan Monnier
2014-10-27 3:36 ` Unfreezing the display during auto-repeated scrolling Eli Zaretskii
2014-10-27 10:05 ` Alan Mackenzie
2014-10-27 16:48 ` Eli Zaretskii
2014-10-27 22:46 ` Alan Mackenzie
2014-10-28 0:22 ` Stefan Monnier
2014-10-27 3:33 ` Unfreezing the display during auto-repeated scrolling. [ Was: Aborting display. Is this possible? ] Eli Zaretskii
2014-10-21 18:01 ` Aborting display. Is this possible? Stefan Monnier
2014-10-21 15:40 ` Eli Zaretskii
2014-10-21 17:00 ` Michael Welsh Duggan
2014-10-21 18:25 ` Alan Mackenzie
2014-10-20 1:59 ` Stefan Monnier
2014-10-20 2:45 ` Eli Zaretskii
-- strict thread matches above, loose matches on Subject: below --
2014-10-20 17:18 grischka
2014-10-20 17:23 ` Eli Zaretskii
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.gnu.org/software/emacs/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20141020185757.GD2947@acm.acm \
--to=acm@muc.de \
--cc=eliz@gnu.org \
--cc=emacs-devel@gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).