emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] scratch/large-fonts 1d87cb3: Avoid very high screen lines


From: Eli Zaretskii
Subject: [Emacs-diffs] scratch/large-fonts 1d87cb3: Avoid very high screen lines with some fonts
Date: Wed, 27 May 2015 15:04:00 +0000

branch: scratch/large-fonts
commit 1d87cb3cfa08086be96f78ab09d99f3e7ba8ca60
Author: Eli Zaretskii <address@hidden>
Commit: Eli Zaretskii <address@hidden>

    Avoid very high screen lines with some fonts
    
    * src/xdisp.c (get_phys_cursor_geometry): Adjust the height of the
    cursor to avoid weird-looking hollow cursor with fonts that have
    large ascent values for some glyphs.  This avoids having the
    hollow cursor start too low.
    (append_space_for_newline): Adjust the ascent value of the newline
    glyph, so that the hollow cursor at end of line displays
    correctly.
    (FONT_TOO_HIGH): New macro.
    (x_produce_glyphs): Use it to detect fonts that claim a
    preposterously large height, in which case we use per-glyph ascent
    and descent values.  (Bug#20628)
---
 src/xdisp.c |   92 +++++++++++++++++++++++++++++++++++++++++++++++++++++-----
 1 files changed, 84 insertions(+), 8 deletions(-)

diff --git a/src/xdisp.c b/src/xdisp.c
index 87f110e..a1b7cf1 100644
--- a/src/xdisp.c
+++ b/src/xdisp.c
@@ -2150,7 +2150,7 @@ get_phys_cursor_geometry (struct window *w, struct 
glyph_row *row,
                          struct glyph *glyph, int *xp, int *yp, int *heightp)
 {
   struct frame *f = XFRAME (WINDOW_FRAME (w));
-  int x, y, wd, h, h0, y0;
+  int x, y, wd, h, h0, y0, ascent;
 
   /* Compute the width of the rectangle to draw.  If on a stretch
      glyph, and `x-stretch-block-cursor' is nil, don't draw a
@@ -2170,13 +2170,21 @@ get_phys_cursor_geometry (struct window *w, struct 
glyph_row *row,
     wd = min (FRAME_COLUMN_WIDTH (f), wd);
   w->phys_cursor_width = wd;
 
-  y = w->phys_cursor.y + row->ascent - glyph->ascent;
+  /* Don't let the hollow cursor glyph descend below the glyph row's
+     ascent value, lest the hollow cursor looks funny.  */
+  y = w->phys_cursor.y;
+  ascent = row->ascent;
+  if (row->ascent < glyph->ascent)
+    {
+      y =- glyph->ascent - row->ascent;
+      ascent = glyph->ascent;
+    }
 
   /* If y is below window bottom, ensure that we still see a cursor.  */
   h0 = min (FRAME_LINE_HEIGHT (f), row->visible_height);
 
-  h = max (h0, glyph->ascent + glyph->descent);
-  h0 = min (h0, glyph->ascent + glyph->descent);
+  h = max (h0, ascent + glyph->descent);
+  h0 = min (h0, ascent + glyph->descent);
 
   y0 = WINDOW_HEADER_LINE_HEIGHT (w);
   if (y < y0)
@@ -19171,6 +19179,7 @@ append_space_for_newline (struct it *it, bool 
default_face_p)
          struct text_pos saved_pos;
          Lisp_Object saved_object;
          struct face *face;
+         struct glyph *g;
 
          saved_object = it->object;
          saved_pos = it->position;
@@ -19202,6 +19211,11 @@ append_space_for_newline (struct it *it, bool 
default_face_p)
 
          PRODUCE_GLYPHS (it);
 
+         /* Make sure this space glyph has the right ascent value, or
+            else hollow cursor at end of line will look funny.  */
+         g = it->glyph_row->glyphs[TEXT_AREA] + n;
+         g->ascent = it->glyph_row->ascent;
+
          it->override_ascent = -1;
          it->constrain_row_ascent_descent_p = false;
          it->current_x = saved_x;
@@ -25282,6 +25296,12 @@ draw_glyphs (struct window *w, int x, struct glyph_row 
*row,
       }                                                        \
   }
 
+/* A heuristic test for fonts that claim they need a preposterously
+   large vertical space.  The heuristics is in the factor of 3.  We
+   ignore the ascent and descent values reported by such fonts, and
+   instead go by the values reported for individual glyphs.  */
+#define FONT_TOO_HIGH(ft)  ((ft)->ascent + (ft)->descent > 3*(ft)->pixel_size)
+
 /* Store one glyph for IT->char_to_display in IT->glyph_row.
    Called from x_produce_glyphs when IT->glyph_row is non-null.  */
 
@@ -26398,6 +26418,22 @@ x_produce_glyphs (struct it *it)
              it->phys_ascent = pcm->ascent + boff;
              it->phys_descent = pcm->descent - boff;
              it->pixel_width = pcm->width;
+             /* Don't use font-global values for ascent and descent
+                if they result in an exceedingly large line height.  */
+             if (it->override_ascent < 0)
+               {
+                 if (FONT_TOO_HIGH (font))
+                   {
+                     it->ascent = it->phys_ascent;
+                     it->descent = it->phys_descent;
+                     /* These limitations are enforced by an
+                        assertion near the end of this function.  */
+                     if (it->ascent < 0)
+                       it->ascent = 0;
+                     if (it->descent < 0)
+                       it->descent = 0;
+                   }
+               }
            }
          else
            {
@@ -26525,8 +26561,18 @@ x_produce_glyphs (struct it *it)
            }
          else
            {
-             it->ascent = FONT_BASE (font) + boff;
-             it->descent = FONT_DESCENT (font) - boff;
+             if (FONT_TOO_HIGH (font))
+               {
+                 it->ascent = font->pixel_size + boff - 1;
+                 it->descent = -boff + 1;
+                 if (it->descent < 0)
+                   it->descent = 0;
+               }
+             else
+               {
+                 it->ascent = FONT_BASE (font) + boff;
+                 it->descent = FONT_DESCENT (font) - boff;
+               }
            }
 
          if (EQ (height, Qt))
@@ -26597,8 +26643,38 @@ x_produce_glyphs (struct it *it)
 
              it->pixel_width = next_tab_x - x;
              it->nglyphs = 1;
-             it->ascent = it->phys_ascent = FONT_BASE (font) + boff;
-             it->descent = it->phys_descent = FONT_DESCENT (font) - boff;
+             if (FONT_TOO_HIGH (font))
+               {
+                 if (get_char_glyph_code (' ', font, &char2b))
+                   {
+                     pcm = get_per_char_metric (font, &char2b);
+                     if (pcm->width == 0
+                         && pcm->rbearing == 0 && pcm->lbearing == 0)
+                       pcm = NULL;
+                   }
+
+                 if (pcm)
+                   {
+                     it->ascent = pcm->ascent + boff;
+                     it->descent = pcm->descent - boff;
+                   }
+                 else
+                   {
+                     it->ascent = font->pixel_size + boff - 1;
+                     it->descent = -boff + 1;
+                   }
+                 if (it->ascent < 0)
+                   it->ascent = 0;
+                 if (it->descent < 0)
+                   it->descent = 0;
+               }
+             else
+               {
+                 it->ascent = FONT_BASE (font) + boff;
+                 it->descent = FONT_DESCENT (font) - boff;
+               }
+             it->phys_ascent = it->ascent;
+             it->phys_descent = it->descent;
 
              if (it->glyph_row)
                {



reply via email to

[Prev in Thread] Current Thread [Next in Thread]