Fixes: fakevim: better undo behaviour

Details:  prevent creation of empty "groups" that required
additional 'u' key strokes to 'undo'
This commit is contained in:
hjk
2009-01-21 16:18:20 +01:00
parent a18770548e
commit 7ce2676c6a

View File

@@ -137,20 +137,20 @@ enum MoveType
struct EditOperation struct EditOperation
{ {
EditOperation() : m_position(-1), m_itemCount(0) {} EditOperation() : position(-1), itemCount(0) {}
int m_position; int position;
int m_itemCount; // used to combine several operations int itemCount; // used to combine several operations
QString m_from; QString from;
QString m_to; QString to;
}; };
QDebug &operator<<(QDebug &ts, const EditOperation &op) QDebug &operator<<(QDebug &ts, const EditOperation &op)
{ {
if (op.m_itemCount > 0) { if (op.itemCount > 0) {
ts << "\n EDIT BLOCK WITH " << op.m_itemCount << " ITEMS"; ts << "\n EDIT BLOCK WITH " << op.itemCount << " ITEMS";
} else { } else {
ts << "\n EDIT AT " << op.m_position ts << "\n EDIT AT " << op.position
<< "\n FROM " << op.m_from << "\n TO " << op.m_to; << "\n FROM " << op.from << "\n TO " << op.to;
} }
return ts; return ts;
} }
@@ -1357,9 +1357,9 @@ void FakeVimHandler::Private::handleExCommand(const QString &cmd0)
m_tc.setPosition(positionForLine(beginLine)); m_tc.setPosition(positionForLine(beginLine));
EditOperation op; EditOperation op;
// FIXME: broken for "upward selection" // FIXME: broken for "upward selection"
op.m_position = m_tc.position(); op.position = m_tc.position();
op.m_from = text; op.from = text;
op.m_to = result; op.to = result;
recordOperation(op); recordOperation(op);
enterCommandMode(); enterCommandMode();
@@ -1757,18 +1757,18 @@ void FakeVimHandler::Private::undo()
} else { } else {
EditOperation op = m_undoStack.pop(); EditOperation op = m_undoStack.pop();
//qDebug() << "UNDO " << op; //qDebug() << "UNDO " << op;
if (op.m_itemCount > 0) { if (op.itemCount > 0) {
for (int i = op.m_itemCount; --i >= 0; ) for (int i = op.itemCount; --i >= 0; )
undo(); undo();
} else { } else {
m_tc.setPosition(op.m_position, MoveAnchor); m_tc.setPosition(op.position, MoveAnchor);
if (!op.m_to.isEmpty()) { if (!op.to.isEmpty()) {
m_tc.setPosition(op.m_position + op.m_to.size(), KeepAnchor); m_tc.setPosition(op.position + op.to.size(), KeepAnchor);
m_tc.deleteChar(); m_tc.deleteChar();
} }
if (!op.m_from.isEmpty()) if (!op.from.isEmpty())
m_tc.insertText(op.m_from); m_tc.insertText(op.from);
m_tc.setPosition(op.m_position, MoveAnchor); m_tc.setPosition(op.position, MoveAnchor);
} }
m_redoStack.push(op); m_redoStack.push(op);
showBlackMessage(QString()); showBlackMessage(QString());
@@ -1786,18 +1786,18 @@ void FakeVimHandler::Private::redo()
} else { } else {
EditOperation op = m_redoStack.pop(); EditOperation op = m_redoStack.pop();
//qDebug() << "REDO " << op; //qDebug() << "REDO " << op;
if (op.m_itemCount > 0) { if (op.itemCount > 0) {
for (int i = op.m_itemCount; --i >= 0; ) for (int i = op.itemCount; --i >= 0; )
redo(); redo();
} else { } else {
m_tc.setPosition(op.m_position, MoveAnchor); m_tc.setPosition(op.position, MoveAnchor);
if (!op.m_from.isEmpty()) { if (!op.from.isEmpty()) {
m_tc.setPosition(op.m_position + op.m_from.size(), KeepAnchor); m_tc.setPosition(op.position + op.from.size(), KeepAnchor);
m_tc.deleteChar(); m_tc.deleteChar();
} }
if (!op.m_to.isEmpty()) if (!op.to.isEmpty())
m_tc.insertText(op.m_to); m_tc.insertText(op.to);
m_tc.setPosition(op.m_position, MoveAnchor); m_tc.setPosition(op.position, MoveAnchor);
} }
m_undoStack.push(op); m_undoStack.push(op);
showBlackMessage(QString()); showBlackMessage(QString());
@@ -1810,15 +1810,15 @@ void FakeVimHandler::Private::recordBeginGroup()
//qDebug() << "PUSH"; //qDebug() << "PUSH";
m_undoGroupStack.push(m_undoStack.size()); m_undoGroupStack.push(m_undoStack.size());
EditOperation op; EditOperation op;
op.m_position = m_tc.position(); op.position = m_tc.position();
recordOperation(op); recordOperation(op);
} }
void FakeVimHandler::Private::recordEndGroup() void FakeVimHandler::Private::recordEndGroup()
{ {
EditOperation op; EditOperation op;
op.m_itemCount = m_undoStack.size() - m_undoGroupStack.pop(); op.itemCount = m_undoStack.size() - m_undoGroupStack.pop();
//qDebug() << "POP " << op.m_itemCount; //qDebug() << "POP " << op.itemCount << m_undoStack;
recordOperation(op); recordOperation(op);
} }
@@ -1831,12 +1831,12 @@ QString FakeVimHandler::Private::recordRemoveSelectedText()
return QString(); return QString();
m_tc.setPosition(anchor(), MoveAnchor); m_tc.setPosition(anchor(), MoveAnchor);
m_tc.setPosition(pos, KeepAnchor); m_tc.setPosition(pos, KeepAnchor);
op.m_position = qMin(pos, anchor()); op.position = qMin(pos, anchor());
op.m_from = m_tc.selection().toPlainText(); op.from = m_tc.selection().toPlainText();
//qDebug() << "OP: " << op; //qDebug() << "OP: " << op;
recordOperation(op); recordOperation(op);
m_tc.deleteChar(); m_tc.deleteChar();
return op.m_from; return op.from;
} }
void FakeVimHandler::Private::recordRemoveNextChar() void FakeVimHandler::Private::recordRemoveNextChar()
@@ -1849,15 +1849,20 @@ void FakeVimHandler::Private::recordRemoveNextChar()
void FakeVimHandler::Private::recordInsertText(const QString &data) void FakeVimHandler::Private::recordInsertText(const QString &data)
{ {
EditOperation op; EditOperation op;
op.m_position = m_tc.position(); op.position = m_tc.position();
op.m_to = data; op.to = data;
recordOperation(op); recordOperation(op);
m_tc.insertText(data); m_tc.insertText(data);
} }
void FakeVimHandler::Private::recordOperation(const EditOperation &op) void FakeVimHandler::Private::recordOperation(const EditOperation &op)
{ {
//qDebug() << "OP: " << op; // No need to record operations that actually do not change anything.
if (op.from.isEmpty() && op.to.isEmpty() && op.itemCount == 0)
return;
// No need to create groups with only one member.
if (op.itemCount == 1)
return;
m_undoStack.push(op); m_undoStack.push(op);
m_redoStack.clear(); m_redoStack.clear();
} }
@@ -1865,16 +1870,16 @@ void FakeVimHandler::Private::recordOperation(const EditOperation &op)
void FakeVimHandler::Private::recordMove(int position, int nestedCount) void FakeVimHandler::Private::recordMove(int position, int nestedCount)
{ {
EditOperation op; EditOperation op;
op.m_position = position; op.position = position;
op.m_itemCount = nestedCount; op.itemCount = nestedCount;
recordOperation(op); recordOperation(op);
} }
void FakeVimHandler::Private::recordInsert(int position, const QString &data) void FakeVimHandler::Private::recordInsert(int position, const QString &data)
{ {
EditOperation op; EditOperation op;
op.m_position = position; op.position = position;
op.m_to = data; op.to = data;
recordOperation(op); recordOperation(op);
} }
@@ -1889,8 +1894,8 @@ void FakeVimHandler::Private::recordRemove(int position, int length)
void FakeVimHandler::Private::recordRemove(int position, const QString &data) void FakeVimHandler::Private::recordRemove(int position, const QString &data)
{ {
EditOperation op; EditOperation op;
op.m_position = position; op.position = position;
op.m_from = data; op.from = data;
recordOperation(op); recordOperation(op);
} }