/// 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);
}
///
CoordCache coord_cache_;
///
- typedef map<MathData const *, MathRow> MathRows;
+ typedef unordered_map<MathData const *, MathRow> MathRows;
MathRows math_rows_;
/// this is used to handle XSelection events in the right manner.
}
-int BufferView::rightMargin() const
+int BufferView::defaultMargin() const
{
// The value used to be hardcoded to 10
- int const default_margin = zoomedPixels(10);
+ return zoomedPixels(20);
+}
+
+
+int BufferView::rightMargin() const
+{
// The additional test for the case the outliner is opened.
- if (!full_screen_ || !lyxrc.full_screen_limit
- || width_ < lyxrc.full_screen_width + 2 * default_margin)
- return default_margin;
+ if (full_screen_ && lyxrc.full_screen_limit)
+ return max(defaultMargin(), (width_ - lyxrc.full_screen_width) / 2);
- return (width_ - lyxrc.full_screen_width) / 2;
+ return defaultMargin();
}
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);
}
}
-void BufferView::updateScrollbar()
+void BufferView::updateScrollbarParameters()
{
if (height_ == 0 && width_ == 0)
return;
// 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;
}
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;
}
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);
}
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)
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.
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;
}
else {
dr.screenUpdate(Update::Force | Update::FitCursor);
dr.forceBufferUpdate();
+ resetInlineCompletionPos();
if (buffer().params().citeEngine() != engine ||
buffer().params().citeEngineType() != enginetype)
buffer().invalidateCiteLabels();
else {
dr.screenUpdate(Update::Force | Update::FitCursor);
dr.forceBufferUpdate();
+ resetInlineCompletionPos();
if (buffer().params().citeEngine() != engine ||
buffer().params().citeEngineType() != enginetype)
buffer().invalidateCiteLabels();
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(
}
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;
}
cur.setCursor(doc_iterator_begin(cur.buffer()));
cur.selHandle(false);
// Force an immediate computation of metrics because we need it below
- updateMetrics();
+ if (scrolled)
+ processUpdateFlags(Update::Force);
d->text_metrics_[&buffer_.text()].editXY(cur, p.x_, p.y_,
true, act == LFUN_SCREEN_UP);
// an arbitrary number to limit number of iterations
const int max_iter = 100000;
int iterations = 0;
- Cursor & curs = d->cursor_;
- Cursor const savecur = curs;
- curs.reset();
- if (!curs.nextInset())
- curs.forwardInset();
- curs.beginUndoGroup();
- while(curs && iterations < max_iter) {
- Inset * const ins = curs.nextInset();
+ Cursor & bvcur = d->cursor_;
+ Cursor const savecur = bvcur;
+ bvcur.reset();
+ if (!bvcur.nextInset())
+ bvcur.forwardInset();
+ bvcur.beginUndoGroup();
+ while(bvcur && iterations < max_iter) {
+ Inset * const ins = bvcur.nextInset();
if (!ins)
break;
docstring insname = ins->layoutName();
while (!insname.empty()) {
if (insname == name || name == from_utf8("*")) {
- curs.recordUndo();
lyx::dispatch(fr, dr);
+ // we do not want to remember selection here
+ bvcur.clearSelection();
++iterations;
break;
}
insname = insname.substr(0, i);
}
// if we did not delete the inset, skip it
- if (!curs.nextInset() || curs.nextInset() == ins)
- curs.forwardInset();
+ if (!bvcur.nextInset() || bvcur.nextInset() == ins)
+ bvcur.forwardInset();
}
- curs = savecur;
- curs.fixIfBroken();
+ bvcur = savecur;
+ bvcur.fixIfBroken();
/** This is a dummy undo record only to remember the cursor
* that has just been set; this will be used on a redo action
* (see ticket #10097)
* FIXME: a better fix would be to have a way to set the
* cursor value directly, but I am not sure it is worth it.
*/
- curs.recordUndo();
- curs.endUndoGroup();
+ bvcur.recordUndo();
+ bvcur.endUndoGroup();
dr.screenUpdate(Update::Force);
dr.forceBufferUpdate();
// Notify left insets
if (cur != old) {
- bool badcursor = old.fixIfBroken() | cur.fixIfBroken();
- badcursor |= notifyCursorLeavesOrEnters(old, cur);
+ bool badcursor = old.fixIfBroken() || cur.fixIfBroken();
+ badcursor = badcursor || notifyCursorLeavesOrEnters(old, cur);
if (badcursor)
cursor().fixIfBroken();
}
{
TexRow::TextEntry start, end;
tie(start,end) = buffer_.texrow().getEntriesFromRow(row);
- LYXERR(Debug::LATEX,
+ LYXERR(Debug::OUTFILE,
"setCursorFromRow: for row " << row << ", TexRow has found "
"start (id=" << start.id << ",pos=" << start.pos << "), "
"end (id=" << end.id << ",pos=" << end.pos << ")");
//lyxerr << "cur_x=" << cur_x << ", offset=" << offset << ", row.wid=" << row.width() << ", margin=" << MARGIN << endl;
- if (offset != d->horiz_scroll_offset_)
+ if (offset != d->horiz_scroll_offset_) {
LYXERR(Debug::PAINTING, "Horiz. scroll offset changed from "
<< d->horiz_scroll_offset_ << " to " << offset);
-
- if (d->update_strategy_ == NoScreenUpdate
- && offset != d->horiz_scroll_offset_) {
- // FIXME: if one uses SingleParUpdate, then home/end
- // will not work on long rows. Why?
- d->update_strategy_ = FullScreenUpdate;
+ row.changed(true);
+ if (d->update_strategy_ == NoScreenUpdate)
+ d->update_strategy_ = SingleParUpdate;
}
d->horiz_scroll_offset_ = offset;
// The scrollbar needs an update.
// FIXME: does it always? see ticket #11947.
- updateScrollbar();
+ updateScrollbarParameters();
// Normalize anchor for next time
pair<pit_type, ParagraphMetrics const *> firstpm = tm.first();