On 19 May 2002, Stephen J. Turnbull said:
>>>>> "nix" == nix
<nix(a)esperi.demon.co.uk> writes:
nix> It's not a small bug fix, but compared to e.g. the syntax
nix> table changes (also bugfixes) it's a tiddler.
Ben's changes won't go in to 21.4 on my watch. I know I have no hope
of understanding that monster. What we're testing here is whether it
makes sense for me to try to understand your patch.
It isn't complex; the one bit that might be called slightly complex has
a huge comment above it to explain WTF it's doing.
It just arranges to track the baseline on a per-rune basis (which you
need to do if each rune is to have its own baseline, as we promised) and
keeps the baseline of the whole line up to date from the per-rune
baseline values.
I'll delineate it insanely verbosely for you on the off-chance that
helps (love the sound of my own voice? Never!):
Tracking the baseline is the most complex bit. We keep `ascent',
`descent' and `yoffset' in the rune to independently track all these
parameters. (We only need at most two of them at any one time, but the
inefficiency won't kill us.) We also remember if anyone explicitly set
the baseline on each rune: if nobody bothered, we don't do anything very
special and all this code reduces to almost nothing.
add_glyph_rune() is modified to remember the ascent and descent of each
rune, and keep track of the maximum height, maximum ascent and maximum
descent of any glyph on the line: this is because if the line is tall, a
short glyph won't affect the baseline of the line as a whole (the
line'll just move up or down on it).
create_text_block() and all the other functions where we used to
compute the baseline get that repeated code torn out, and instead
we call two functions.
The first one (calculate_baseline()) is the one with the big comment
above it, and is the most complicated change: it works out what the
baseline for the line as a whole should be given the linewide maximum
ascent and descent, the baseline of the default face and other
things. The comment explains it more clearly than I can here. :) Most of
this code is generalizations of code that was being run by one or
another of the routines elsewhere in redisplay (and has been removed
from them and moved here).
When this function returns, the line's new_ascent/new_descent are
known. The caller then uses these to work out the line's actual ascent
and descent in just the same way they always did (it differs for
different callers), and then they call calculate_yoffset().
calculate_yoffset() takes the ascent of the line and the ascent and
descent of each glyph rune on the line, and sets up that rune's yoffset
field: that being the amount by which the rune must be shifted down from
the topmost point the display_line is plotted at (`upper baseline'?) to
appear at the right position, given its ascent and descent, and the
ascent of the line (which the caller has turned the line's baseline
into). This is what XEmacs used to use as a `baseline' (even though it's
almost exactly the opposite). Non-glyph runes always have a zero
yoffset, which means `use the pre-existing line-wide ascent as usual'.
The net effect of all this is that the glyphs or bits of text that stick
up or down furthest on the line control the baseline of the line, while
the glyphs themselves are correctly positioned with respect to this
baseline.
The changes to redisplay-{output,msw,gtk,x}.c are all parameter changes
to pass the yoffset to the routines that do the display, and a tiny
calculation change in redisplay-output.c:redisplay_calculate_display_boxes()
to actually use the yoffset value, instead of the value it used to use;
these changes are mostly mechanical and boring.
(There's also a small change in
redisplay-output.c:redisplay_normalize_glyph_area(), which through
oversight hasn't been added to the changelog: it arranges that if a
partial-line scroll is in place and a glyph has been ascented up so it's
now completely invisible on a line that is still otherwise visible, the
glyph's height stays at something sane, rather than wrapping to a huge
positive value and mushing up the screen.)
A suitable changelog line for this would be
* redisplay-output.c (redisplay_normalize_glyph_area): Cater for
that glyphs that are pushed above the top of the visible area
on still-visible lines.
(Oops. Everything else is described in the changelog, I just checked.)
Hm. That's still not very clear, but I hope this rephrasing makes it a
bit clearer than it was. I tried to explain it in the original patch
postings, too: if you read all of these together then some sense might
emerge:)
Thanks for considering this at this late stage.
nix> As a heavy user of auto-revert-buffer with huge files on
slow
nix> machines with data coming from *dog* slow NFS servers, I
nix> applaud.
Yeah, well, there's already a bug report in, against 21.4.7 Windows
[1] which is the same code I put in. :-(
Damn:( still, until you've seen an NFS server with an effective file
transmission rate of 10K/s you haven't seen slow. Anything that
reduces file access from a box like that is good. :)
--
`There are not words enough to describe how fucked up imake is.'
--- Peter da Silva