diff options
author | Eli Zaretskii <eliz@gnu.org> | 2014-12-25 17:38:15 +0200 |
---|---|---|
committer | Eli Zaretskii <eliz@gnu.org> | 2014-12-25 17:38:15 +0200 |
commit | a41d07b329c034ad34e442bef93b6fcaeb556f9f (patch) | |
tree | 2c2f674122fcb67314d13a7228eee142291a1200 | |
parent | b70977ce02432b1ded569215096402e2eee318a3 (diff) | |
download | emacs-a41d07b329c034ad34e442bef93b6fcaeb556f9f.tar.gz emacs-a41d07b329c034ad34e442bef93b6fcaeb556f9f.tar.bz2 emacs-a41d07b329c034ad34e442bef93b6fcaeb556f9f.zip |
Fix rendering of composed caharacters on the mode line. (Bug#19435)
src/xdisp.c (set_iterator_to_next) <GET_FROM_STRING>: Limit search in
composition_compute_stop_pos to the number of characters in the
string.
<GET_FROM_BUFFER, GET_FROM_STRING>: Simplify code.
src/composite.c (composition_compute_stop_pos): If no composition
was found in a string before ENDPOS, and ENDPOS is the string end,
no need to back up to a safe point.
src/dispextern.h (struct it) <end_charpos>: Improve commentary.
-rw-r--r-- | src/ChangeLog | 13 | ||||
-rw-r--r-- | src/composite.c | 3 | ||||
-rw-r--r-- | src/dispextern.h | 5 | ||||
-rw-r--r-- | src/xdisp.c | 171 |
4 files changed, 93 insertions, 99 deletions
diff --git a/src/ChangeLog b/src/ChangeLog index 2840109ac1c..2df83082fbd 100644 --- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,16 @@ +2014-12-25 Eli Zaretskii <eliz@gnu.org> + + * xdisp.c (set_iterator_to_next) <GET_FROM_STRING>: Limit search in + composition_compute_stop_pos to the number of characters in the + string. (Bug#19435) + <GET_FROM_BUFFER, GET_FROM_STRING>: Simplify code. + + * composite.c (composition_compute_stop_pos): If no composition + was found in a string before ENDPOS, and ENDPOS is the string end, + no need to back up to a safe point. + + * dispextern.h (struct it) <end_charpos>: Improve commentary. + 2014-12-24 Jan Djärv <jan.h.d@swipnet.se> * nsimage.m (allocInitFromFile:): Initialize bmRep. diff --git a/src/composite.c b/src/composite.c index fa882141908..a1282103972 100644 --- a/src/composite.c +++ b/src/composite.c @@ -1036,7 +1036,8 @@ composition_compute_stop_pos (struct composition_it *cmp_it, ptrdiff_t charpos, } } } - if (charpos == endpos) + if (charpos == endpos + && !(STRINGP (string) && endpos == SCHARS (string))) { /* We couldn't find a composition point before ENDPOS. But, some character after ENDPOS may be composed with diff --git a/src/dispextern.h b/src/dispextern.h index 576f22870c2..0e5a73a929c 100644 --- a/src/dispextern.h +++ b/src/dispextern.h @@ -2222,7 +2222,10 @@ struct it ptrdiff_t base_level_stop; /* Maximum string or buffer position + 1. ZV when iterating over - current_buffer. */ + current_buffer. When iterating over a string in display_string, + this can be smaller or greater than the number of string + characters, depending on the values of PRECISION and FIELD_WIDTH + with which display_string was called. */ ptrdiff_t end_charpos; /* C string to iterate over. Non-null means get characters from diff --git a/src/xdisp.c b/src/xdisp.c index e3e00357ed0..173df5d011b 100644 --- a/src/xdisp.c +++ b/src/xdisp.c @@ -7330,27 +7330,15 @@ set_iterator_to_next (struct it *it, int reseat_p) else if (it->cmp_it.id >= 0) { /* We are currently getting glyphs from a composition. */ - int i; - if (! it->bidi_p) { IT_CHARPOS (*it) += it->cmp_it.nchars; IT_BYTEPOS (*it) += it->cmp_it.nbytes; - if (it->cmp_it.to < it->cmp_it.nglyphs) - { - it->cmp_it.from = it->cmp_it.to; - } - else - { - it->cmp_it.id = -1; - composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it), - IT_BYTEPOS (*it), - it->end_charpos, Qnil); - } } - else if (! it->cmp_it.reversed_p) + else { - /* Composition created while scanning forward. */ + int i; + /* Update IT's char/byte positions to point to the first character of the next grapheme cluster, or to the character visually after the current composition. */ @@ -7358,52 +7346,34 @@ set_iterator_to_next (struct it *it, int reseat_p) bidi_move_to_visually_next (&it->bidi_it); IT_BYTEPOS (*it) = it->bidi_it.bytepos; IT_CHARPOS (*it) = it->bidi_it.charpos; + } - if (it->cmp_it.to < it->cmp_it.nglyphs) - { - /* Proceed to the next grapheme cluster. */ - it->cmp_it.from = it->cmp_it.to; - } - else - { - /* No more grapheme clusters in this composition. - Find the next stop position. */ - ptrdiff_t stop = it->end_charpos; - if (it->bidi_it.scan_dir < 0) - /* Now we are scanning backward and don't know - where to stop. */ - stop = -1; - composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it), - IT_BYTEPOS (*it), stop, Qnil); - } + if ((! it->bidi_p || ! it->cmp_it.reversed_p) + && it->cmp_it.to < it->cmp_it.nglyphs) + { + /* Composition created while scanning forward. Proceed + to the next grapheme cluster. */ + it->cmp_it.from = it->cmp_it.to; + } + else if ((it->bidi_p && it->cmp_it.reversed_p) + && it->cmp_it.from > 0) + { + /* Composition created while scanning backward. Proceed + to the previous grapheme cluster. */ + it->cmp_it.to = it->cmp_it.from; } else { - /* Composition created while scanning backward. */ - /* Update IT's char/byte positions to point to the last - character of the previous grapheme cluster, or the - character visually after the current composition. */ - for (i = 0; i < it->cmp_it.nchars; i++) - bidi_move_to_visually_next (&it->bidi_it); - IT_BYTEPOS (*it) = it->bidi_it.bytepos; - IT_CHARPOS (*it) = it->bidi_it.charpos; - if (it->cmp_it.from > 0) - { - /* Proceed to the previous grapheme cluster. */ - it->cmp_it.to = it->cmp_it.from; - } - else - { - /* No more grapheme clusters in this composition. - Find the next stop position. */ - ptrdiff_t stop = it->end_charpos; - if (it->bidi_it.scan_dir < 0) - /* Now we are scanning backward and don't know - where to stop. */ - stop = -1; - composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it), - IT_BYTEPOS (*it), stop, Qnil); - } + /* No more grapheme clusters in this composition. + Find the next stop position. */ + ptrdiff_t stop = it->end_charpos; + + if (it->bidi_it.scan_dir < 0) + /* Now we are scanning backward and don't know + where to stop. */ + stop = -1; + composition_compute_stop_pos (&it->cmp_it, IT_CHARPOS (*it), + IT_BYTEPOS (*it), stop, Qnil); } } else @@ -7532,61 +7502,63 @@ set_iterator_to_next (struct it *it, int reseat_p) } if (it->cmp_it.id >= 0) { - int i; - + /* We are delivering display elements from a composition. + Update the string position past the grapheme cluster + we've just processed. */ if (! it->bidi_p) { IT_STRING_CHARPOS (*it) += it->cmp_it.nchars; IT_STRING_BYTEPOS (*it) += it->cmp_it.nbytes; - if (it->cmp_it.to < it->cmp_it.nglyphs) - it->cmp_it.from = it->cmp_it.to; - else - { - it->cmp_it.id = -1; - composition_compute_stop_pos (&it->cmp_it, - IT_STRING_CHARPOS (*it), - IT_STRING_BYTEPOS (*it), - it->end_charpos, it->string); - } } - else if (! it->cmp_it.reversed_p) + else { + int i; + for (i = 0; i < it->cmp_it.nchars; i++) bidi_move_to_visually_next (&it->bidi_it); IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos; IT_STRING_CHARPOS (*it) = it->bidi_it.charpos; + } - if (it->cmp_it.to < it->cmp_it.nglyphs) - it->cmp_it.from = it->cmp_it.to; - else - { - ptrdiff_t stop = it->end_charpos; - if (it->bidi_it.scan_dir < 0) - stop = -1; - composition_compute_stop_pos (&it->cmp_it, - IT_STRING_CHARPOS (*it), - IT_STRING_BYTEPOS (*it), stop, - it->string); - } + /* Did we exhaust all the grapheme clusters of this + composition? */ + if ((! it->bidi_p || ! it->cmp_it.reversed_p) + && (it->cmp_it.to < it->cmp_it.nglyphs)) + { + /* Not all the grapheme clusters were processed yet; + advance to the next cluster. */ + it->cmp_it.from = it->cmp_it.to; + } + else if ((it->bidi_p && it->cmp_it.reversed_p) + && it->cmp_it.from > 0) + { + /* Likewise: advance to the next cluster, but going in + the reverse direction. */ + it->cmp_it.to = it->cmp_it.from; } else { - for (i = 0; i < it->cmp_it.nchars; i++) - bidi_move_to_visually_next (&it->bidi_it); - IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos; - IT_STRING_CHARPOS (*it) = it->bidi_it.charpos; - if (it->cmp_it.from > 0) - it->cmp_it.to = it->cmp_it.from; - else + /* This composition was fully processed; find the next + candidate place for checking for composed + characters. */ + /* Always limit string searches to the string length; + any padding spaces are not part of the string, and + there cannot be any compositions in that padding. */ + ptrdiff_t stop = SCHARS (it->string); + + if (it->bidi_p && it->bidi_it.scan_dir < 0) + stop = -1; + else if (it->end_charpos < stop) { - ptrdiff_t stop = it->end_charpos; - if (it->bidi_it.scan_dir < 0) - stop = -1; - composition_compute_stop_pos (&it->cmp_it, - IT_STRING_CHARPOS (*it), - IT_STRING_BYTEPOS (*it), stop, - it->string); + /* Cf. PRECISION in reseat_to_string: we might be + limited in how many of the string characters we + need to deliver. */ + stop = it->end_charpos; } + composition_compute_stop_pos (&it->cmp_it, + IT_STRING_CHARPOS (*it), + IT_STRING_BYTEPOS (*it), stop, + it->string); } } else @@ -7609,12 +7581,17 @@ set_iterator_to_next (struct it *it, int reseat_p) bidi_move_to_visually_next (&it->bidi_it); IT_STRING_BYTEPOS (*it) = it->bidi_it.bytepos; IT_STRING_CHARPOS (*it) = it->bidi_it.charpos; + /* If the scan direction changes, we may need to update + the place where to check for composed characters. */ if (prev_scan_dir != it->bidi_it.scan_dir) { - ptrdiff_t stop = it->end_charpos; + ptrdiff_t stop = SCHARS (it->string); if (it->bidi_it.scan_dir < 0) stop = -1; + else if (it->end_charpos < stop) + stop = it->end_charpos; + composition_compute_stop_pos (&it->cmp_it, IT_STRING_CHARPOS (*it), IT_STRING_BYTEPOS (*it), stop, |