diff options
| author | Eli Zaretskii | 2014-09-29 22:10:28 +0300 |
|---|---|---|
| committer | Eli Zaretskii | 2014-09-29 22:10:28 +0300 |
| commit | 5bb6d037f01ae43baf5a2f71398e803ccfa3643b (patch) | |
| tree | 0ab5158ffc2e03dc08df51fe3f0a510a68386d75 /src | |
| parent | 95e509140eb219cd9e729f5f371f5dcdf89223cc (diff) | |
| download | emacs-5bb6d037f01ae43baf5a2f71398e803ccfa3643b.tar.gz emacs-5bb6d037f01ae43baf5a2f71398e803ccfa3643b.zip | |
Fix bug #18545 with lack of scrolling a window when point goes out of view.
src/xdisp.c (cursor_row_fully_visible_p): Update commentary.
(redisplay_window): Treat the frame's frozen_window_starts flag
the same way as the optional_new_start flag for the window: only
obey it if the glyph row showing point will be fully visible.
Likewise when the window start is in a continuation line. If,
after trying everything under the 'force_start' label, point is
still not fully visible, give up and scroll the window. Add
debugging traces.
src/window.c (Frecenter): Set the window's redisplay flag.
Diffstat (limited to 'src')
| -rw-r--r-- | src/ChangeLog | 13 | ||||
| -rw-r--r-- | src/window.c | 2 | ||||
| -rw-r--r-- | src/xdisp.c | 60 |
3 files changed, 64 insertions, 11 deletions
diff --git a/src/ChangeLog b/src/ChangeLog index a5c25ab7168..cc04e0cd826 100644 --- a/src/ChangeLog +++ b/src/ChangeLog | |||
| @@ -1,3 +1,16 @@ | |||
| 1 | 2014-09-29 Eli Zaretskii <eliz@gnu.org> | ||
| 2 | |||
| 3 | * xdisp.c (cursor_row_fully_visible_p): Update commentary. | ||
| 4 | (redisplay_window): Treat the frame's frozen_window_starts flag | ||
| 5 | the same way as the optional_new_start flag for the window: only | ||
| 6 | obey it if the glyph row showing point will be fully visible. | ||
| 7 | Likewise when the window start is in a continuation line. If, | ||
| 8 | after trying everything under the 'force_start' label, point is | ||
| 9 | still not fully visible, give up and scroll the window. Add | ||
| 10 | debugging traces. (Bug#18545) | ||
| 11 | |||
| 12 | * window.c (Frecenter): Set the window's redisplay flag. | ||
| 13 | |||
| 1 | 2014-09-24 Eli Zaretskii <eliz@gnu.org> | 14 | 2014-09-24 Eli Zaretskii <eliz@gnu.org> |
| 2 | 15 | ||
| 3 | * w32term.c (w32_read_socket): Don't use frame dimensions for | 16 | * w32term.c (w32_read_socket): Don't use frame dimensions for |
diff --git a/src/window.c b/src/window.c index 7e50282a39b..2210d5bc868 100644 --- a/src/window.c +++ b/src/window.c | |||
| @@ -5897,6 +5897,8 @@ and redisplay normally--don't erase and redraw the frame. */) | |||
| 5897 | w->start_at_line_beg = (bytepos == BEGV_BYTE || | 5897 | w->start_at_line_beg = (bytepos == BEGV_BYTE || |
| 5898 | FETCH_BYTE (bytepos - 1) == '\n'); | 5898 | FETCH_BYTE (bytepos - 1) == '\n'); |
| 5899 | 5899 | ||
| 5900 | wset_redisplay (w); | ||
| 5901 | |||
| 5900 | set_buffer_internal (obuf); | 5902 | set_buffer_internal (obuf); |
| 5901 | return Qnil; | 5903 | return Qnil; |
| 5902 | } | 5904 | } |
diff --git a/src/xdisp.c b/src/xdisp.c index 754862d59d1..ee05ea2a053 100644 --- a/src/xdisp.c +++ b/src/xdisp.c | |||
| @@ -15027,6 +15027,10 @@ run_window_scroll_functions (Lisp_Object window, struct text_pos startp) | |||
| 15027 | If FORCE_P is non-zero, return 0 even if partial visible cursor row | 15027 | If FORCE_P is non-zero, return 0 even if partial visible cursor row |
| 15028 | is higher than window. | 15028 | is higher than window. |
| 15029 | 15029 | ||
| 15030 | If CURRENT_MATRIX_P is non-zero, use the information from the | ||
| 15031 | window's current glyph matrix; otherwise uze the desired glyph | ||
| 15032 | matrix. | ||
| 15033 | |||
| 15030 | A value of 0 means the caller should do scrolling | 15034 | A value of 0 means the caller should do scrolling |
| 15031 | as if point had gone off the screen. */ | 15035 | as if point had gone off the screen. */ |
| 15032 | 15036 | ||
| @@ -16136,26 +16140,48 @@ redisplay_window (Lisp_Object window, bool just_this_one_p) | |||
| 16136 | 16140 | ||
| 16137 | /* If someone specified a new starting point but did not insist, | 16141 | /* If someone specified a new starting point but did not insist, |
| 16138 | check whether it can be used. */ | 16142 | check whether it can be used. */ |
| 16139 | if (w->optional_new_start | 16143 | if ((w->optional_new_start || window_frozen_p (w)) |
| 16140 | && CHARPOS (startp) >= BEGV | 16144 | && CHARPOS (startp) >= BEGV |
| 16141 | && CHARPOS (startp) <= ZV) | 16145 | && CHARPOS (startp) <= ZV) |
| 16142 | { | 16146 | { |
| 16147 | ptrdiff_t it_charpos; | ||
| 16148 | |||
| 16143 | w->optional_new_start = 0; | 16149 | w->optional_new_start = 0; |
| 16144 | start_display (&it, w, startp); | 16150 | start_display (&it, w, startp); |
| 16145 | move_it_to (&it, PT, 0, it.last_visible_y, -1, | 16151 | move_it_to (&it, PT, 0, it.last_visible_y, -1, |
| 16146 | MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y); | 16152 | MOVE_TO_POS | MOVE_TO_X | MOVE_TO_Y); |
| 16147 | if (IT_CHARPOS (it) == PT) | 16153 | /* Record IT's position now, since line_bottom_y might change |
| 16148 | w->force_start = 1; | 16154 | that. */ |
| 16149 | /* IT may overshoot PT if text at PT is invisible. */ | 16155 | it_charpos = IT_CHARPOS (it); |
| 16150 | else if (IT_CHARPOS (it) > PT && CHARPOS (startp) <= PT) | 16156 | /* Make sure we set the force_start flag only if the cursor row |
| 16151 | w->force_start = 1; | 16157 | will be fully visible. Otherwise, the code under force_start |
| 16158 | label below will try to move point back into view, which is | ||
| 16159 | not what the code which sets optional_new_start wants. */ | ||
| 16160 | if ((it.current_y == 0 || line_bottom_y (&it) < it.last_visible_y) | ||
| 16161 | && !w->force_start) | ||
| 16162 | { | ||
| 16163 | if (it_charpos == PT) | ||
| 16164 | w->force_start = 1; | ||
| 16165 | /* IT may overshoot PT if text at PT is invisible. */ | ||
| 16166 | else if (it_charpos > PT && CHARPOS (startp) <= PT) | ||
| 16167 | w->force_start = 1; | ||
| 16168 | #ifdef GLYPH_DEBUG | ||
| 16169 | if (w->force_start) | ||
| 16170 | { | ||
| 16171 | if (window_frozen_p (w)) | ||
| 16172 | debug_method_add (w, "set force_start from frozen window start"); | ||
| 16173 | else | ||
| 16174 | debug_method_add (w, "set force_start from optional_new_start"); | ||
| 16175 | } | ||
| 16176 | #endif | ||
| 16177 | } | ||
| 16152 | } | 16178 | } |
| 16153 | 16179 | ||
| 16154 | force_start: | 16180 | force_start: |
| 16155 | 16181 | ||
| 16156 | /* Handle case where place to start displaying has been specified, | 16182 | /* Handle case where place to start displaying has been specified, |
| 16157 | unless the specified location is outside the accessible range. */ | 16183 | unless the specified location is outside the accessible range. */ |
| 16158 | if (w->force_start || window_frozen_p (w)) | 16184 | if (w->force_start) |
| 16159 | { | 16185 | { |
| 16160 | /* We set this later on if we have to adjust point. */ | 16186 | /* We set this later on if we have to adjust point. */ |
| 16161 | int new_vpos = -1; | 16187 | int new_vpos = -1; |
| @@ -16200,7 +16226,7 @@ redisplay_window (Lisp_Object window, bool just_this_one_p) | |||
| 16200 | goto need_larger_matrices; | 16226 | goto need_larger_matrices; |
| 16201 | } | 16227 | } |
| 16202 | 16228 | ||
| 16203 | if (w->cursor.vpos < 0 && !window_frozen_p (w)) | 16229 | if (w->cursor.vpos < 0) |
| 16204 | { | 16230 | { |
| 16205 | /* If point does not appear, try to move point so it does | 16231 | /* If point does not appear, try to move point so it does |
| 16206 | appear. The desired matrix has been built above, so we | 16232 | appear. The desired matrix has been built above, so we |
| @@ -16293,6 +16319,11 @@ redisplay_window (Lisp_Object window, bool just_this_one_p) | |||
| 16293 | } | 16319 | } |
| 16294 | */ | 16320 | */ |
| 16295 | } | 16321 | } |
| 16322 | if (w->cursor.vpos < 0 || !cursor_row_fully_visible_p (w, 0, 0)) | ||
| 16323 | { | ||
| 16324 | clear_glyph_matrix (w->desired_matrix); | ||
| 16325 | goto try_to_scroll; | ||
| 16326 | } | ||
| 16296 | 16327 | ||
| 16297 | #ifdef GLYPH_DEBUG | 16328 | #ifdef GLYPH_DEBUG |
| 16298 | debug_method_add (w, "forced window start"); | 16329 | debug_method_add (w, "forced window start"); |
| @@ -16357,7 +16388,8 @@ redisplay_window (Lisp_Object window, bool just_this_one_p) | |||
| 16357 | || CHARPOS (startp) == BEGV | 16388 | || CHARPOS (startp) == BEGV |
| 16358 | || !window_outdated (w))) | 16389 | || !window_outdated (w))) |
| 16359 | { | 16390 | { |
| 16360 | int d1, d2, d3, d4, d5, d6; | 16391 | int d1, d2, d5, d6; |
| 16392 | int rtop, rbot; | ||
| 16361 | 16393 | ||
| 16362 | /* If first window line is a continuation line, and window start | 16394 | /* If first window line is a continuation line, and window start |
| 16363 | is inside the modified region, but the first change is before | 16395 | is inside the modified region, but the first change is before |
| @@ -16382,14 +16414,20 @@ redisplay_window (Lisp_Object window, bool just_this_one_p) | |||
| 16382 | && compute_window_start_on_continuation_line (w) | 16414 | && compute_window_start_on_continuation_line (w) |
| 16383 | /* It doesn't make sense to force the window start like we | 16415 | /* It doesn't make sense to force the window start like we |
| 16384 | do at label force_start if it is already known that point | 16416 | do at label force_start if it is already known that point |
| 16385 | will not be visible in the resulting window, because | 16417 | will not be fully visible in the resulting window, because |
| 16386 | doing so will move point from its correct position | 16418 | doing so will move point from its correct position |
| 16387 | instead of scrolling the window to bring point into view. | 16419 | instead of scrolling the window to bring point into view. |
| 16388 | See bug#9324. */ | 16420 | See bug#9324. */ |
| 16389 | && pos_visible_p (w, PT, &d1, &d2, &d3, &d4, &d5, &d6)) | 16421 | && pos_visible_p (w, PT, &d1, &d2, &rtop, &rbot, &d5, &d6) |
| 16422 | /* A very tall row could need more than the window height, | ||
| 16423 | in which case we accept that it is partially visible. */ | ||
| 16424 | && (rtop != 0) == (rbot != 0)) | ||
| 16390 | { | 16425 | { |
| 16391 | w->force_start = 1; | 16426 | w->force_start = 1; |
| 16392 | SET_TEXT_POS_FROM_MARKER (startp, w->start); | 16427 | SET_TEXT_POS_FROM_MARKER (startp, w->start); |
| 16428 | #ifdef GLYPH_DEBUG | ||
| 16429 | debug_method_add (w, "recomputed window start in continuation line"); | ||
| 16430 | #endif | ||
| 16393 | goto force_start; | 16431 | goto force_start; |
| 16394 | } | 16432 | } |
| 16395 | 16433 | ||