vim-mode: message for Vim mode

This commit is contained in:
Le Tan 2017-06-17 19:02:42 +08:00
parent 7871965bf8
commit ffce4b9611
19 changed files with 161 additions and 252 deletions

View File

@ -14,10 +14,10 @@ background: 005fff
editor-current-line
background: c5cae9
vim-insert-background: c5cae9
vim-insert-background: e1bee7
vim-normal-background: a5d6a7
vim-visual-background: a5d6a7
vim-replace-background: a5d6a7
vim-visual-background: 90caf9
vim-replace-background: f8bbd0
H1
foreground: 111111

View File

@ -251,3 +251,16 @@ repeat:
p_cursor.setPosition(block.position() + idx, p_mode);
return true;
}
int VEditUtils::selectedBlockCount(const QTextCursor &p_cursor)
{
if (!p_cursor.hasSelection()) {
return 0;
}
QTextDocument *doc = p_cursor.document();
int sbNum = doc->findBlock(p_cursor.selectionStart()).blockNumber();
int ebNum = doc->findBlock(p_cursor.selectionEnd()).blockNumber();
return ebNum - sbNum + 1;
}

View File

@ -71,6 +71,9 @@ public:
bool p_forward,
bool p_inclusive);
// Get the count of blocks selected.
static int selectedBlockCount(const QTextCursor &p_cursor);
private:
VEditUtils() {}
};

View File

