diff options
author | nyamatongwe <unknown> | 2005-05-07 10:50:38 +0000 |
---|---|---|
committer | nyamatongwe <unknown> | 2005-05-07 10:50:38 +0000 |
commit | a5947254aab31b2e51f37144206133a8b0e4ac6e (patch) | |
tree | 4bf911b047a0c992d2dfb9e74b63c66ebe0e1e4f /src | |
parent | 4d4ebd95f2f25e4c814dcd441a98d388e659455a (diff) | |
download | scintilla-mirror-a5947254aab31b2e51f37144206133a8b0e4ac6e.tar.gz |
Patch from Robert that avoids slow performance for multiple step undo
or redo by only modifying the scroll bars at the end.
When document is read only, undo and redo send a SCN_MODIFYATTEMPTRO
notification.
Diffstat (limited to 'src')
-rw-r--r-- | src/CellBuffer.cxx | 4 | ||||
-rw-r--r-- | src/Document.cxx | 176 |
2 files changed, 102 insertions, 78 deletions
diff --git a/src/CellBuffer.cxx b/src/CellBuffer.cxx index 772f48e6e..2bb4f5a6c 100644 --- a/src/CellBuffer.cxx +++ b/src/CellBuffer.cxx @@ -1024,7 +1024,7 @@ void CellBuffer::DeleteUndoHistory() { } bool CellBuffer::CanUndo() { - return (!readOnly) && (uh.CanUndo()); + return uh.CanUndo(); } int CellBuffer::StartUndo() { @@ -1052,7 +1052,7 @@ void CellBuffer::PerformUndoStep() { } bool CellBuffer::CanRedo() { - return (!readOnly) && (uh.CanRedo()); + return uh.CanRedo(); } int CellBuffer::StartRedo() { diff --git a/src/Document.cxx b/src/Document.cxx index 0def97a8f..51299b37c 100644 --- a/src/Document.cxx +++ b/src/Document.cxx @@ -336,6 +336,14 @@ void Document::ModifiedAt(int pos) { endStyled = pos; } +void Document::CheckReadOnly() { + if (cb.IsReadOnly() && enteredReadOnlyCount == 0) { + enteredReadOnlyCount++; + NotifyModifyAttempt(); + enteredReadOnlyCount--; + } +} + // Document only modified by gateways DeleteChars, InsertStyledString, Undo, Redo, and SetStyleAt. // SetStyleAt does not change the persistent state of a document @@ -345,11 +353,7 @@ bool Document::DeleteChars(int pos, int len) { return false; if ((pos + len) > Length()) return false; - if (cb.IsReadOnly() && enteredReadOnlyCount == 0) { - enteredReadOnlyCount++; - NotifyModifyAttempt(); - enteredReadOnlyCount--; - } + CheckReadOnly(); if (enteredCount != 0) { return false; } else { @@ -384,11 +388,7 @@ bool Document::DeleteChars(int pos, int len) { * Insert a styled string (char/style pairs) with a length. */ bool Document::InsertStyledString(int position, char *s, int insertLength) { - if (cb.IsReadOnly() && enteredReadOnlyCount == 0) { - enteredReadOnlyCount++; - NotifyModifyAttempt(); - enteredReadOnlyCount--; - } + CheckReadOnly(); if (enteredCount != 0) { return false; } else { @@ -417,86 +417,110 @@ bool Document::InsertStyledString(int position, char *s, int insertLength) { } int Document::Undo() { - int newPos = 0; + int newPos = -1; + CheckReadOnly(); if (enteredCount == 0) { enteredCount++; - bool startSavePoint = cb.IsSavePoint(); - int steps = cb.StartUndo(); - //Platform::DebugPrintf("Steps=%d\n", steps); - for (int step = 0; step < steps; step++) { - int prevLinesTotal = LinesTotal(); - const Action &action = cb.GetUndoStep(); - if (action.at == removeAction) { - NotifyModified(DocModification( - SC_MOD_BEFOREINSERT | SC_PERFORMED_UNDO, action)); - } else { - NotifyModified(DocModification( - SC_MOD_BEFOREDELETE | SC_PERFORMED_UNDO, action)); - } - cb.PerformUndoStep(); - int cellPosition = action.position / 2; - ModifiedAt(cellPosition); - newPos = cellPosition; - - int modFlags = SC_PERFORMED_UNDO; - // With undo, an insertion action becomes a deletion notification - if (action.at == removeAction) { - newPos += action.lenData; - modFlags |= SC_MOD_INSERTTEXT; - } else { - modFlags |= SC_MOD_DELETETEXT; + if (!cb.IsReadOnly()) { + bool startSavePoint = cb.IsSavePoint(); + bool multiLine = false; + int steps = cb.StartUndo(); + //Platform::DebugPrintf("Steps=%d\n", steps); + for (int step = 0; step < steps; step++) { + const int prevLinesTotal = LinesTotal(); + const Action &action = cb.GetUndoStep(); + if (action.at == removeAction) { + NotifyModified(DocModification( + SC_MOD_BEFOREINSERT | SC_PERFORMED_UNDO, action)); + } else { + NotifyModified(DocModification( + SC_MOD_BEFOREDELETE | SC_PERFORMED_UNDO, action)); + } + cb.PerformUndoStep(); + int cellPosition = action.position / 2; + ModifiedAt(cellPosition); + newPos = cellPosition; + + int modFlags = SC_PERFORMED_UNDO; + // With undo, an insertion action becomes a deletion notification + if (action.at == removeAction) { + newPos += action.lenData; + modFlags |= SC_MOD_INSERTTEXT; + } else { + modFlags |= SC_MOD_DELETETEXT; + } + if (steps > 1) + modFlags |= SC_MULTISTEPUNDOREDO; + const int linesAdded = LinesTotal() - prevLinesTotal; + if (linesAdded != 0) + multiLine = true; + if (step == steps - 1) { + modFlags |= SC_LASTSTEPINUNDOREDO; + if (multiLine) + modFlags |= SC_MULTILINEUNDOREDO; + } + NotifyModified(DocModification(modFlags, cellPosition, action.lenData, + linesAdded, action.data)); } - if (step == steps - 1) - modFlags |= SC_LASTSTEPINUNDOREDO; - NotifyModified(DocModification(modFlags, cellPosition, action.lenData, - LinesTotal() - prevLinesTotal, action.data)); - } - bool endSavePoint = cb.IsSavePoint(); - if (startSavePoint != endSavePoint) - NotifySavePoint(endSavePoint); + bool endSavePoint = cb.IsSavePoint(); + if (startSavePoint != endSavePoint) + NotifySavePoint(endSavePoint); + } enteredCount--; } return newPos; } int Document::Redo() { - int newPos = 0; + int newPos = -1; + CheckReadOnly(); if (enteredCount == 0) { enteredCount++; - bool startSavePoint = cb.IsSavePoint(); - int steps = cb.StartRedo(); - for (int step = 0; step < steps; step++) { - int prevLinesTotal = LinesTotal(); - const Action &action = cb.GetRedoStep(); - if (action.at == insertAction) { - NotifyModified(DocModification( - SC_MOD_BEFOREINSERT | SC_PERFORMED_REDO, action)); - } else { - NotifyModified(DocModification( - SC_MOD_BEFOREDELETE | SC_PERFORMED_REDO, action)); - } - cb.PerformRedoStep(); - ModifiedAt(action.position / 2); - newPos = action.position / 2; - - int modFlags = SC_PERFORMED_REDO; - if (action.at == insertAction) { - newPos += action.lenData; - modFlags |= SC_MOD_INSERTTEXT; - } else { - modFlags |= SC_MOD_DELETETEXT; + if (!cb.IsReadOnly()) { + bool startSavePoint = cb.IsSavePoint(); + bool multiLine = false; + int steps = cb.StartRedo(); + for (int step = 0; step < steps; step++) { + const int prevLinesTotal = LinesTotal(); + const Action &action = cb.GetRedoStep(); + if (action.at == insertAction) { + NotifyModified(DocModification( + SC_MOD_BEFOREINSERT | SC_PERFORMED_REDO, action)); + } else { + NotifyModified(DocModification( + SC_MOD_BEFOREDELETE | SC_PERFORMED_REDO, action)); + } + cb.PerformRedoStep(); + ModifiedAt(action.position / 2); + newPos = action.position / 2; + + int modFlags = SC_PERFORMED_REDO; + if (action.at == insertAction) { + newPos += action.lenData; + modFlags |= SC_MOD_INSERTTEXT; + } else { + modFlags |= SC_MOD_DELETETEXT; + } + if (steps > 1) + modFlags |= SC_MULTISTEPUNDOREDO; + const int linesAdded = LinesTotal() - prevLinesTotal; + if (linesAdded != 0) + multiLine = true; + if (step == steps - 1) { + modFlags |= SC_LASTSTEPINUNDOREDO; + if (multiLine) + modFlags |= SC_MULTILINEUNDOREDO; + } + NotifyModified( + DocModification(modFlags, action.position / 2, action.lenData, + linesAdded, action.data)); } - if (step == steps - 1) - modFlags |= SC_LASTSTEPINUNDOREDO; - NotifyModified( - DocModification(modFlags, action.position / 2, action.lenData, - LinesTotal() - prevLinesTotal, action.data)); - } - bool endSavePoint = cb.IsSavePoint(); - if (startSavePoint != endSavePoint) - NotifySavePoint(endSavePoint); + bool endSavePoint = cb.IsSavePoint(); + if (startSavePoint != endSavePoint) + NotifySavePoint(endSavePoint); + } enteredCount--; } return newPos; |