forked from qt-creator/qt-creator
FakeVim: Don't overuse cursor setting and scrolling in editor
Set new text cursor and scroll in editor widget only if it's only needed. Sometimes these action can have side-effects. Set new cursor and scroll especially after no pending input and commands are available to process for FakeVim. Change-Id: I47df4d0328ac990e2e5c6981955ea7d1bd608c71 Reviewed-by: hjk <hjk121@nokiamail.com>
This commit is contained in:
@@ -2948,3 +2948,357 @@ void FakeVimPlugin::test_macros()
|
|||||||
KEYS("gg@x", "abc" N X "def");
|
KEYS("gg@x", "abc" N X "def");
|
||||||
data.doCommand("unmap <S-down>");
|
data.doCommand("unmap <S-down>");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void FakeVimPlugin::test_vim_qtcreator()
|
||||||
|
{
|
||||||
|
TestData data;
|
||||||
|
setup(&data);
|
||||||
|
|
||||||
|
// Pass input keys in insert mode to underlying editor widget.
|
||||||
|
data.doCommand("set passkeys");
|
||||||
|
|
||||||
|
data.setText("" N "");
|
||||||
|
KEYS("i" "void f(int arg1) {<cr>// TODO<cr>;",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" ;" X N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("cc" "assert(arg1 != 0",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" assert(arg1 != 0" X ")" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("k" "." "A;",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0);" X N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("j.",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0)" X ";" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("4b2#",
|
||||||
|
"void f(int " X "arg1) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("e" "a, int arg2 = 0<esc>" "n",
|
||||||
|
"void f(int " X "arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Record macro.
|
||||||
|
KEYS("2j" "qa" "<C-A>" "f!" "2s>=<esc>" "q",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg2 >" X "= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
// Replay macro.
|
||||||
|
KEYS("n" "@a",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg2 >" X "= 0);" N
|
||||||
|
" assert(arg2 >= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Undo.
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(" X "arg1 != 0);" N
|
||||||
|
" assert(arg2 >= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg2 " X "!= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(" X "arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1" X ") {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0" X ")" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0" X ")" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" " X "// TODO" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" " X ";" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Redo and occasional undo.
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" " X "assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" " X "assert(arg1 != 0)" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0)" X ";" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0" X ")" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0)" X ";" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0)" X ";" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1" X ", int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(" X "arg2 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg2 " X ">= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(" X "arg2 >= 0);" N
|
||||||
|
" assert(arg2 >= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("3u",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(" X "arg1 != 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Repeat last command.
|
||||||
|
KEYS("w.",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 != 0);" N
|
||||||
|
" assert(arg1 >" X "= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
KEYS("kdd",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" " X "assert(arg1 >= 0);" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Make mistakes.
|
||||||
|
KEYS("4<esc>3<esc>" "2oif (arg3<bs>2<bs>1 > 0) return true;<esc>",
|
||||||
|
"void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true" X ";" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Jumps around and change stuff.
|
||||||
|
KEYS("gg" "ciw" "bool",
|
||||||
|
"bool" X " f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("`'",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true" X ";" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("caW" " false;",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return false;" X N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("k.",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return false" X ";" N
|
||||||
|
" if (arg1 > 0) return false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Undo/redo again.
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return" X " true;" N
|
||||||
|
" if (arg1 > 0) return false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return" X " true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return" X " false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return" X " true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
X "void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Record long insert mode.
|
||||||
|
KEYS("qb" "4s" "bool" "<down>" "Q_<insert>ASSERT" "<down><down>" "<insert><bs>2"
|
||||||
|
"<c-o>2w<delete>1" "<c-o>:s/true/false<cr><esc>" "q",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" " X " if (arg2 > 1) return false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
X " if (arg2 > 1) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg2 > " X "0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1" X " > 0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" " X "assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("u",
|
||||||
|
X "void f(int arg1, int arg2 = 0) {" N
|
||||||
|
" assert(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Replay.
|
||||||
|
KEYS("@b",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" " X " if (arg2 > 1) return false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Return to the first change.
|
||||||
|
KEYS("99u" "<C-R>",
|
||||||
|
X "void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" ;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" // TODO" N
|
||||||
|
" " X "assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
KEYS("<C-R>",
|
||||||
|
"void f(int arg1) {" N
|
||||||
|
" " X "assert(arg1 != 0)" N
|
||||||
|
" assert(arg1 != 0)" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
|
||||||
|
// Return to the last change.
|
||||||
|
KEYS("99<C-R>",
|
||||||
|
"bool f(int arg1, int arg2 = 0) {" N
|
||||||
|
" Q_ASSERT(arg1 >= 0);" N
|
||||||
|
" if (arg1 > 0) return true;" N
|
||||||
|
" if (arg2 > 1) return false;" N
|
||||||
|
"}" N
|
||||||
|
"");
|
||||||
|
}
|
||||||
|
@@ -1499,14 +1499,14 @@ public:
|
|||||||
int mvCount() const { return m_mvcount.isEmpty() ? 1 : m_mvcount.toInt(); }
|
int mvCount() const { return m_mvcount.isEmpty() ? 1 : m_mvcount.toInt(); }
|
||||||
int opCount() const { return m_opcount.isEmpty() ? 1 : m_opcount.toInt(); }
|
int opCount() const { return m_opcount.isEmpty() ? 1 : m_opcount.toInt(); }
|
||||||
int count() const { return mvCount() * opCount(); }
|
int count() const { return mvCount() * opCount(); }
|
||||||
QTextBlock block() const { return cursor().block(); }
|
QTextBlock block() const { return m_cursor.block(); }
|
||||||
int leftDist() const { return position() - block().position(); }
|
int leftDist() const { return position() - block().position(); }
|
||||||
int rightDist() const { return block().length() - leftDist() - 1; }
|
int rightDist() const { return block().length() - leftDist() - 1; }
|
||||||
bool atBlockStart() const { return cursor().atBlockStart(); }
|
bool atBlockStart() const { return m_cursor.atBlockStart(); }
|
||||||
bool atBlockEnd() const { return cursor().atBlockEnd(); }
|
bool atBlockEnd() const { return m_cursor.atBlockEnd(); }
|
||||||
bool atEndOfLine() const { return atBlockEnd() && block().length() > 1; }
|
bool atEndOfLine() const { return atBlockEnd() && block().length() > 1; }
|
||||||
bool atDocumentEnd() const { return position() >= lastPositionInDocument(); }
|
bool atDocumentEnd() const { return position() >= lastPositionInDocument(); }
|
||||||
bool atDocumentStart() const { return cursor().atStart(); }
|
bool atDocumentStart() const { return m_cursor.atStart(); }
|
||||||
|
|
||||||
bool atEmptyLine(const QTextCursor &tc = QTextCursor()) const;
|
bool atEmptyLine(const QTextCursor &tc = QTextCursor()) const;
|
||||||
bool atBoundary(bool end, bool simple, bool onlyWords = false,
|
bool atBoundary(bool end, bool simple, bool onlyWords = false,
|
||||||
@@ -1540,8 +1540,11 @@ public:
|
|||||||
int logicalToPhysicalColumn(int logical, const QString &text) const;
|
int logicalToPhysicalColumn(int logical, const QString &text) const;
|
||||||
int windowScrollOffset() const; // return scrolloffset but max half the current window height
|
int windowScrollOffset() const; // return scrolloffset but max half the current window height
|
||||||
Column cursorColumn() const; // as visible on screen
|
Column cursorColumn() const; // as visible on screen
|
||||||
|
void updateFirstVisibleLine();
|
||||||
int firstVisibleLine() const;
|
int firstVisibleLine() const;
|
||||||
void setScrollBarValue(int line);
|
int lastVisibleLine() const;
|
||||||
|
int lineOnTop(int count = 1) const; // [count]-th line from top reachable without scrolling
|
||||||
|
int lineOnBottom(int count = 1) const; // [count]-th line from bottom reachable without scrolling
|
||||||
void scrollToLine(int line);
|
void scrollToLine(int line);
|
||||||
void scrollUp(int count);
|
void scrollUp(int count);
|
||||||
void scrollDown(int count) { scrollUp(-count); }
|
void scrollDown(int count) { scrollUp(-count); }
|
||||||
@@ -1549,6 +1552,8 @@ public:
|
|||||||
void alignViewportToCursor(Qt::AlignmentFlag align, int line = -1,
|
void alignViewportToCursor(Qt::AlignmentFlag align, int line = -1,
|
||||||
bool moveToNonBlank = false);
|
bool moveToNonBlank = false);
|
||||||
|
|
||||||
|
int lineToBlockNumber(int line) const;
|
||||||
|
|
||||||
void setCursorPosition(const CursorPosition &p);
|
void setCursorPosition(const CursorPosition &p);
|
||||||
void setCursorPosition(QTextCursor *tc, const CursorPosition &p);
|
void setCursorPosition(QTextCursor *tc, const CursorPosition &p);
|
||||||
|
|
||||||
@@ -1596,56 +1601,38 @@ public:
|
|||||||
}
|
}
|
||||||
void moveRight(int n = 1) {
|
void moveRight(int n = 1) {
|
||||||
//dump("RIGHT 1");
|
//dump("RIGHT 1");
|
||||||
QTextCursor tc = cursor();
|
m_cursor.movePosition(Right, KeepAnchor, n);
|
||||||
tc.movePosition(Right, KeepAnchor, n);
|
|
||||||
setCursor(tc);
|
|
||||||
if (atEndOfLine())
|
if (atEndOfLine())
|
||||||
emit q->fold(1, false);
|
emit q->fold(1, false);
|
||||||
//dump("RIGHT 2");
|
//dump("RIGHT 2");
|
||||||
}
|
}
|
||||||
void moveLeft(int n = 1) {
|
void moveLeft(int n = 1) {
|
||||||
QTextCursor tc = cursor();
|
m_cursor.movePosition(Left, KeepAnchor, n);
|
||||||
tc.movePosition(Left, KeepAnchor, n);
|
|
||||||
setCursor(tc);
|
|
||||||
}
|
}
|
||||||
void setAnchor() {
|
void setAnchor() {
|
||||||
QTextCursor tc = cursor();
|
m_cursor.setPosition(position(), MoveAnchor);
|
||||||
tc.setPosition(tc.position(), MoveAnchor);
|
|
||||||
setCursor(tc);
|
|
||||||
}
|
}
|
||||||
void setAnchor(int position) {
|
void setAnchor(int position) {
|
||||||
QTextCursor tc = cursor();
|
m_cursor.setPosition(position, KeepAnchor);
|
||||||
tc.setPosition(tc.anchor(), MoveAnchor);
|
|
||||||
tc.setPosition(position, KeepAnchor);
|
|
||||||
setCursor(tc);
|
|
||||||
}
|
}
|
||||||
void setPosition(int position) {
|
void setPosition(int position) {
|
||||||
QTextCursor tc = cursor();
|
m_cursor.setPosition(position, KeepAnchor);
|
||||||
tc.setPosition(position, KeepAnchor);
|
|
||||||
setCursor(tc);
|
|
||||||
}
|
}
|
||||||
void setAnchorAndPosition(int anchor, int position) {
|
void setAnchorAndPosition(int anchor, int position) {
|
||||||
QTextCursor tc = cursor();
|
m_cursor.setPosition(anchor, MoveAnchor);
|
||||||
tc.setPosition(anchor, MoveAnchor);
|
m_cursor.setPosition(position, KeepAnchor);
|
||||||
tc.setPosition(position, KeepAnchor);
|
}
|
||||||
setCursor(tc);
|
// Set cursor in text editor widget.
|
||||||
|
void commitCursor() {
|
||||||
|
if (editor())
|
||||||
|
EDITOR(setTextCursor(m_cursor));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Workaround for occational crash when setting text cursor while in edit block.
|
// Values to save when starting FakeVim processing.
|
||||||
|
bool m_inFakeVim;
|
||||||
|
int m_firstVisibleLine;
|
||||||
QTextCursor m_cursor;
|
QTextCursor m_cursor;
|
||||||
|
|
||||||
QTextCursor cursor() const {
|
|
||||||
if (m_editBlockLevel > 0)
|
|
||||||
return m_cursor;
|
|
||||||
return EDITOR(textCursor());
|
|
||||||
}
|
|
||||||
|
|
||||||
void setCursor(const QTextCursor &tc) {
|
|
||||||
m_cursor = tc;
|
|
||||||
if (m_editBlockLevel == 0)
|
|
||||||
EDITOR(setTextCursor(tc));
|
|
||||||
}
|
|
||||||
|
|
||||||
bool moveToPreviousParagraph(int count) { return moveToNextParagraph(-count); }
|
bool moveToPreviousParagraph(int count) { return moveToNextParagraph(-count); }
|
||||||
bool moveToNextParagraph(int count);
|
bool moveToNextParagraph(int count);
|
||||||
|
|
||||||
@@ -1747,8 +1734,8 @@ public:
|
|||||||
|
|
||||||
bool m_breakEditBlock;
|
bool m_breakEditBlock;
|
||||||
|
|
||||||
int anchor() const { return cursor().anchor(); }
|
int anchor() const { return m_cursor.anchor(); }
|
||||||
int position() const { return cursor().position(); }
|
int position() const { return m_cursor.position(); }
|
||||||
|
|
||||||
struct TransformationData
|
struct TransformationData
|
||||||
{
|
{
|
||||||
@@ -2009,6 +1996,8 @@ void FakeVimHandler::Private::init()
|
|||||||
m_searchStartPosition = 0;
|
m_searchStartPosition = 0;
|
||||||
m_searchFromScreenLine = 0;
|
m_searchFromScreenLine = 0;
|
||||||
m_editBlockLevel = 0;
|
m_editBlockLevel = 0;
|
||||||
|
m_inFakeVim = false;
|
||||||
|
m_firstVisibleLine = 0;
|
||||||
|
|
||||||
setupCharClass();
|
setupCharClass();
|
||||||
}
|
}
|
||||||
@@ -2026,29 +2015,32 @@ void FakeVimHandler::Private::focus()
|
|||||||
|
|
||||||
void FakeVimHandler::Private::enterFakeVim()
|
void FakeVimHandler::Private::enterFakeVim()
|
||||||
{
|
{
|
||||||
|
QTC_ASSERT(!m_inFakeVim, qDebug() << "enterFakeVim() shouldn't be called recursively!");
|
||||||
|
|
||||||
|
m_cursor = EDITOR(textCursor());
|
||||||
|
m_inFakeVim = true;
|
||||||
|
|
||||||
|
updateFirstVisibleLine();
|
||||||
importSelection();
|
importSelection();
|
||||||
|
|
||||||
QTextCursor tc = cursor();
|
|
||||||
|
|
||||||
// Position changed externally, e.g. by code completion.
|
// Position changed externally, e.g. by code completion.
|
||||||
if (tc.position() != m_oldPosition) {
|
if (position() != m_oldPosition) {
|
||||||
// record external jump to different line
|
// record external jump to different line
|
||||||
if (m_oldPosition != -1 && lineForPosition(m_oldPosition) != lineForPosition(tc.position()))
|
if (m_oldPosition != -1 && lineForPosition(m_oldPosition) != lineForPosition(position()))
|
||||||
recordJump(m_oldPosition);
|
recordJump(m_oldPosition);
|
||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
if (atEndOfLine() && !isVisualMode() && !isInsertMode())
|
if (atEndOfLine() && !isVisualMode() && !isInsertMode())
|
||||||
moveLeft();
|
moveLeft();
|
||||||
}
|
}
|
||||||
|
|
||||||
tc.setVisualNavigation(true);
|
|
||||||
setCursor(tc);
|
|
||||||
|
|
||||||
if (m_fakeEnd)
|
if (m_fakeEnd)
|
||||||
moveRight();
|
moveRight();
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::leaveFakeVim()
|
void FakeVimHandler::Private::leaveFakeVim()
|
||||||
{
|
{
|
||||||
|
QTC_ASSERT(m_inFakeVim, qDebug() << "enterFakeVim() not called before leaveFakeVim()!");
|
||||||
|
|
||||||
// The command might have destroyed the editor.
|
// The command might have destroyed the editor.
|
||||||
if (m_textedit || m_plaintextedit) {
|
if (m_textedit || m_plaintextedit) {
|
||||||
// We fake vi-style end-of-line behaviour
|
// We fake vi-style end-of-line behaviour
|
||||||
@@ -2066,7 +2058,18 @@ void FakeVimHandler::Private::leaveFakeVim()
|
|||||||
|
|
||||||
exportSelection();
|
exportSelection();
|
||||||
updateCursorShape();
|
updateCursorShape();
|
||||||
|
commitCursor();
|
||||||
|
|
||||||
|
// Move cursor line to middle of screen if it's not visible.
|
||||||
|
const int line = cursorLine();
|
||||||
|
if (line < firstVisibleLine() || line >= firstVisibleLine() + linesOnScreen())
|
||||||
|
scrollToLine(qMax(0, line - linesOnScreen() / 2));
|
||||||
|
else
|
||||||
|
scrollToLine(firstVisibleLine());
|
||||||
|
updateScrollOffset();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m_inFakeVim = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FakeVimHandler::Private::wantsOverride(QKeyEvent *ev)
|
bool FakeVimHandler::Private::wantsOverride(QKeyEvent *ev)
|
||||||
@@ -2144,7 +2147,7 @@ EventResult FakeVimHandler::Private::handleEvent(QKeyEvent *ev)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Fake "End of line"
|
// Fake "End of line"
|
||||||
//m_tc = cursor();
|
//m_tc = m_cursor;
|
||||||
|
|
||||||
//bool hasBlock = false;
|
//bool hasBlock = false;
|
||||||
//emit q->requestHasBlockSelection(&hasBlock);
|
//emit q->requestHasBlockSelection(&hasBlock);
|
||||||
@@ -2257,7 +2260,7 @@ void FakeVimHandler::Private::exportSelection()
|
|||||||
setMark(QLatin1Char('>'), mark(QLatin1Char('>')).position);
|
setMark(QLatin1Char('>'), mark(QLatin1Char('>')).position);
|
||||||
} else {
|
} else {
|
||||||
if (m_subsubmode == SearchSubSubMode && !m_searchCursor.isNull())
|
if (m_subsubmode == SearchSubSubMode && !m_searchCursor.isNull())
|
||||||
setCursor(m_searchCursor);
|
m_cursor = m_searchCursor;
|
||||||
else
|
else
|
||||||
setAnchorAndPosition(pos, pos);
|
setAnchorAndPosition(pos, pos);
|
||||||
}
|
}
|
||||||
@@ -2339,7 +2342,7 @@ void FakeVimHandler::Private::importSelection()
|
|||||||
} else {
|
} else {
|
||||||
// Import new selection.
|
// Import new selection.
|
||||||
Qt::KeyboardModifiers mods = QApplication::keyboardModifiers();
|
Qt::KeyboardModifiers mods = QApplication::keyboardModifiers();
|
||||||
if (cursor().hasSelection()) {
|
if (m_cursor.hasSelection()) {
|
||||||
if (mods & HostOsInfo::controlModifier())
|
if (mods & HostOsInfo::controlModifier())
|
||||||
m_visualMode = VisualBlockMode;
|
m_visualMode = VisualBlockMode;
|
||||||
else if (mods & Qt::AltModifier)
|
else if (mods & Qt::AltModifier)
|
||||||
@@ -2587,8 +2590,7 @@ void FakeVimHandler::Private::stopIncrementalFind()
|
|||||||
{
|
{
|
||||||
if (g.findPending) {
|
if (g.findPending) {
|
||||||
g.findPending = false;
|
g.findPending = false;
|
||||||
QTextCursor tc = cursor();
|
setAnchorAndPosition(m_findStartPosition, m_cursor.selectionStart());
|
||||||
setAnchorAndPosition(m_findStartPosition, tc.selectionStart());
|
|
||||||
finishMovement();
|
finishMovement();
|
||||||
setAnchor();
|
setAnchor();
|
||||||
}
|
}
|
||||||
@@ -2621,7 +2623,7 @@ bool FakeVimHandler::Private::isInputCount(const Input &input) const
|
|||||||
bool FakeVimHandler::Private::atEmptyLine(const QTextCursor &tc) const
|
bool FakeVimHandler::Private::atEmptyLine(const QTextCursor &tc) const
|
||||||
{
|
{
|
||||||
if (tc.isNull())
|
if (tc.isNull())
|
||||||
return atEmptyLine(cursor());
|
return atEmptyLine(m_cursor);
|
||||||
return tc.block().length() == 1;
|
return tc.block().length() == 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2629,7 +2631,7 @@ bool FakeVimHandler::Private::atBoundary(bool end, bool simple, bool onlyWords,
|
|||||||
const QTextCursor &tc) const
|
const QTextCursor &tc) const
|
||||||
{
|
{
|
||||||
if (tc.isNull())
|
if (tc.isNull())
|
||||||
return atBoundary(end, simple, onlyWords, cursor());
|
return atBoundary(end, simple, onlyWords, m_cursor);
|
||||||
if (atEmptyLine(tc))
|
if (atEmptyLine(tc))
|
||||||
return true;
|
return true;
|
||||||
int pos = tc.position();
|
int pos = tc.position();
|
||||||
@@ -2674,12 +2676,13 @@ void FakeVimHandler::Private::pushUndoState(bool overwrite)
|
|||||||
|
|
||||||
int pos = position();
|
int pos = position();
|
||||||
if (!isInsertMode()) {
|
if (!isInsertMode()) {
|
||||||
if (isVisualMode() || m_submode == DeleteSubMode) {
|
if (isVisualMode() || m_submode == DeleteSubMode
|
||||||
|
|| (m_submode == ChangeSubMode && m_movetype != MoveLineWise)) {
|
||||||
pos = qMin(pos, anchor());
|
pos = qMin(pos, anchor());
|
||||||
if (isVisualLineMode())
|
if (isVisualLineMode())
|
||||||
pos = firstPositionInLine(lineForPosition(pos));
|
pos = firstPositionInLine(lineForPosition(pos));
|
||||||
} else if (m_movetype == MoveLineWise && hasConfig(ConfigStartOfLine)) {
|
} else if (m_movetype == MoveLineWise && hasConfig(ConfigStartOfLine)) {
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
if (m_submode == ShiftLeftSubMode || m_submode == ShiftRightSubMode
|
if (m_submode == ShiftLeftSubMode || m_submode == ShiftRightSubMode
|
||||||
|| m_submode == IndentSubMode) {
|
|| m_submode == IndentSubMode) {
|
||||||
pos = qMin(pos, anchor());
|
pos = qMin(pos, anchor());
|
||||||
@@ -2702,7 +2705,7 @@ void FakeVimHandler::Private::pushUndoState(bool overwrite)
|
|||||||
|
|
||||||
void FakeVimHandler::Private::moveDown(int n)
|
void FakeVimHandler::Private::moveDown(int n)
|
||||||
{
|
{
|
||||||
QTextBlock block = cursor().block();
|
QTextBlock block = m_cursor.block();
|
||||||
const int col = position() - block.position();
|
const int col = position() - block.position();
|
||||||
const int targetLine = qMax(0, lineNumber(block) + n);
|
const int targetLine = qMax(0, lineNumber(block) + n);
|
||||||
|
|
||||||
@@ -2711,8 +2714,6 @@ void FakeVimHandler::Private::moveDown(int n)
|
|||||||
block = document()->lastBlock();
|
block = document()->lastBlock();
|
||||||
setPosition(block.position() + qMax(0, qMin(block.length() - 2, col)));
|
setPosition(block.position() + qMax(0, qMin(block.length() - 2, col)));
|
||||||
moveToTargetColumn();
|
moveToTargetColumn();
|
||||||
|
|
||||||
updateScrollOffset();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::movePageDown(int count)
|
void FakeVimHandler::Private::movePageDown(int count)
|
||||||
@@ -2726,7 +2727,7 @@ void FakeVimHandler::Private::movePageDown(int count)
|
|||||||
if (count > 0)
|
if (count > 0)
|
||||||
scrollToLine(cursorLine());
|
scrollToLine(cursorLine());
|
||||||
else
|
else
|
||||||
scrollToLine(qMax(0, cursorLine() - screenLines));
|
scrollToLine(qMax(0, cursorLine() - screenLines + 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FakeVimHandler::Private::moveToNextParagraph(int count)
|
bool FakeVimHandler::Private::moveToNextParagraph(int count)
|
||||||
@@ -2891,7 +2892,7 @@ void FakeVimHandler::Private::finishMovement(const QString &dotCommandMovement)
|
|||||||
|
|
||||||
QString dotCommand;
|
QString dotCommand;
|
||||||
if (m_submode == ChangeSubMode) {
|
if (m_submode == ChangeSubMode) {
|
||||||
pushUndoState();
|
pushUndoState(false);
|
||||||
beginEditBlock();
|
beginEditBlock();
|
||||||
removeText(currentRange());
|
removeText(currentRange());
|
||||||
dotCommand = _("c");
|
dotCommand = _("c");
|
||||||
@@ -2902,7 +2903,7 @@ void FakeVimHandler::Private::finishMovement(const QString &dotCommandMovement)
|
|||||||
m_lastInsertion.clear();
|
m_lastInsertion.clear();
|
||||||
g.returnToMode = InsertMode;
|
g.returnToMode = InsertMode;
|
||||||
} else if (m_submode == DeleteSubMode) {
|
} else if (m_submode == DeleteSubMode) {
|
||||||
pushUndoState();
|
pushUndoState(false);
|
||||||
beginEditBlock();
|
beginEditBlock();
|
||||||
const int pos = position();
|
const int pos = position();
|
||||||
// Always delete something (e.g. 'dw' on an empty line deletes the line).
|
// Always delete something (e.g. 'dw' on an empty line deletes the line).
|
||||||
@@ -2919,7 +2920,7 @@ void FakeVimHandler::Private::finishMovement(const QString &dotCommandMovement)
|
|||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
endEditBlock();
|
endEditBlock();
|
||||||
} else if (m_submode == YankSubMode) {
|
} else if (m_submode == YankSubMode) {
|
||||||
const QTextCursor tc = cursor();
|
const QTextCursor tc = m_cursor;
|
||||||
if (m_rangemode == RangeBlockMode) {
|
if (m_rangemode == RangeBlockMode) {
|
||||||
const int pos1 = tc.block().position();
|
const int pos1 = tc.block().position();
|
||||||
const int pos2 = document()->findBlock(tc.anchor()).position();
|
const int pos2 = document()->findBlock(tc.anchor()).position();
|
||||||
@@ -2955,7 +2956,7 @@ void FakeVimHandler::Private::finishMovement(const QString &dotCommandMovement)
|
|||||||
|| m_submode == ShiftRightSubMode
|
|| m_submode == ShiftRightSubMode
|
||||||
|| m_submode == ShiftLeftSubMode) {
|
|| m_submode == ShiftLeftSubMode) {
|
||||||
recordJump();
|
recordJump();
|
||||||
pushUndoState();
|
pushUndoState(false);
|
||||||
if (m_submode == IndentSubMode) {
|
if (m_submode == IndentSubMode) {
|
||||||
indentSelectedText();
|
indentSelectedText();
|
||||||
dotCommand = _("=");
|
dotCommand = _("=");
|
||||||
@@ -3010,11 +3011,11 @@ void FakeVimHandler::Private::updateSelection()
|
|||||||
for (MarksIterator it(m_marks); it.hasNext(); ) {
|
for (MarksIterator it(m_marks); it.hasNext(); ) {
|
||||||
it.next();
|
it.next();
|
||||||
QTextEdit::ExtraSelection sel;
|
QTextEdit::ExtraSelection sel;
|
||||||
sel.cursor = cursor();
|
sel.cursor = m_cursor;
|
||||||
setCursorPosition(&sel.cursor, it.value().position);
|
setCursorPosition(&sel.cursor, it.value().position);
|
||||||
sel.cursor.setPosition(sel.cursor.position(), MoveAnchor);
|
sel.cursor.setPosition(sel.cursor.position(), MoveAnchor);
|
||||||
sel.cursor.movePosition(Right, KeepAnchor);
|
sel.cursor.movePosition(Right, KeepAnchor);
|
||||||
sel.format = cursor().blockCharFormat();
|
sel.format = m_cursor.blockCharFormat();
|
||||||
sel.format.setForeground(Qt::blue);
|
sel.format.setForeground(Qt::blue);
|
||||||
sel.format.setBackground(Qt::green);
|
sel.format.setBackground(Qt::green);
|
||||||
selections.append(sel);
|
selections.append(sel);
|
||||||
@@ -3181,7 +3182,7 @@ bool FakeVimHandler::Private::handleCommandSubSubMode(const Input &input)
|
|||||||
handled = false;
|
handled = false;
|
||||||
}
|
}
|
||||||
} else if (m_subsubmode == MarkSubSubMode) {
|
} else if (m_subsubmode == MarkSubSubMode) {
|
||||||
setMark(input.asChar(), CursorPosition(cursor()));
|
setMark(input.asChar(), CursorPosition(m_cursor));
|
||||||
m_subsubmode = NoSubSubMode;
|
m_subsubmode = NoSubSubMode;
|
||||||
} else if (m_subsubmode == BackTickSubSubMode
|
} else if (m_subsubmode == BackTickSubSubMode
|
||||||
|| m_subsubmode == TickSubSubMode) {
|
|| m_subsubmode == TickSubSubMode) {
|
||||||
@@ -3295,7 +3296,7 @@ bool FakeVimHandler::Private::handleMovement(const Input &input)
|
|||||||
} else if (input.is('#') || input.is('*')) {
|
} else if (input.is('#') || input.is('*')) {
|
||||||
// FIXME: That's not proper vim behaviour
|
// FIXME: That's not proper vim behaviour
|
||||||
QString needle;
|
QString needle;
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
tc.select(QTextCursor::WordUnderCursor);
|
tc.select(QTextCursor::WordUnderCursor);
|
||||||
needle = QRegExp::escape(tc.selection().toPlainText());
|
needle = QRegExp::escape(tc.selection().toPlainText());
|
||||||
if (!m_gflag)
|
if (!m_gflag)
|
||||||
@@ -3420,6 +3421,7 @@ bool FakeVimHandler::Private::handleMovement(const Input &input)
|
|||||||
setPosition(firstPositionInLine(n, false));
|
setPosition(firstPositionInLine(n, false));
|
||||||
}
|
}
|
||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
|
updateScrollOffset();
|
||||||
} else if (input.is('h') || input.isKey(Key_Left) || input.isBackspace()) {
|
} else if (input.is('h') || input.isKey(Key_Left) || input.isBackspace()) {
|
||||||
m_movetype = MoveExclusive;
|
m_movetype = MoveExclusive;
|
||||||
int n = qMin(count, leftDist());
|
int n = qMin(count, leftDist());
|
||||||
@@ -3429,8 +3431,8 @@ bool FakeVimHandler::Private::handleMovement(const Input &input)
|
|||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
movement = _("h");
|
movement = _("h");
|
||||||
} else if (input.is('H')) {
|
} else if (input.is('H')) {
|
||||||
setCursor(EDITOR(cursorForPosition(QPoint(0, 0))));
|
const CursorPosition pos(lineToBlockNumber(lineOnTop(count)), 0);
|
||||||
moveDown(qMax(count - 1, 0));
|
setCursorPosition(&m_cursor, pos);
|
||||||
handleStartOfLine();
|
handleStartOfLine();
|
||||||
} else if (input.is('j') || input.isKey(Key_Down)
|
} else if (input.is('j') || input.isKey(Key_Down)
|
||||||
|| input.isControl('j') || input.isControl('n')) {
|
|| input.isControl('j') || input.isControl('n')) {
|
||||||
@@ -3449,28 +3451,26 @@ bool FakeVimHandler::Private::handleMovement(const Input &input)
|
|||||||
if (pastEnd && isVisualMode())
|
if (pastEnd && isVisualMode())
|
||||||
m_visualTargetColumn = -1;
|
m_visualTargetColumn = -1;
|
||||||
} else if (input.is('L')) {
|
} else if (input.is('L')) {
|
||||||
QTextCursor tc = EDITOR(cursorForPosition(QPoint(0, EDITOR(height()))));
|
const CursorPosition pos(lineToBlockNumber(lineOnBottom(count)), 0);
|
||||||
setCursor(tc);
|
setCursorPosition(&m_cursor, pos);
|
||||||
moveUp(qMax(count, 1));
|
|
||||||
handleStartOfLine();
|
handleStartOfLine();
|
||||||
} else if (m_gflag && input.is('m')) {
|
} else if (m_gflag && input.is('m')) {
|
||||||
moveToStartOfLine();
|
moveToStartOfLine();
|
||||||
moveRight(qMin(columnsOnScreen() / 2, rightDist()) - 1);
|
moveRight(qMin(columnsOnScreen() / 2, rightDist()) - 1);
|
||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
} else if (input.is('M')) {
|
} else if (input.is('M')) {
|
||||||
QTextCursor tc = EDITOR(cursorForPosition(QPoint(0, EDITOR(height()) / 2)));
|
m_cursor = EDITOR(cursorForPosition(QPoint(0, EDITOR(height()) / 2)));
|
||||||
setCursor(tc);
|
|
||||||
handleStartOfLine();
|
handleStartOfLine();
|
||||||
} else if (input.is('n') || input.is('N')) {
|
} else if (input.is('n') || input.is('N')) {
|
||||||
if (hasConfig(ConfigUseCoreSearch)) {
|
if (hasConfig(ConfigUseCoreSearch)) {
|
||||||
bool forward = (input.is('n')) ? g.lastSearchForward : !g.lastSearchForward;
|
bool forward = (input.is('n')) ? g.lastSearchForward : !g.lastSearchForward;
|
||||||
int pos = position();
|
int pos = position();
|
||||||
emit q->findNextRequested(!forward);
|
emit q->findNextRequested(!forward);
|
||||||
if (forward && pos == cursor().selectionStart()) {
|
if (forward && pos == m_cursor.selectionStart()) {
|
||||||
// if cursor is already positioned at the start of a find result, this is returned
|
// if cursor is already positioned at the start of a find result, this is returned
|
||||||
emit q->findNextRequested(false);
|
emit q->findNextRequested(false);
|
||||||
}
|
}
|
||||||
setPosition(cursor().selectionStart());
|
setPosition(m_cursor.selectionStart());
|
||||||
} else {
|
} else {
|
||||||
searchNext(input.is('n'));
|
searchNext(input.is('n'));
|
||||||
}
|
}
|
||||||
@@ -3647,7 +3647,7 @@ bool FakeVimHandler::Private::handleNoSubMode(const Input &input)
|
|||||||
// << input;
|
// << input;
|
||||||
QString savedCommand = g.dotCommand;
|
QString savedCommand = g.dotCommand;
|
||||||
g.dotCommand.clear();
|
g.dotCommand.clear();
|
||||||
beginEditBlock();
|
beginLargeEditBlock();
|
||||||
replay(savedCommand);
|
replay(savedCommand);
|
||||||
endEditBlock();
|
endEditBlock();
|
||||||
resetCommandMode();
|
resetCommandMode();
|
||||||
@@ -3765,7 +3765,8 @@ bool FakeVimHandler::Private::handleNoSubMode(const Input &input)
|
|||||||
removeText(currentRange());
|
removeText(currentRange());
|
||||||
setPosition(qMin(position(), anchor()));
|
setPosition(qMin(position(), anchor()));
|
||||||
} else if (input.isControl('d')) {
|
} else if (input.isControl('d')) {
|
||||||
int sline = cursorLineOnScreen();
|
const int scrollOffset = windowScrollOffset();
|
||||||
|
int sline = cursorLine() < scrollOffset ? scrollOffset : cursorLineOnScreen();
|
||||||
// FIXME: this should use the "scroll" option, and "count"
|
// FIXME: this should use the "scroll" option, and "count"
|
||||||
moveDown(linesOnScreen() / 2);
|
moveDown(linesOnScreen() / 2);
|
||||||
handleStartOfLine();
|
handleStartOfLine();
|
||||||
@@ -4382,11 +4383,11 @@ EventResult FakeVimHandler::Private::handleInsertMode(const Input &input)
|
|||||||
pos.column = qMax(lastPosition.column, lastAnchor.column) + 1;
|
pos.column = qMax(lastPosition.column, lastAnchor.column) + 1;
|
||||||
while (pos.line < lastPosition.line) {
|
while (pos.line < lastPosition.line) {
|
||||||
++pos.line;
|
++pos.line;
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
setCursorPosition(&tc, pos);
|
setCursorPosition(&tc, pos);
|
||||||
if (pos.line != tc.blockNumber())
|
if (pos.line != tc.blockNumber())
|
||||||
break;
|
break;
|
||||||
setCursor(tc);
|
m_cursor = tc;
|
||||||
if (tc.positionInBlock() == pos.column)
|
if (tc.positionInBlock() == pos.column)
|
||||||
replay(text.repeated(repeat));
|
replay(text.repeated(repeat));
|
||||||
}
|
}
|
||||||
@@ -4417,10 +4418,10 @@ EventResult FakeVimHandler::Private::handleInsertMode(const Input &input)
|
|||||||
m_ctrlVActive = true;
|
m_ctrlVActive = true;
|
||||||
insert = _("<C-V>");
|
insert = _("<C-V>");
|
||||||
} else if (input.isControl('w')) {
|
} else if (input.isControl('w')) {
|
||||||
const int blockNumber = cursor().blockNumber();
|
const int blockNumber = m_cursor.blockNumber();
|
||||||
const int endPos = position();
|
const int endPos = position();
|
||||||
moveToNextWordStart(count(), false, false);
|
moveToNextWordStart(count(), false, false);
|
||||||
if (blockNumber != cursor().blockNumber())
|
if (blockNumber != m_cursor.blockNumber())
|
||||||
moveToEndOfLine();
|
moveToEndOfLine();
|
||||||
const int beginPos = position();
|
const int beginPos = position();
|
||||||
Range range(beginPos, endPos, RangeCharMode);
|
Range range(beginPos, endPos, RangeCharMode);
|
||||||
@@ -4488,7 +4489,7 @@ EventResult FakeVimHandler::Private::handleInsertMode(const Input &input)
|
|||||||
moveRight(prefix.size());
|
moveRight(prefix.size());
|
||||||
} else {
|
} else {
|
||||||
setAnchor();
|
setAnchor();
|
||||||
cursor().deletePreviousChar();
|
m_cursor.deletePreviousChar();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
insert = _("<BS>");
|
insert = _("<BS>");
|
||||||
@@ -4497,7 +4498,7 @@ EventResult FakeVimHandler::Private::handleInsertMode(const Input &input)
|
|||||||
} else if (input.isKey(Key_Delete)) {
|
} else if (input.isKey(Key_Delete)) {
|
||||||
if (!handleInsertInEditor(input, &insert)) {
|
if (!handleInsertInEditor(input, &insert)) {
|
||||||
joinPreviousEditBlock();
|
joinPreviousEditBlock();
|
||||||
cursor().deleteChar();
|
m_cursor.deleteChar();
|
||||||
insert = _("<DELETE>");
|
insert = _("<DELETE>");
|
||||||
endEditBlock();
|
endEditBlock();
|
||||||
}
|
}
|
||||||
@@ -4541,10 +4542,10 @@ EventResult FakeVimHandler::Private::handleInsertMode(const Input &input)
|
|||||||
//} else if (key >= control('a') && key <= control('z')) {
|
//} else if (key >= control('a') && key <= control('z')) {
|
||||||
// // ignore these
|
// // ignore these
|
||||||
} else if (input.isControl('p') || input.isControl('n')) {
|
} else if (input.isControl('p') || input.isControl('n')) {
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
moveToNextWordStart(count(), false, false);
|
moveToNextWordStart(count(), false, false);
|
||||||
QString str = selectText(Range(position(), tc.position()));
|
QString str = selectText(Range(position(), tc.position()));
|
||||||
setCursor(tc);
|
m_cursor = tc;
|
||||||
emit q->simpleCompletionRequested(str, input.isControl('n'));
|
emit q->simpleCompletionRequested(str, input.isControl('n'));
|
||||||
if (input.isControl('p'))
|
if (input.isControl('p'))
|
||||||
insert = _("<C-P>");
|
insert = _("<C-P>");
|
||||||
@@ -4997,7 +4998,7 @@ bool FakeVimHandler::Private::handleExSubstituteCommand(const ExCommand &cmd)
|
|||||||
lastBlock = block;
|
lastBlock = block;
|
||||||
beginEditBlock();
|
beginEditBlock();
|
||||||
}
|
}
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
const int pos = block.position();
|
const int pos = block.position();
|
||||||
const int anchor = pos + block.length() - 1;
|
const int anchor = pos + block.length() - 1;
|
||||||
tc.setPosition(anchor);
|
tc.setPosition(anchor);
|
||||||
@@ -5779,7 +5780,7 @@ void FakeVimHandler::Private::search(const SearchData &sd, bool showMessages)
|
|||||||
|
|
||||||
QTextCursor tc = search(sd, m_searchStartPosition, count(), showMessages);
|
QTextCursor tc = search(sd, m_searchStartPosition, count(), showMessages);
|
||||||
if (tc.isNull()) {
|
if (tc.isNull()) {
|
||||||
tc = cursor();
|
tc = m_cursor;
|
||||||
tc.setPosition(m_searchStartPosition);
|
tc.setPosition(m_searchStartPosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -5796,7 +5797,7 @@ void FakeVimHandler::Private::search(const SearchData &sd, bool showMessages)
|
|||||||
if (oldLine != cursorLine() - cursorLineOnScreen())
|
if (oldLine != cursorLine() - cursorLineOnScreen())
|
||||||
scrollToLine(cursorLine() - linesOnScreen() / 2);
|
scrollToLine(cursorLine() - linesOnScreen() / 2);
|
||||||
|
|
||||||
m_searchCursor = cursor();
|
m_searchCursor = m_cursor;
|
||||||
|
|
||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
}
|
}
|
||||||
@@ -5824,9 +5825,7 @@ void FakeVimHandler::Private::highlightMatches(const QString &needle)
|
|||||||
|
|
||||||
void FakeVimHandler::Private::moveToFirstNonBlankOnLine()
|
void FakeVimHandler::Private::moveToFirstNonBlankOnLine()
|
||||||
{
|
{
|
||||||
QTextCursor tc2 = cursor();
|
moveToFirstNonBlankOnLine(&m_cursor);
|
||||||
moveToFirstNonBlankOnLine(&tc2);
|
|
||||||
setPosition(tc2.position());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::moveToFirstNonBlankOnLine(QTextCursor *tc)
|
void FakeVimHandler::Private::moveToFirstNonBlankOnLine(QTextCursor *tc)
|
||||||
@@ -5835,11 +5834,11 @@ void FakeVimHandler::Private::moveToFirstNonBlankOnLine(QTextCursor *tc)
|
|||||||
int firstPos = tc->block().position();
|
int firstPos = tc->block().position();
|
||||||
for (int i = firstPos, n = firstPos + block().length(); i < n; ++i) {
|
for (int i = firstPos, n = firstPos + block().length(); i < n; ++i) {
|
||||||
if (!doc->characterAt(i).isSpace() || i == n - 1) {
|
if (!doc->characterAt(i).isSpace() || i == n - 1) {
|
||||||
tc->setPosition(i);
|
tc->setPosition(i, KeepAnchor);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
tc->setPosition(block().position());
|
tc->setPosition(block().position(), KeepAnchor);
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::indentSelectedText(QChar typedChar)
|
void FakeVimHandler::Private::indentSelectedText(QChar typedChar)
|
||||||
@@ -5897,7 +5896,7 @@ void FakeVimHandler::Private::shiftRegionRight(int repeat)
|
|||||||
QTextBlock block = document()->findBlockByLineNumber(beginLine - 1);
|
QTextBlock block = document()->findBlockByLineNumber(beginLine - 1);
|
||||||
while (block.isValid() && lineNumber(block) <= endLine) {
|
while (block.isValid() && lineNumber(block) <= endLine) {
|
||||||
const Column col = indentation(block.text());
|
const Column col = indentation(block.text());
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
tc.setPosition(block.position());
|
tc.setPosition(block.position());
|
||||||
if (col.physical > 0)
|
if (col.physical > 0)
|
||||||
tc.setPosition(tc.position() + col.physical, KeepAnchor);
|
tc.setPosition(tc.position() + col.physical, KeepAnchor);
|
||||||
@@ -6042,7 +6041,7 @@ void FakeVimHandler::Private::moveToBoundary(bool simple, bool forward)
|
|||||||
c = doc->characterAt(tc.position());
|
c = doc->characterAt(tc.position());
|
||||||
int thisClass = charClass(c, simple);
|
int thisClass = charClass(c, simple);
|
||||||
if (thisClass != lastClass || (forward ? tc.atBlockEnd() : tc.atBlockStart())) {
|
if (thisClass != lastClass || (forward ? tc.atBlockEnd() : tc.atBlockStart())) {
|
||||||
if (tc != cursor())
|
if (tc != m_cursor)
|
||||||
tc.movePosition(forward ? Left : Right);
|
tc.movePosition(forward ? Left : Right);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -6162,7 +6161,7 @@ void FakeVimHandler::Private::moveToMatchingParanthesis()
|
|||||||
bool forward = false;
|
bool forward = false;
|
||||||
|
|
||||||
const int anc = anchor();
|
const int anc = anchor();
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
emit q->moveToMatchingParenthesis(&moved, &forward, &tc);
|
emit q->moveToMatchingParenthesis(&moved, &forward, &tc);
|
||||||
if (moved && forward)
|
if (moved && forward)
|
||||||
tc.movePosition(Left, KeepAnchor, 1);
|
tc.movePosition(Left, KeepAnchor, 1);
|
||||||
@@ -6265,39 +6264,62 @@ Column FakeVimHandler::Private::cursorColumn() const
|
|||||||
|
|
||||||
int FakeVimHandler::Private::linesInDocument() const
|
int FakeVimHandler::Private::linesInDocument() const
|
||||||
{
|
{
|
||||||
if (cursor().isNull())
|
if (m_cursor.isNull())
|
||||||
return 0;
|
return 0;
|
||||||
return document()->blockCount();
|
return document()->blockCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::setScrollBarValue(int line)
|
void FakeVimHandler::Private::scrollToLine(int line)
|
||||||
{
|
{
|
||||||
QScrollBar *scrollBar = EDITOR(verticalScrollBar());
|
QScrollBar *scrollBar = EDITOR(verticalScrollBar());
|
||||||
|
|
||||||
// Convert line number to scroll bar value.
|
// Convert line number to scroll bar value.
|
||||||
const int maxValue = scrollBar->maximum();
|
const int maxValue = scrollBar->maximum();
|
||||||
const int scrollLines = qMax(1, linesInDocument() - linesOnScreen());
|
const int scrollLines = qMax(1, linesInDocument() - linesOnScreen() + 1);
|
||||||
const int value = maxValue >= scrollLines ? line * maxValue / scrollLines : line;
|
const int value = maxValue >= scrollLines ? line * maxValue / scrollLines : line;
|
||||||
|
|
||||||
scrollBar->setValue(value);
|
scrollBar->setValue(value);
|
||||||
|
|
||||||
|
updateFirstVisibleLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::scrollToLine(int line)
|
void FakeVimHandler::Private::updateFirstVisibleLine()
|
||||||
{
|
{
|
||||||
setScrollBarValue(line);
|
QScrollBar *scrollBar = EDITOR(verticalScrollBar());
|
||||||
updateScrollOffset();
|
|
||||||
|
// Convert scroll bar value to line number.
|
||||||
|
const int maxValue = qMax(1, scrollBar->maximum());
|
||||||
|
const int scrollLines = qMax(1, linesInDocument() - linesOnScreen() + 1);
|
||||||
|
const int value = scrollBar->value();
|
||||||
|
|
||||||
|
m_firstVisibleLine = maxValue >= scrollLines ? value * scrollLines / maxValue : value;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FakeVimHandler::Private::firstVisibleLine() const
|
int FakeVimHandler::Private::firstVisibleLine() const
|
||||||
{
|
{
|
||||||
QScrollBar *scrollBar = EDITOR(verticalScrollBar());
|
return m_firstVisibleLine;
|
||||||
if (0 && scrollBar->value() != cursorLine() - cursorLineOnScreen()) {
|
}
|
||||||
qDebug() << "SCROLLBAR: " << scrollBar->value()
|
|
||||||
<< "CURSORLINE IN DOC" << cursorLine()
|
int FakeVimHandler::Private::lastVisibleLine() const
|
||||||
<< "CURSORLINE ON SCREEN" << cursorLineOnScreen();
|
{
|
||||||
}
|
const int blockNumber = lineToBlockNumber(m_firstVisibleLine + linesOnScreen());
|
||||||
//return scrollBar->value();
|
const QTextBlock block = document()->findBlockByNumber(blockNumber);
|
||||||
return cursorLine() - cursorLineOnScreen();
|
return block.isValid() ? block.firstLineNumber() : document()->lastBlock().firstLineNumber();
|
||||||
|
}
|
||||||
|
|
||||||
|
int FakeVimHandler::Private::lineOnTop(int count) const
|
||||||
|
{
|
||||||
|
const int scrollOffset = qMax(count - 1, windowScrollOffset());
|
||||||
|
const int line = firstVisibleLine();
|
||||||
|
return line == 0 ? count - 1 : scrollOffset + line;
|
||||||
|
}
|
||||||
|
|
||||||
|
int FakeVimHandler::Private::lineOnBottom(int count) const
|
||||||
|
{
|
||||||
|
const int scrollOffset = qMax(count - 1, windowScrollOffset());
|
||||||
|
const int line = lastVisibleLine();
|
||||||
|
return line >= document()->lastBlock().firstLineNumber() ? line - count + 1
|
||||||
|
: line - scrollOffset - 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::scrollUp(int count)
|
void FakeVimHandler::Private::scrollUp(int count)
|
||||||
@@ -6307,18 +6329,11 @@ void FakeVimHandler::Private::scrollUp(int count)
|
|||||||
|
|
||||||
void FakeVimHandler::Private::updateScrollOffset()
|
void FakeVimHandler::Private::updateScrollOffset()
|
||||||
{
|
{
|
||||||
// Precision of scroll offset depends on singleStep property of vertical scroll bar.
|
|
||||||
const int offset = windowScrollOffset();
|
|
||||||
const int line = cursorLine();
|
const int line = cursorLine();
|
||||||
const int scrollLine = firstVisibleLine();
|
if (line < lineOnTop())
|
||||||
int d = line - scrollLine;
|
scrollToLine(qMax(0, line - windowScrollOffset()));
|
||||||
if (d <= offset) {
|
else if (line > lineOnBottom())
|
||||||
setScrollBarValue(scrollLine - offset + d);
|
scrollToLine(line - linesOnScreen() + windowScrollOffset() + 1);
|
||||||
} else {
|
|
||||||
d = linesOnScreen() - d;
|
|
||||||
if (d <= offset)
|
|
||||||
setScrollBarValue(scrollLine + offset - d + 1);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::alignViewportToCursor(AlignmentFlag align, int line,
|
void FakeVimHandler::Private::alignViewportToCursor(AlignmentFlag align, int line,
|
||||||
@@ -6337,16 +6352,18 @@ void FakeVimHandler::Private::alignViewportToCursor(AlignmentFlag align, int lin
|
|||||||
scrollUp(linesOnScreen() - cursorLineOnScreen());
|
scrollUp(linesOnScreen() - cursorLineOnScreen());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int FakeVimHandler::Private::lineToBlockNumber(int line) const
|
||||||
|
{
|
||||||
|
return document()->findBlockByLineNumber(line).blockNumber();
|
||||||
|
}
|
||||||
|
|
||||||
void FakeVimHandler::Private::setCursorPosition(const CursorPosition &p)
|
void FakeVimHandler::Private::setCursorPosition(const CursorPosition &p)
|
||||||
{
|
{
|
||||||
const int firstLine = firstVisibleLine();
|
const int firstLine = firstVisibleLine();
|
||||||
const int firstBlock = document()->findBlockByLineNumber(firstLine).blockNumber();
|
const int firstBlock = lineToBlockNumber(firstLine);
|
||||||
const int lastBlock =
|
const int lastBlock = lineToBlockNumber(firstLine + linesOnScreen() - 2);
|
||||||
document()->findBlockByLineNumber(firstLine + linesOnScreen() - 2).blockNumber();
|
|
||||||
bool isLineVisible = firstBlock <= p.line && p.line <= lastBlock;
|
bool isLineVisible = firstBlock <= p.line && p.line <= lastBlock;
|
||||||
QTextCursor tc = cursor();
|
setCursorPosition(&m_cursor, p);
|
||||||
setCursorPosition(&tc, p);
|
|
||||||
setCursor(tc);
|
|
||||||
if (!isLineVisible)
|
if (!isLineVisible)
|
||||||
alignViewportToCursor(Qt::AlignVCenter);
|
alignViewportToCursor(Qt::AlignVCenter);
|
||||||
}
|
}
|
||||||
@@ -6426,7 +6443,7 @@ void FakeVimHandler::Private::yankText(const Range &range, int reg)
|
|||||||
void FakeVimHandler::Private::transformText(const Range &range,
|
void FakeVimHandler::Private::transformText(const Range &range,
|
||||||
Transformation transformFunc, const QVariant &extra)
|
Transformation transformFunc, const QVariant &extra)
|
||||||
{
|
{
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
int posAfter = range.beginPos;
|
int posAfter = range.beginPos;
|
||||||
switch (range.rangemode) {
|
switch (range.rangemode) {
|
||||||
case RangeCharMode: {
|
case RangeCharMode: {
|
||||||
@@ -6505,9 +6522,8 @@ void FakeVimHandler::Private::transformText(const Range &range,
|
|||||||
void FakeVimHandler::Private::insertText(QTextCursor &tc, const QString &text)
|
void FakeVimHandler::Private::insertText(QTextCursor &tc, const QString &text)
|
||||||
{
|
{
|
||||||
if (hasConfig(ConfigPassKeys)) {
|
if (hasConfig(ConfigPassKeys)) {
|
||||||
QTextCursor oldTc = cursor();
|
QTextCursor oldTc = m_cursor;
|
||||||
setCursor(tc);
|
m_cursor = tc;
|
||||||
EDITOR(setOverwriteMode(false));
|
|
||||||
|
|
||||||
if (tc.hasSelection() && text.isEmpty()) {
|
if (tc.hasSelection() && text.isEmpty()) {
|
||||||
QKeyEvent event(QEvent::KeyPress, Qt::Key_Delete, Qt::NoModifier, QString());
|
QKeyEvent event(QEvent::KeyPress, Qt::Key_Delete, Qt::NoModifier, QString());
|
||||||
@@ -6520,7 +6536,7 @@ void FakeVimHandler::Private::insertText(QTextCursor &tc, const QString &text)
|
|||||||
}
|
}
|
||||||
|
|
||||||
updateCursorShape();
|
updateCursorShape();
|
||||||
setCursor(oldTc);
|
m_cursor = oldTc;
|
||||||
} else {
|
} else {
|
||||||
tc.insertText(text);
|
tc.insertText(text);
|
||||||
}
|
}
|
||||||
@@ -6531,7 +6547,7 @@ void FakeVimHandler::Private::insertText(const Register ®)
|
|||||||
QTC_ASSERT(reg.rangemode == RangeCharMode,
|
QTC_ASSERT(reg.rangemode == RangeCharMode,
|
||||||
qDebug() << "WRONG INSERT MODE: " << reg.rangemode; return);
|
qDebug() << "WRONG INSERT MODE: " << reg.rangemode; return);
|
||||||
setAnchor();
|
setAnchor();
|
||||||
cursor().insertText(reg.contents);
|
m_cursor.insertText(reg.contents);
|
||||||
//dump("AFTER INSERT");
|
//dump("AFTER INSERT");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -6649,7 +6665,7 @@ void FakeVimHandler::Private::pasteText(bool afterCursor)
|
|||||||
}
|
}
|
||||||
case RangeLineMode:
|
case RangeLineMode:
|
||||||
case RangeLineModeExclusive: {
|
case RangeLineModeExclusive: {
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
if (visualCharMode)
|
if (visualCharMode)
|
||||||
tc.insertBlock();
|
tc.insertBlock();
|
||||||
else
|
else
|
||||||
@@ -6678,7 +6694,7 @@ void FakeVimHandler::Private::pasteText(bool afterCursor)
|
|||||||
const int pos = position();
|
const int pos = position();
|
||||||
if (pasteAfter && rightDist() > 0)
|
if (pasteAfter && rightDist() > 0)
|
||||||
moveRight();
|
moveRight();
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
const int col = tc.columnNumber();
|
const int col = tc.columnNumber();
|
||||||
QTextBlock block = tc.block();
|
QTextBlock block = tc.block();
|
||||||
const QStringList lines = text.split(QLatin1Char('\n'));
|
const QStringList lines = text.split(QLatin1Char('\n'));
|
||||||
@@ -6719,7 +6735,7 @@ void FakeVimHandler::Private::pasteText(bool afterCursor)
|
|||||||
void FakeVimHandler::Private::joinLines(int count, bool preserveSpace)
|
void FakeVimHandler::Private::joinLines(int count, bool preserveSpace)
|
||||||
{
|
{
|
||||||
int pos = position();
|
int pos = position();
|
||||||
const int blockNumber = cursor().blockNumber();
|
const int blockNumber = m_cursor.blockNumber();
|
||||||
for (int i = qMax(count - 2, 0); i >= 0 && blockNumber < document()->blockCount(); --i) {
|
for (int i = qMax(count - 2, 0); i >= 0 && blockNumber < document()->blockCount(); --i) {
|
||||||
moveBehindEndOfLine();
|
moveBehindEndOfLine();
|
||||||
pos = position();
|
pos = position();
|
||||||
@@ -6730,7 +6746,7 @@ void FakeVimHandler::Private::joinLines(int count, bool preserveSpace)
|
|||||||
} else {
|
} else {
|
||||||
while (characterAtCursor() == QLatin1Char(' ') || characterAtCursor() == QLatin1Char('\t'))
|
while (characterAtCursor() == QLatin1Char(' ') || characterAtCursor() == QLatin1Char('\t'))
|
||||||
moveRight();
|
moveRight();
|
||||||
cursor().insertText(QString(QLatin1Char(' ')));
|
m_cursor.insertText(QString(QLatin1Char(' ')));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
setPosition(pos);
|
setPosition(pos);
|
||||||
@@ -6760,6 +6776,7 @@ bool FakeVimHandler::Private::handleInsertInEditor(const Input &input, QString *
|
|||||||
|
|
||||||
QKeyEvent event(QEvent::KeyPress, input.key(),
|
QKeyEvent event(QEvent::KeyPress, input.key(),
|
||||||
static_cast<Qt::KeyboardModifiers>(input.modifiers()), input.text());
|
static_cast<Qt::KeyboardModifiers>(input.modifiers()), input.text());
|
||||||
|
setAnchor();
|
||||||
if (!passEventToEditor(event))
|
if (!passEventToEditor(event))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@@ -6777,14 +6794,14 @@ bool FakeVimHandler::Private::passEventToEditor(QEvent &event)
|
|||||||
{
|
{
|
||||||
removeEventFilter();
|
removeEventFilter();
|
||||||
|
|
||||||
QTextCursor tc = m_cursor;
|
commitCursor();
|
||||||
EDITOR(setTextCursor(tc));
|
EDITOR(setOverwriteMode(false));
|
||||||
bool accepted = QApplication::sendEvent(editor(), &event);
|
bool accepted = QApplication::sendEvent(editor(), &event);
|
||||||
|
|
||||||
installEventFilter();
|
installEventFilter();
|
||||||
|
|
||||||
if (accepted)
|
if (accepted)
|
||||||
setPosition(EDITOR(textCursor()).position());
|
m_cursor = EDITOR(textCursor());
|
||||||
|
|
||||||
return accepted;
|
return accepted;
|
||||||
}
|
}
|
||||||
@@ -6811,7 +6828,7 @@ QString FakeVimHandler::Private::guessInsertCommand(int pos1, int pos2, int len1
|
|||||||
} else if (len1 < len2) {
|
} else if (len1 < len2) {
|
||||||
// Text inserted.
|
// Text inserted.
|
||||||
if (pos1 < pos2) {
|
if (pos1 < pos2) {
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
tc.setPosition(pos1);
|
tc.setPosition(pos1);
|
||||||
tc.setPosition(pos2, KeepAnchor);
|
tc.setPosition(pos2, KeepAnchor);
|
||||||
insert = QString(tc.selectedText()).replace(_("<"), _("<LT>"));
|
insert = QString(tc.selectedText()).replace(_("<"), _("<LT>"));
|
||||||
@@ -6861,7 +6878,7 @@ QString FakeVimHandler::Private::lineContents(int line) const
|
|||||||
void FakeVimHandler::Private::setLineContents(int line, const QString &contents)
|
void FakeVimHandler::Private::setLineContents(int line, const QString &contents)
|
||||||
{
|
{
|
||||||
QTextBlock block = document()->findBlockByLineNumber(line - 1);
|
QTextBlock block = document()->findBlockByLineNumber(line - 1);
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
const int begin = block.position();
|
const int begin = block.position();
|
||||||
const int len = block.length();
|
const int len = block.length();
|
||||||
tc.setPosition(begin);
|
tc.setPosition(begin);
|
||||||
@@ -6876,7 +6893,7 @@ int FakeVimHandler::Private::blockBoundary(const QString &left,
|
|||||||
const QString &end = closing ? right : left;
|
const QString &end = closing ? right : left;
|
||||||
|
|
||||||
// shift cursor if it is already on opening/closing string
|
// shift cursor if it is already on opening/closing string
|
||||||
QTextCursor tc1 = cursor();
|
QTextCursor tc1 = m_cursor;
|
||||||
int pos = tc1.position();
|
int pos = tc1.position();
|
||||||
int max = document()->characterCount();
|
int max = document()->characterCount();
|
||||||
int sz = left.size();
|
int sz = left.size();
|
||||||
@@ -6899,7 +6916,7 @@ int FakeVimHandler::Private::blockBoundary(const QString &left,
|
|||||||
// - on closing string:
|
// - on closing string:
|
||||||
tc1.setPosition(from + i);
|
tc1.setPosition(from + i);
|
||||||
} else {
|
} else {
|
||||||
tc1 = cursor();
|
tc1 = m_cursor;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -7035,7 +7052,7 @@ void FakeVimHandler::Private::joinPreviousEditBlock()
|
|||||||
UNDO_DEBUG("JOIN");
|
UNDO_DEBUG("JOIN");
|
||||||
if (m_breakEditBlock && m_editBlockLevel == 0) {
|
if (m_breakEditBlock && m_editBlockLevel == 0) {
|
||||||
beginEditBlock();
|
beginEditBlock();
|
||||||
QTextCursor tc(cursor());
|
QTextCursor tc(m_cursor);
|
||||||
tc.setPosition(tc.position());
|
tc.setPosition(tc.position());
|
||||||
tc.beginEditBlock();
|
tc.beginEditBlock();
|
||||||
tc.insertText(_("X"));
|
tc.insertText(_("X"));
|
||||||
@@ -7051,9 +7068,6 @@ void FakeVimHandler::Private::joinPreviousEditBlock()
|
|||||||
void FakeVimHandler::Private::beginEditBlock(bool largeEditBlock)
|
void FakeVimHandler::Private::beginEditBlock(bool largeEditBlock)
|
||||||
{
|
{
|
||||||
UNDO_DEBUG("BEGIN EDIT BLOCK");
|
UNDO_DEBUG("BEGIN EDIT BLOCK");
|
||||||
if (m_editBlockLevel == 0)
|
|
||||||
m_cursor = cursor();
|
|
||||||
|
|
||||||
if (!largeEditBlock && !m_undoState.isValid())
|
if (!largeEditBlock && !m_undoState.isValid())
|
||||||
pushUndoState(false);
|
pushUndoState(false);
|
||||||
++m_editBlockLevel;
|
++m_editBlockLevel;
|
||||||
@@ -7066,14 +7080,9 @@ void FakeVimHandler::Private::endEditBlock()
|
|||||||
QTC_ASSERT(m_editBlockLevel > 0,
|
QTC_ASSERT(m_editBlockLevel > 0,
|
||||||
qDebug() << "beginEditBlock() not called before endEditBlock()!"; return);
|
qDebug() << "beginEditBlock() not called before endEditBlock()!"; return);
|
||||||
--m_editBlockLevel;
|
--m_editBlockLevel;
|
||||||
if (m_editBlockLevel == 0) {
|
if (m_editBlockLevel == 0 && m_undoState.isValid() && m_undoState.revisions > 0) {
|
||||||
setCursor(m_cursor);
|
m_undo.push(m_undoState);
|
||||||
if (m_undoState.isValid()) {
|
m_undoState = State();
|
||||||
if (m_undoState.revisions > 0) {
|
|
||||||
m_undo.push(m_undoState);
|
|
||||||
m_undoState = State();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -7118,9 +7127,7 @@ void FakeVimHandler::Private::undoRedo(bool undo)
|
|||||||
|
|
||||||
State state = !stack.empty() ? stack.pop() : State();
|
State state = !stack.empty() ? stack.pop() : State();
|
||||||
|
|
||||||
const int firstLine = firstVisibleLine();
|
CursorPosition lastPos(m_cursor);
|
||||||
|
|
||||||
CursorPosition lastPos(cursor());
|
|
||||||
const int current = revision();
|
const int current = revision();
|
||||||
|
|
||||||
++m_editBlockLevel;
|
++m_editBlockLevel;
|
||||||
@@ -7137,8 +7144,6 @@ void FakeVimHandler::Private::undoRedo(bool undo)
|
|||||||
|
|
||||||
--m_editBlockLevel;
|
--m_editBlockLevel;
|
||||||
|
|
||||||
scrollToLine(firstLine);
|
|
||||||
|
|
||||||
if (current == revision()) {
|
if (current == revision()) {
|
||||||
const QString msg = undo ? FakeVimHandler::tr("Already at oldest change.")
|
const QString msg = undo ? FakeVimHandler::tr("Already at oldest change.")
|
||||||
: FakeVimHandler::tr("Already at newest change.");
|
: FakeVimHandler::tr("Already at newest change.");
|
||||||
@@ -7160,6 +7165,9 @@ void FakeVimHandler::Private::undoRedo(bool undo)
|
|||||||
setCursorPosition(m_lastChangePosition);
|
setCursorPosition(m_lastChangePosition);
|
||||||
setAnchor();
|
setAnchor();
|
||||||
stack2.push(state);
|
stack2.push(state);
|
||||||
|
} else {
|
||||||
|
updateFirstVisibleLine();
|
||||||
|
m_cursor = EDITOR(textCursor());
|
||||||
}
|
}
|
||||||
|
|
||||||
setTargetColumn();
|
setTargetColumn();
|
||||||
@@ -7183,7 +7191,7 @@ void FakeVimHandler::Private::updateCursorShape()
|
|||||||
|| m_subsubmode == SearchSubSubMode
|
|| m_subsubmode == SearchSubSubMode
|
||||||
|| m_mode == InsertMode
|
|| m_mode == InsertMode
|
||||||
|| isVisualMode()
|
|| isVisualMode()
|
||||||
|| cursor().hasSelection();
|
|| m_cursor.hasSelection();
|
||||||
EDITOR(setOverwriteMode(!thinCursor));
|
EDITOR(setOverwriteMode(!thinCursor));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -7259,7 +7267,7 @@ void FakeVimHandler::Private::enterExMode(const QString &contents)
|
|||||||
void FakeVimHandler::Private::recordJump(int position)
|
void FakeVimHandler::Private::recordJump(int position)
|
||||||
{
|
{
|
||||||
CursorPosition pos = position >= 0 ? CursorPosition(document(), position)
|
CursorPosition pos = position >= 0 ? CursorPosition(document(), position)
|
||||||
: CursorPosition(cursor());
|
: CursorPosition(m_cursor);
|
||||||
setMark(QLatin1Char('\''), pos);
|
setMark(QLatin1Char('\''), pos);
|
||||||
setMark(QLatin1Char('`'), pos);
|
setMark(QLatin1Char('`'), pos);
|
||||||
if (m_jumpListUndo.isEmpty() || m_jumpListUndo.top() != pos)
|
if (m_jumpListUndo.isEmpty() || m_jumpListUndo.top() != pos)
|
||||||
@@ -7273,7 +7281,7 @@ void FakeVimHandler::Private::jump(int distance)
|
|||||||
QStack<CursorPosition> &from = (distance > 0) ? m_jumpListRedo : m_jumpListUndo;
|
QStack<CursorPosition> &from = (distance > 0) ? m_jumpListRedo : m_jumpListUndo;
|
||||||
QStack<CursorPosition> &to = (distance > 0) ? m_jumpListUndo : m_jumpListRedo;
|
QStack<CursorPosition> &to = (distance > 0) ? m_jumpListUndo : m_jumpListRedo;
|
||||||
int len = qMin(qAbs(distance), from.size());
|
int len = qMin(qAbs(distance), from.size());
|
||||||
CursorPosition m(cursor());
|
CursorPosition m(m_cursor);
|
||||||
setMark(QLatin1Char('\''), m);
|
setMark(QLatin1Char('\''), m);
|
||||||
setMark(QLatin1Char('`'), m);
|
setMark(QLatin1Char('`'), m);
|
||||||
for (int i = 0; i < len; ++i) {
|
for (int i = 0; i < len; ++i) {
|
||||||
@@ -7358,6 +7366,7 @@ void FakeVimHandler::Private::handleStartOfLine()
|
|||||||
void FakeVimHandler::Private::replay(const QString &command)
|
void FakeVimHandler::Private::replay(const QString &command)
|
||||||
{
|
{
|
||||||
//qDebug() << "REPLAY: " << quoteUnprintable(command);
|
//qDebug() << "REPLAY: " << quoteUnprintable(command);
|
||||||
|
clearCommandMode();
|
||||||
Inputs inputs(command);
|
Inputs inputs(command);
|
||||||
foreach (const Input &in, inputs) {
|
foreach (const Input &in, inputs) {
|
||||||
if (handleDefaultKey(in) != EventHandled)
|
if (handleDefaultKey(in) != EventHandled)
|
||||||
@@ -7367,7 +7376,7 @@ void FakeVimHandler::Private::replay(const QString &command)
|
|||||||
|
|
||||||
QString FakeVimHandler::Private::visualDotCommand() const
|
QString FakeVimHandler::Private::visualDotCommand() const
|
||||||
{
|
{
|
||||||
QTextCursor start(cursor());
|
QTextCursor start(m_cursor);
|
||||||
QTextCursor end(start);
|
QTextCursor end(start);
|
||||||
end.setPosition(end.anchor());
|
end.setPosition(end.anchor());
|
||||||
|
|
||||||
@@ -7443,7 +7452,8 @@ void FakeVimHandler::Private::selectTextObject(bool simple, bool inner)
|
|||||||
moveToWordStart(1, simple, false);
|
moveToWordStart(1, simple, false);
|
||||||
|
|
||||||
// select trailing spaces if no leading space
|
// select trailing spaces if no leading space
|
||||||
if (!leadingSpace && document()->characterAt(position() + direction).isSpace()
|
QChar afterCursor = document()->characterAt(position() + direction);
|
||||||
|
if (!leadingSpace && afterCursor.isSpace() && afterCursor != ParagraphSeparator
|
||||||
&& !atBlockStart()) {
|
&& !atBlockStart()) {
|
||||||
if (forward)
|
if (forward)
|
||||||
moveToNextBoundaryEnd(1, simple);
|
moveToNextBoundaryEnd(1, simple);
|
||||||
@@ -7543,7 +7553,7 @@ bool FakeVimHandler::Private::changeNumberTextObject(int count)
|
|||||||
{
|
{
|
||||||
const QTextBlock block = this->block();
|
const QTextBlock block = this->block();
|
||||||
const QString lineText = block.text();
|
const QString lineText = block.text();
|
||||||
const int posMin = cursor().positionInBlock() + 1;
|
const int posMin = m_cursor.positionInBlock() + 1;
|
||||||
|
|
||||||
// find first decimal, hexadecimal or octal number under or after cursor position
|
// find first decimal, hexadecimal or octal number under or after cursor position
|
||||||
QRegExp re(_("(0[xX])(0*[0-9a-fA-F]+)|(0)(0*[0-7]+)(?=\\D|$)|(\\d+)"));
|
QRegExp re(_("(0[xX])(0*[0-9a-fA-F]+)|(0)(0*[0-7]+)(?=\\D|$)|(\\d+)"));
|
||||||
@@ -7607,7 +7617,7 @@ bool FakeVimHandler::Private::changeNumberTextObject(int count)
|
|||||||
bool FakeVimHandler::Private::selectQuotedStringTextObject(bool inner,
|
bool FakeVimHandler::Private::selectQuotedStringTextObject(bool inner,
|
||||||
const QString "e)
|
const QString "e)
|
||||||
{
|
{
|
||||||
QTextCursor tc = cursor();
|
QTextCursor tc = m_cursor;
|
||||||
int sz = quote.size();
|
int sz = quote.size();
|
||||||
|
|
||||||
QTextCursor tc1;
|
QTextCursor tc1;
|
||||||
@@ -7983,6 +7993,19 @@ void FakeVimHandler::setTextCursorPosition(int position)
|
|||||||
d->setAnchorAndPosition(pos, pos);
|
d->setAnchorAndPosition(pos, pos);
|
||||||
d->m_fakeEnd = false;
|
d->m_fakeEnd = false;
|
||||||
d->setTargetColumn();
|
d->setTargetColumn();
|
||||||
|
|
||||||
|
if (!d->m_inFakeVim)
|
||||||
|
d->commitCursor();
|
||||||
|
}
|
||||||
|
|
||||||
|
QTextCursor FakeVimHandler::textCursor() const
|
||||||
|
{
|
||||||
|
return d->m_cursor;
|
||||||
|
}
|
||||||
|
|
||||||
|
void FakeVimHandler::setTextCursor(const QTextCursor &cursor)
|
||||||
|
{
|
||||||
|
d->m_cursor = cursor;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FakeVimHandler::jumpToLocalMark(QChar mark, bool backTickMode)
|
bool FakeVimHandler::jumpToLocalMark(QChar mark, bool backTickMode)
|
||||||
|
@@ -125,6 +125,9 @@ public slots:
|
|||||||
// Set text cursor position. Keeps anchor if in visual mode.
|
// Set text cursor position. Keeps anchor if in visual mode.
|
||||||
void setTextCursorPosition(int position);
|
void setTextCursorPosition(int position);
|
||||||
|
|
||||||
|
QTextCursor textCursor() const;
|
||||||
|
void setTextCursor(const QTextCursor &cursor);
|
||||||
|
|
||||||
bool jumpToLocalMark(QChar mark, bool backTickMode);
|
bool jumpToLocalMark(QChar mark, bool backTickMode);
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
|
@@ -1406,10 +1406,10 @@ void FakeVimPluginPrivate::findNext(bool reverse)
|
|||||||
void FakeVimPluginPrivate::foldToggle(int depth)
|
void FakeVimPluginPrivate::foldToggle(int depth)
|
||||||
{
|
{
|
||||||
IEditor *ieditor = EditorManager::currentEditor();
|
IEditor *ieditor = EditorManager::currentEditor();
|
||||||
BaseTextEditorWidget *editor = qobject_cast<BaseTextEditorWidget *>(ieditor->widget());
|
FakeVimHandler *handler = m_editorToHandler.value(ieditor, 0);
|
||||||
QTC_ASSERT(editor != 0, return);
|
QTC_ASSERT(handler != 0, return);
|
||||||
|
|
||||||
QTextBlock block = editor->textCursor().block();
|
QTextBlock block = handler->textCursor().block();
|
||||||
fold(depth, !BaseTextDocumentLayout::isFolded(block));
|
fold(depth, !BaseTextDocumentLayout::isFolded(block));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1437,6 +1437,8 @@ void FakeVimPluginPrivate::foldAll(bool fold)
|
|||||||
void FakeVimPluginPrivate::fold(int depth, bool fold)
|
void FakeVimPluginPrivate::fold(int depth, bool fold)
|
||||||
{
|
{
|
||||||
IEditor *ieditor = EditorManager::currentEditor();
|
IEditor *ieditor = EditorManager::currentEditor();
|
||||||
|
FakeVimHandler *handler = m_editorToHandler.value(ieditor, 0);
|
||||||
|
QTC_ASSERT(handler != 0, return);
|
||||||
BaseTextEditorWidget *editor = qobject_cast<BaseTextEditorWidget *>(ieditor->widget());
|
BaseTextEditorWidget *editor = qobject_cast<BaseTextEditorWidget *>(ieditor->widget());
|
||||||
QTC_ASSERT(editor != 0, return);
|
QTC_ASSERT(editor != 0, return);
|
||||||
|
|
||||||
@@ -1445,7 +1447,7 @@ void FakeVimPluginPrivate::fold(int depth, bool fold)
|
|||||||
qobject_cast<BaseTextDocumentLayout*>(doc->documentLayout());
|
qobject_cast<BaseTextDocumentLayout*>(doc->documentLayout());
|
||||||
QTC_ASSERT(documentLayout != 0, return);
|
QTC_ASSERT(documentLayout != 0, return);
|
||||||
|
|
||||||
QTextBlock block = editor->textCursor().block();
|
QTextBlock block = handler->textCursor().block();
|
||||||
int indent = BaseTextDocumentLayout::foldingIndent(block);
|
int indent = BaseTextDocumentLayout::foldingIndent(block);
|
||||||
if (fold) {
|
if (fold) {
|
||||||
if (BaseTextDocumentLayout::isFolded(block)) {
|
if (BaseTextDocumentLayout::isFolded(block)) {
|
||||||
@@ -1496,10 +1498,10 @@ void FakeVimPluginPrivate::fold(int depth, bool fold)
|
|||||||
void FakeVimPluginPrivate::foldGoTo(int count, bool current)
|
void FakeVimPluginPrivate::foldGoTo(int count, bool current)
|
||||||
{
|
{
|
||||||
IEditor *ieditor = EditorManager::currentEditor();
|
IEditor *ieditor = EditorManager::currentEditor();
|
||||||
BaseTextEditorWidget *editor = qobject_cast<BaseTextEditorWidget *>(ieditor->widget());
|
FakeVimHandler *handler = m_editorToHandler.value(ieditor, 0);
|
||||||
QTC_ASSERT(editor != 0, return);
|
QTC_ASSERT(handler != 0, return);
|
||||||
|
|
||||||
QTextCursor tc = editor->textCursor();
|
QTextCursor tc = handler->textCursor();
|
||||||
QTextBlock block = tc.block();
|
QTextBlock block = tc.block();
|
||||||
|
|
||||||
int pos = -1;
|
int pos = -1;
|
||||||
@@ -1546,7 +1548,7 @@ void FakeVimPluginPrivate::foldGoTo(int count, bool current)
|
|||||||
|
|
||||||
if (pos != -1) {
|
if (pos != -1) {
|
||||||
tc.setPosition(pos, QTextCursor::KeepAnchor);
|
tc.setPosition(pos, QTextCursor::KeepAnchor);
|
||||||
editor->setTextCursor(tc);
|
handler->setTextCursor(tc);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -142,6 +142,8 @@ private slots:
|
|||||||
|
|
||||||
void test_macros();
|
void test_macros();
|
||||||
|
|
||||||
|
void test_vim_qtcreator();
|
||||||
|
|
||||||
// special tests
|
// special tests
|
||||||
void test_i_cw_i();
|
void test_i_cw_i();
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user