]> git.eshelyaron.com Git - emacs.git/commitdiff
Fix bug #14476 with posn-at-point and glyphs from display vector.
authorEli Zaretskii <eliz@gnu.org>
Mon, 27 May 2013 16:54:33 +0000 (19:54 +0300)
committerEli Zaretskii <eliz@gnu.org>
Mon, 27 May 2013 16:54:33 +0000 (19:54 +0300)
 src/xdisp.c (pos_visible_p): When CHARPOS is displayed frrom a
 display vector, and we backtrack, handle the case that the
 previous character position is also displayed from a display
 vector or covered by a display string or image.

src/ChangeLog
src/xdisp.c

index 5bcdb7ed068de1c573c622da064d02b8f4ec935d..b1f13e62b4061c3b7d72b9f890db087f456c558e 100644 (file)
@@ -1,3 +1,10 @@
+2013-05-27  Eli Zaretskii  <eliz@gnu.org>
+
+       * xdisp.c (pos_visible_p): When CHARPOS is displayed frrom a
+       display vector, and we backtrack, handle the case that the
+       previous character position is also displayed from a display
+       vector or covered by a display string or image.  (Bug#14476)
+
 2013-05-25  Jan Djärv  <jan.h.d@swipnet.se>
 
        * xfns.c (Qgeometry, Qworkarea, Qmm_size, Qframes, Qsource): Remove.
index 5e92f3643c07eedc1e3f252d5726be353026cdc0..9f3be44ecfdae30fa99d86a6ab68e8cfacc471dc 100644 (file)
@@ -1371,18 +1371,41 @@ pos_visible_p (struct window *w, ptrdiff_t charpos, int *x, int *y,
                top_x = it.glyph_row->x;
              else
                {
-                 struct it it2;
+                 struct it it2, it2_prev;
+                 /* The idea is to get to the previous buffer
+                    position, consume the character there, and use
+                    the pixel coordinates we get after that.  But if
+                    the previous buffer position is also displayed
+                    from a display vector, we need to consume all of
+                    the glyphs from that display vector.  */
                  start_display (&it2, w, top);
                  move_it_to (&it2, charpos - 1, -1, -1, -1, MOVE_TO_POS);
-                 get_next_display_element (&it2);
-                 PRODUCE_GLYPHS (&it2);
-                 if (ITERATOR_AT_END_OF_LINE_P (&it2)
-                     || it2.current_x > it2.last_visible_x)
+                 /* If we didn't get to CHARPOS - 1, there's some
+                    replacing display property at that position, and
+                    we stopped after it.  That is exactly the place
+                    whose coordinates we want.  */
+                 if (IT_CHARPOS (it2) != charpos - 1)
+                   it2_prev = it2;
+                 else
+                   {
+                     /* Iterate until we get out of the display
+                        vector that displays the character at
+                        CHARPOS - 1.  */
+                     do {
+                       get_next_display_element (&it2);
+                       PRODUCE_GLYPHS (&it2);
+                       it2_prev = it2;
+                       set_iterator_to_next (&it2, 1);
+                     } while (it2.method == GET_FROM_DISPLAY_VECTOR
+                              && IT_CHARPOS (it2) < charpos);
+                   }
+                 if (ITERATOR_AT_END_OF_LINE_P (&it2_prev)
+                     || it2_prev.current_x > it2_prev.last_visible_x)
                    top_x = it.glyph_row->x;
                  else
                    {
-                     top_x = it2.current_x;
-                     top_y = it2.current_y;
+                     top_x = it2_prev.current_x;
+                     top_y = it2_prev.current_y;
                    }
                }
            }