@ -2119,6 +2119,9 @@ void VVim::processDeleteAction(QList<Token> &p_tokens)
VEditUtils::removeBlock(cursor);
}
message(tr("%1 fewer %2").arg(repeat).arg(repeat > 1 ? tr("lines")
: tr("line")));
qDebug() << "delete" << repeat << "lines";
break;
}
@ -2181,18 +2184,6 @@ void VVim::processDeleteAction(QList<Token> &p_tokens)
if (hasMoved) {
bool clearEmptyBlock = false;
switch (to.m_movement) {
case Movement::Left:
{
qDebug() << "delete backward" << repeat << "chars";
break;
}
case Movement::Right:
{
qDebug() << "delete forward" << repeat << "chars";
break;
}
case Movement::Up:
{
expandSelectionToWholeLines(cursor);
@ -2209,24 +2200,6 @@ void VVim::processDeleteAction(QList<Token> &p_tokens)
break;
}
case Movement::VisualUp:
{
qDebug() << "delete visual up" << repeat << "lines";
break;
}
case Movement::VisualDown:
{
qDebug() << "delete visual down" << repeat << "lines";
break;
}
case Movement::StartOfLine:
{
qDebug() << "delete till start of line";
break;
}
case Movement::EndOfLine:
{
// End of line (block).
@ -2238,12 +2211,6 @@ void VVim::processDeleteAction(QList<Token> &p_tokens)
break;
}
case Movement::FirstCharacter:
{
qDebug() << "delete till first non-space character";
break;
}
case Movement::LineJump:
{
expandSelectionToWholeLines(cursor);
@ -2268,58 +2235,16 @@ void VVim::processDeleteAction(QList<Token> &p_tokens)
break;
}
case Movement::WordForward:
{
qDebug() << "delete" << repeat << "words forward";
break;
}
case Movement::WORDForward:
{
qDebug() << "delete" << repeat << "WORDs forward";
break;
}
case Movement::ForwardEndOfWord:
{
qDebug() << "delete" << repeat << "end of words forward";
break;
}
case Movement::ForwardEndOfWORD:
{
qDebug() << "delete" << repeat << "end of WORDs forward";
break;
}
case Movement::WordBackward:
{
qDebug() << "delete" << repeat << "words backward";
break;
}
case Movement::WORDBackward:
{
qDebug() << "delete" << repeat << "WORDs backward";
break;
}
case Movement::BackwardEndOfWord:
{
qDebug() << "delete" << repeat << "end of words backward";
break;
}
case Movement::BackwardEndOfWORD:
{
qDebug() << "delete" << repeat << "end of WORDs backward";
break;
}
default:
break;
}
if (clearEmptyBlock) {
int nrBlock = VEditUtils::selectedBlockCount(cursor);
message(tr("%1 fewer %2").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
}
deleteSelectedText(cursor, clearEmptyBlock);
}
@ -2359,7 +2284,7 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
switch (to.m_range) {
case Range::Line:
{
// yy, delete current line.
// yy, copy current line.
if (repeat == -1) {
repeat = 1;
}
@ -2370,6 +2295,9 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
saveToRegister("\n");
}
message(tr("%1 %2 yanked").arg(repeat).arg(repeat > 1 ? tr("lines")
: tr("line")));
qDebug() << "copy" << repeat << "lines";
break;
}
@ -2437,18 +2365,6 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
if (changed) {
bool addNewLine = false;
switch (to.m_movement) {
case Movement::Left:
{
qDebug() << "copy backward" << repeat << "chars";
break;
}
case Movement::Right:
{
qDebug() << "copy forward" << repeat << "chars";
break;
}
case Movement::Up:
{
expandSelectionToWholeLines(cursor);
@ -2465,24 +2381,6 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
break;
}
case Movement::VisualUp:
{
qDebug() << "copy visual up" << repeat << "lines";
break;
}
case Movement::VisualDown:
{
qDebug() << "copy visual down" << repeat << "lines";
break;
}
case Movement::StartOfLine:
{
qDebug() << "copy till start of line";
break;
}
case Movement::EndOfLine:
{
// End of line (block).
@ -2491,12 +2389,6 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
break;
}
case Movement::FirstCharacter:
{
qDebug() << "copy till first non-space character";
break;
}
case Movement::LineJump:
{
expandSelectionToWholeLines(cursor);
@ -2521,58 +2413,16 @@ void VVim::processCopyAction(QList<Token> &p_tokens)
break;
}
case Movement::WordForward:
{
qDebug() << "copy" << repeat << "words forward";
break;
}
case Movement::WORDForward:
{
qDebug() << "copy" << repeat << "WORDs forward";
break;
}
case Movement::ForwardEndOfWord:
{
qDebug() << "copy" << repeat << "end of words forward";
break;
}
case Movement::ForwardEndOfWORD:
{
qDebug() << "copy" << repeat << "end of WORDs forward";
break;
}
case Movement::WordBackward:
{
qDebug() << "copy" << repeat << "words backward";
break;
}
case Movement::WORDBackward:
{
qDebug() << "copy" << repeat << "WORDs backward";
break;
}
case Movement::BackwardEndOfWord:
{
qDebug() << "copy" << repeat << "end of words backward";
break;
}
case Movement::BackwardEndOfWORD:
{
qDebug() << "copy" << repeat << "end of WORDs backward";
break;
}
default:
break;
}
if (addNewLine) {
int nrBlock = VEditUtils::selectedBlockCount(cursor);
message(tr("%1 %2 yanked").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
}
copySelectedText(cursor, addNewLine);
if (cursor.position() != oriPos) {
cursor.setPosition(oriPos);
@ -2626,6 +2476,12 @@ void VVim::processPasteAction(QList<Token> &p_tokens, bool p_pasteBefore)
// inserBlock() already insert a new line, so eliminate one here.
cursor.insertText(text.left(text.size() - 1));
int nrBlock = text.count('\n');
if (nrBlock > 0) {
message(tr("%1 more %2").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
}
} else {
if (!p_pasteBefore && !cursor.atBlockEnd()) {
// Insert behind current cursor.
@ -2944,6 +2800,15 @@ void VVim::processIndentAction(QList<Token> &p_tokens, bool p_isIndent)
cursor,
m_editConfig->m_tabSpaces,
p_isIndent);
if (p_isIndent) {
message(tr("%1 %2 >ed 1 time").arg(repeat).arg(repeat > 1 ? tr("lines")
: tr("line")));
} else {
message(tr("%1 %2 <ed 1 time").arg(repeat).arg(repeat > 1 ? tr("lines")
: tr("line")));
}
break;
}
@ -2989,6 +2854,16 @@ void VVim::processIndentAction(QList<Token> &p_tokens, bool p_isIndent)
QTextCursor::KeepAnchor,
to,
repeat);
int nrBlock = VEditUtils::selectedBlockCount(cursor);
if (p_isIndent) {
message(tr("%1 %2 >ed 1 time").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
} else {
message(tr("%1 %2 <ed 1 time").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
}
VEditUtils::indentSelectedBlocks(doc,
cursor,
m_editConfig->m_tabSpaces,
@ -3021,6 +2896,12 @@ void VVim::processToLowerAction(QList<Token> &p_tokens, bool p_toLower)
if (changed) {
oriPos = cursor.selectionStart();
convertCaseOfSelectedText(cursor, p_toLower);
if (to.m_range == Range::Line) {
message(tr("%1 %2 changed").arg(repeat == -1 ? 1 : repeat)
.arg(repeat > 1 ? tr("lines") : tr("line")));
}
cursor.setPosition(oriPos);
}
@ -3054,117 +2935,54 @@ void VVim::processToLowerAction(QList<Token> &p_tokens, bool p_toLower)
if (changed) {
oriPos = cursor.selectionStart();
bool isBlock = false;
switch (to.m_movement) {
case Movement::Left:
{
break;
}
case Movement::Right:
{
break;
}
case Movement::Up:
{
isBlock = true;
expandSelectionToWholeLines(cursor);
break;
}
case Movement::Down:
{
isBlock = true;
expandSelectionToWholeLines(cursor);
break;
}
case Movement::VisualUp:
{
break;
}
case Movement::VisualDown:
{
break;
}
case Movement::StartOfLine:
{
break;
}
case Movement::EndOfLine:
{
break;
}
case Movement::FirstCharacter:
{
break;
}
case Movement::LineJump:
{
isBlock = true;
expandSelectionToWholeLines(cursor);
break;
}
case Movement::StartOfDocument:
{
isBlock = true;
expandSelectionToWholeLines(cursor);
break;
}
case Movement::EndOfDocument:
{
isBlock = true;
expandSelectionToWholeLines(cursor);
break;
}
case Movement::WordForward:
{
break;
}
case Movement::WORDForward:
{
break;
}
case Movement::ForwardEndOfWord:
{
break;
}
case Movement::ForwardEndOfWORD:
{
break;
}
case Movement::WordBackward:
{
break;
}
case Movement::WORDBackward:
{
break;
}
case Movement::BackwardEndOfWord:
{
break;
}
case Movement::BackwardEndOfWORD:
{
break;
}
default:
break;
}
if (isBlock) {
int nrBlock = VEditUtils::selectedBlockCount(cursor);
message(tr("%1 %2 changed").arg(nrBlock).arg(nrBlock > 1 ? tr("lines")
: tr("line")));
}
convertCaseOfSelectedText(cursor, p_toLower);
cursor.setPosition(oriPos);
@ -3556,3 +3374,9 @@ void VVim::repeatLastFindMovement(bool p_reverse)
addMovementToken(mm, key);
processCommand(m_tokens);
}
void VVim::message(const QString &p_msg)
{
qDebug() << "vim msg:" << p_msg;
emit vimMessage(p_msg);
}

View File

@ -42,6 +42,9 @@ signals:
// Emit when current mode has been changed.
void modeChanged(VimMode p_mode);
// Emit when VVim want to display some messages.
void vimMessage(const QString &p_msg);
private slots:
// When user use mouse to select texts in Normal mode, we should change to
// Visual mode.
@ -452,6 +455,8 @@ private:
// Repeat m_lastFindToken.
void repeatLastFindMovement(bool p_reverse);
void message(const QString &p_str);
VEdit *m_editor;
const VEditConfig *m_editConfig;
VimMode m_mode;

View File

@ -330,7 +330,10 @@ QString VConfigManager::getLogFilePath()
void VConfigManager::updateMarkdownEditStyle()
{
static const QString defaultCurrentLineBackground = "#C5CAE9";
static const QString defaultCurrentLineVimBackground = "#A5D6A7";
static const QString defaultVimNormalBg = "#A5D6A7";
static const QString defaultVimInsertBg = "#E1BEE7";
static const QString defaultVimVisualBg = "#90CAF9";
static const QString defaultVimReplaceBg = "#F8BBD0";
static const QString defaultTrailingSpaceBackground = "#FFEBEE";
// Read style file .mdhl
@ -351,10 +354,10 @@ void VConfigManager::updateMarkdownEditStyle()
parser.fetchMarkdownEditorStyles(mdEditPalette, mdEditFont, styles);
m_editorCurrentLineBg = defaultCurrentLineBackground;
m_editorVimInsertBg = defaultCurrentLineBackground;
m_editorVimNormalBg = defaultCurrentLineVimBackground;
m_editorVimVisualBg = m_editorVimNormalBg;
m_editorVimReplaceBg = m_editorVimNormalBg;
m_editorVimInsertBg = defaultVimInsertBg;
m_editorVimNormalBg = defaultVimNormalBg;
m_editorVimVisualBg = defaultVimVisualBg;
m_editorVimReplaceBg = defaultVimReplaceBg;
auto editorCurrentLineIt = styles.find("editor-current-line");
if (editorCurrentLineIt != styles.end()) {
auto backgroundIt = editorCurrentLineIt->find("background");

View File

@ -89,6 +89,9 @@ signals:
// Emit when m_config has been updated.
void configUpdated();
// Emit when want to show message in status bar.
void statusMessage(const QString &p_msg);
public slots:
virtual void highlightCurrentLine();

View File

@ -79,6 +79,8 @@ void VEditArea::insertSplitWindow(int idx)
this, &VEditArea::handleOutlineChanged);
connect(win, &VEditWindow::curHeaderChanged,
this, &VEditArea::handleCurHeaderChanged);
connect(win, &VEditWindow::statusMessage,
this, &VEditArea::handleWindowStatusMessage);
}
void VEditArea::handleEditWindowStatusChanged(const VFile *p_file,
@ -90,6 +92,13 @@ void VEditArea::handleEditWindowStatusChanged(const VFile *p_file,
}
}
void VEditArea::handleWindowStatusMessage(const QString &p_msg)
{
if (splitter->widget(curWindowIndex) == sender()) {
emit statusMessage(p_msg);
}
}
void VEditArea::removeSplitWindow(VEditWindow *win)
{
if (!win) {

View File

@ -63,6 +63,9 @@ signals:
void outlineChanged(const VToc &toc);
void curHeaderChanged(const VAnchor &anchor);
// Emit when want to show message in status bar.
void statusMessage(const QString &p_msg);
protected:
void mousePressEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
@ -95,6 +98,9 @@ private slots:
const VEditTab *p_editTab,
bool p_editMode);
// Handle the statusMessage signal of VEditWindow.
void handleWindowStatusMessage(const QString &p_msg);
private:
void setupUI();
QVector<QPair<int, int> > findTabsByFile(const VFile *p_file);

View File

@ -18,6 +18,8 @@ VEditOperations::VEditOperations(VEdit *p_editor, VFile *p_file)
this, &VEditOperations::handleEditConfigUpdated);
connect(m_vim, &VVim::modeChanged,
this, &VEditOperations::handleVimModeChanged);
connect(m_vim, &VVim::vimMessage,
this, &VEditOperations::statusMessage);
}
void VEditOperations::insertTextAtCurPos(const QString &p_text)

View File

@ -27,6 +27,10 @@ public:
// processed.
virtual bool handleKeyPressEvent(QKeyEvent *p_event) = 0;
signals:
// Want to display a template message in status bar.
void statusMessage(const QString &p_msg);
protected slots:
// Handle the update of VEditConfig of the editor.
virtual void handleEditConfigUpdated();

View File

@ -93,6 +93,9 @@ signals:
void statusChanged();
// Emit when want to show message in status bar.
void statusMessage(const QString &p_msg);
private slots:
// Called when app focus changed.
void handleFocusChanged(QWidget *p_old, QWidget *p_now);

View File

@ -268,6 +268,8 @@ int VEditWindow::openFileInTab(VFile *p_file, OpenFileMode p_mode)
this, &VEditWindow::handleCurHeaderChanged);
connect(editor, &VEditTab::statusChanged,
this, &VEditWindow::handleTabStatusChanged);
connect(editor, &VEditTab::statusMessage,
this, &VEditWindow::handleTabStatusMessage);
int idx = appendEditTab(p_file, editor);
return idx;
@ -576,6 +578,14 @@ void VEditWindow::handleTabStatusChanged()
}
}
void VEditWindow::handleTabStatusMessage(const QString &p_msg)
{
int idx = indexOf(dynamic_cast<QWidget *>(sender()));
if (idx == currentIndex()) {
emit statusMessage(p_msg);
}
}
void VEditWindow::updateFileInfo(const VFile *p_file)
{
if (!p_file) {

View File

@ -68,6 +68,9 @@ signals:
void outlineChanged(const VToc &toc);
void curHeaderChanged(const VAnchor &anchor);
// Emit when want to show message in status bar.
void statusMessage(const QString &p_msg);
private slots:
bool handleTabCloseRequest(int index);
void splitWindow();
@ -85,6 +88,9 @@ private slots:
void handleMoveLeftAct();
void handleMoveRightAct();
// Handle the statusMessage signal of VEditTab.
void handleTabStatusMessage(const QString &p_msg);
private:
void initTabActions();
void setupCornerWidget();

View File

@ -39,6 +39,8 @@ void VHtmlTab::setupUI()
this, &VHtmlTab::discardAndRead);
connect(m_editor, &VEdit::editNote,
this, &VHtmlTab::editFile);
connect(m_editor, &VEdit::statusMessage,
this, &VEditTab::statusMessage);
m_editor->reloadFile();
QVBoxLayout *mainLayout = new QVBoxLayout();

View File

@ -109,6 +109,8 @@ void VMainWindow::setupUI()
editArea, &VEditArea::handleFileUpdated);
connect(editArea, &VEditArea::curTabStatusChanged,
this, &VMainWindow::handleCurTabStatusChanged);
connect(editArea, &VEditArea::statusMessage,
this, &VMainWindow::showStatusMessage);
connect(m_findReplaceDialog, &VFindReplaceDialog::findTextChanged,
this, &VMainWindow::handleFindDialogTextChanged);
@ -1488,3 +1490,9 @@ QAction *VMainWindow::newAction(const QIcon &p_icon,
return new QAction(p_icon, p_text, p_parent);
#endif
}
void VMainWindow::showStatusMessage(const QString &p_msg)
{
const int timeout = 3000;
statusBar()->showMessage(p_msg, timeout);
}

View File

@ -85,6 +85,9 @@ private slots:
void printNote();
void exportAsPDF();
// Show a temporary message in status bar.
void showStatusMessage(const QString &p_msg);
protected:
void closeEvent(QCloseEvent *event) Q_DECL_OVERRIDE;
void resizeEvent(QResizeEvent *event) Q_DECL_OVERRIDE;

View File

@ -51,6 +51,9 @@ VMdEdit::VMdEdit(VFile *p_file, VDocument *p_vdoc, MarkdownConverterType p_type,
m_editOps = new VMdEditOperations(this, m_file);
connect(m_editOps, &VEditOperations::statusMessage,
this, &VEdit::statusMessage);
connect(this, &VMdEdit::cursorPositionChanged,
this, &VMdEdit::updateCurHeader);

View File

@ -58,6 +58,8 @@ void VMdTab::setupUI()
this, &VMdTab::saveAndRead);
connect(m_editor, &VEdit::discardAndRead,
this, &VMdTab::discardAndRead);
connect(m_editor, &VEdit::statusMessage,
this, &VEditTab::statusMessage);
m_editor->reloadFile();
m_stacks->addWidget(m_editor);