commit 42abb26054ed2a4aa161e97f9479a6902c92e669
Author: Jean-Marc Lasgouttes <[email protected]>
Date:   Wed Feb 17 12:30:16 2021 +0100

    Make paragraph-goto and friends set paragraph to the top
    
    Add parameter 'force' to scrollToCursor(...) to avoid the case where the
    cursor is not set to top because it is already visible on screen.
    Change screen offset in this method so that the paragraph is really at
    the top of the screen. This part may cause unforeseen issues and needs care.
    
    gotoInset: use the new force flag and do not trigger a redraw.
    Instead, return a boolean telling whether redraw is needed.
    In the code that use it, set an update flag instead of the extra redraw.
    
    In the handling of paragraph-goto, also set the update flag instead of
    triggering a repaint.
    
    Remove Bufferview::scrollToCursor(), which was equivalent to showCursor().
    
    Fixes bug #10425.
---
 src/BufferView.cpp               |   57 ++++++++++++++-----------------------
 src/BufferView.h                 |    8 ++--
 src/frontends/qt/GuiWorkArea.cpp |    2 +-
 3 files changed, 27 insertions(+), 40 deletions(-)

diff --git a/src/BufferView.cpp b/src/BufferView.cpp
index bff44cd..526cb33 100644
--- a/src/BufferView.cpp
+++ b/src/BufferView.cpp
@@ -171,18 +171,18 @@ bool findInset(DocIterator & dit, vector<InsetCode> const 
& codes,
 
 
 /// Moves cursor to the next inset with one of the given codes.
-void gotoInset(BufferView * bv, vector<InsetCode> const & codes,
+bool gotoInset(BufferView * bv, vector<InsetCode> const & codes,
               bool same_content)
 {
        Cursor tmpcur = bv->cursor();
        if (!findInset(tmpcur, codes, same_content)) {
                bv->cursor().message(_("No more insets"));
-               return;
+               return false;
        }
 
        tmpcur.clearSelection();
        bv->setCursor(tmpcur);
-       bv->showCursor();
+       return bv->scrollToCursor(bv->cursor(), false, true);
 }
 
 
@@ -541,13 +541,13 @@ void BufferView::processUpdateFlags(Update::flags flags)
                if (needsFitCursor()) {
                        // First try to make the selection start visible
                        // (which is just the cursor when there is no selection)
-                       scrollToCursor(d->cursor_.selectionBegin(), false);
+                       scrollToCursor(d->cursor_.selectionBegin(), false, 
false);
                        // Metrics have to be recomputed (maybe again)
                        updateMetrics();
                        // Is the cursor visible? (only useful if cursor is at 
end of selection)
                        if (needsFitCursor()) {
                                // then try to make cursor visible instead
-                               scrollToCursor(d->cursor_, false);
+                               scrollToCursor(d->cursor_, false, false);
                                // Metrics have to be recomputed (maybe again)
                                updateMetrics(flags);
                        }
@@ -741,7 +741,7 @@ void BufferView::scrollDocView(int const pixels, bool 
update)
        // cut off at the top
        if (pixels <= d->scrollbarParameters_.min) {
                DocIterator dit = doc_iterator_begin(&buffer_);
-               showCursor(dit, false, update);
+               showCursor(dit, false, false, update);
                LYXERR(Debug::SCROLLING, "scroll to top");
                return;
        }
@@ -750,7 +750,7 @@ void BufferView::scrollDocView(int const pixels, bool 
update)
        if (pixels >= d->scrollbarParameters_.max) {
                DocIterator dit = doc_iterator_end(&buffer_);
                dit.backwardPos();
-               showCursor(dit, false, update);
+               showCursor(dit, false, false, update);
                LYXERR(Debug::SCROLLING, "scroll to bottom");
                return;
        }
@@ -775,7 +775,7 @@ void BufferView::scrollDocView(int const pixels, bool 
update)
        DocIterator dit = doc_iterator_begin(&buffer_);
        dit.pit() = i;
        LYXERR(Debug::SCROLLING, "pixels = " << pixels << " -> scroll to pit " 
<< i);
-       showCursor(dit, false, update);
+       showCursor(dit, false, false, update);
 }
 
 
@@ -961,32 +961,25 @@ int BufferView::workWidth() const
 
 void BufferView::recenter()
 {
-       showCursor(d->cursor_, true, true);
+       showCursor(d->cursor_, true, false, true);
 }
 
 
 void BufferView::showCursor()
 {
-       showCursor(d->cursor_, false, true);
+       showCursor(d->cursor_, false, false, true);
 }
 
 
 void BufferView::showCursor(DocIterator const & dit,
-       bool recenter, bool update)
-{
-       if (scrollToCursor(dit, recenter) && update)
-               processUpdateFlags(Update::Force);
-}
-
-
-void BufferView::scrollToCursor()
+       bool recenter, bool force, bool update)
 {
-       if (scrollToCursor(d->cursor_, false))
+       if (scrollToCursor(dit, recenter, force) && update)
                processUpdateFlags(Update::Force);
 }
 
 
-bool BufferView::scrollToCursor(DocIterator const & dit, bool const recenter)
+bool BufferView::scrollToCursor(DocIterator const & dit, bool const recenter, 
bool force)
 {
        // We are not properly started yet, delay until resizing is done.
        if (height_ == 0)
@@ -1014,7 +1007,7 @@ bool BufferView::scrollToCursor(DocIterator const & dit, 
bool const recenter)
        else if (bot_pit == tm.last().first + 1)
                tm.newParMetricsDown();
 
-       if (tm.contains(bot_pit)) {
+       if (tm.contains(bot_pit) && !force) {
                ParagraphMetrics const & pm = tm.parMetrics(bot_pit);
                LBUFERR(!pm.rows().empty());
                // FIXME: smooth scrolling doesn't work in mathed.
@@ -1078,9 +1071,9 @@ bool BufferView::scrollToCursor(DocIterator const & dit, 
bool const recenter)
        else if (d->anchor_pit_ == max_pit)
                d->anchor_ypos_ = height_ - offset - row_dim.descent();
        else if (offset > height_)
-               d->anchor_ypos_ = height_ - offset - defaultRowHeight();
+               d->anchor_ypos_ = height_ - offset - row_dim.descent();
        else
-               d->anchor_ypos_ = defaultRowHeight() * 2;
+               d->anchor_ypos_ = row_dim.ascent();
 
        return true;
 }
@@ -1586,8 +1579,8 @@ void BufferView::dispatch(FuncRequest const & cmd, 
DispatchResult & dr)
                                        success = setCursorFromEntries({id, 
pos},
                                                                       {id_end, 
pos_end});
                                }
-                               if (success)
-                                       dr.screenUpdate(Update::Force | 
Update::FitCursor);
+                               if (success && scrollToCursor(d->cursor_, 
false, true))
+                                               dr.screenUpdate(Update::Force);
                        } else {
                                // Switch to other buffer view and resend cmd
                                lyx::dispatch(FuncRequest(
@@ -1600,19 +1593,13 @@ void BufferView::dispatch(FuncRequest const & cmd, 
DispatchResult & dr)
        }
 
        case LFUN_NOTE_NEXT:
-               gotoInset(this, { NOTE_CODE }, false);
-               // FIXME: if SinglePar is changed to act on the inner
-               // paragraph, this will not be OK anymore. The update is
-               // useful for auto-open collapsible insets.
-               dr.screenUpdate(Update::SinglePar | Update::FitCursor);
+               if (gotoInset(this, { NOTE_CODE }, false))
+                       dr.screenUpdate(Update::Force);
                break;
 
        case LFUN_REFERENCE_NEXT: {
-               gotoInset(this, { LABEL_CODE, REF_CODE }, true);
-               // FIXME: if SinglePar is changed to act on the inner
-               // paragraph, this will not be OK anymore. The update is
-               // useful for auto-open collapsible insets.
-               dr.screenUpdate(Update::SinglePar | Update::FitCursor);
+               if (gotoInset(this, { LABEL_CODE, REF_CODE }, true))
+                       dr.screenUpdate(Update::Force);
                break;
        }
 
diff --git a/src/BufferView.h b/src/BufferView.h
index b2fa1c0..e831e3a 100644
--- a/src/BufferView.h
+++ b/src/BufferView.h
@@ -205,13 +205,13 @@ public:
        /// This method will automatically scroll and update the BufferView
        /// (metrics+drawing) if needed.
        /// \param recenter Whether the cursor should be centered on screen
-       void showCursor(DocIterator const & dit, bool recenter,
+       /// \param force If true, disregard current position
+       void showCursor(DocIterator const & dit, bool recenter, bool force,
                bool update);
        /// Scroll to the cursor.
-       void scrollToCursor();
-       /// Scroll to the cursor.
        /// \param recenter Whether the cursor should be centered on screen
-       bool scrollToCursor(DocIterator const & dit, bool recenter);
+       /// \param force If true, disregard current position
+       bool scrollToCursor(DocIterator const & dit, bool recenter, bool force);
        /// scroll down document by the given number of pixels.
        int scrollDown(int pixels);
        /// scroll up document by the given number of pixels.
diff --git a/src/frontends/qt/GuiWorkArea.cpp b/src/frontends/qt/GuiWorkArea.cpp
index bebd122..e08779a 100644
--- a/src/frontends/qt/GuiWorkArea.cpp
+++ b/src/frontends/qt/GuiWorkArea.cpp
@@ -464,7 +464,7 @@ void GuiWorkArea::Private::resizeBufferView()
        bool const caret_in_view = buffer_view_->caretInView();
        buffer_view_->resize(p->viewport()->width(), p->viewport()->height());
        if (caret_in_view)
-               buffer_view_->scrollToCursor();
+               buffer_view_->showCursor();
        resetCaret();
 
        // Update scrollbars which might have changed due different
-- 
lyx-cvs mailing list
[email protected]
http://lists.lyx.org/mailman/listinfo/lyx-cvs

Reply via email to