aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Schulz <david.schulz@qt.io>2019-11-28 13:03:32 +0100
committerDavid Schulz <david.schulz@qt.io>2020-02-10 14:09:38 +0000
commite85d6b363bd039c4407bbf5367cce0efdd559945 (patch)
tree4c997d75bed34e5fc100eb1ae411fb70eb034420
parentc522ceb7dd678df063db930288c9d269ee464e13 (diff)
Editor: Improve splitting format range performance
Instead of copying the list and move some items individualy from one list to the other use Utils::partition. Fixes: QTCREATORBUG-23281 Change-Id: Iaf9430c041aa916feecf9214303ba30f17290ba8 Reviewed-by: Eike Ziller <eike.ziller@qt.io>
-rw-r--r--src/plugins/texteditor/syntaxhighlighter.cpp50
1 files changed, 21 insertions, 29 deletions
diff --git a/src/plugins/texteditor/syntaxhighlighter.cpp b/src/plugins/texteditor/syntaxhighlighter.cpp
index b28ac1ee18..bfa0f85a86 100644
--- a/src/plugins/texteditor/syntaxhighlighter.cpp
+++ b/src/plugins/texteditor/syntaxhighlighter.cpp
@@ -78,13 +78,13 @@ public:
bool noAutomaticHighlighting = false;
};
-static bool adjustRange(QTextLayout::FormatRange &range, int from, int charsRemoved, int charsAdded) {
-
+static bool adjustRange(QTextLayout::FormatRange &range, int from, int charsDelta)
+{
if (range.start >= from) {
- range.start += charsAdded - charsRemoved;
+ range.start += charsDelta;
return true;
} else if (range.start + range.length > from) {
- range.length += charsAdded - charsRemoved;
+ range.length += charsDelta;
return true;
}
return false;
@@ -105,32 +105,24 @@ void SyntaxHighlighterPrivate::applyFormatChanges(int from, int charsRemoved, in
QTextLayout *layout = currentBlock.layout();
- QVector<QTextLayout::FormatRange> ranges = layout->formats();
-
- bool doAdjustRange = currentBlock.contains(from);
-
- QVector<QTextLayout::FormatRange> old_ranges;
+ QVector<QTextLayout::FormatRange> ranges;
+ QVector<QTextLayout::FormatRange> oldRanges;
+ std::tie(ranges, oldRanges)
+ = Utils::partition(layout->formats(), [](const QTextLayout::FormatRange &range) {
+ return range.format.property(QTextFormat::UserProperty).toBool();
+ });
- if (!ranges.isEmpty()) {
- auto it = ranges.begin();
- while (it != ranges.end()) {
- if (it->format.property(QTextFormat::UserProperty).toBool()) {
- if (doAdjustRange)
- formatsChanged = adjustRange(*it, from - currentBlock.position(), charsRemoved, charsAdded)
- || formatsChanged;
- ++it;
- } else {
- old_ranges.append(*it);
- it = ranges.erase(it);
- }
- }
+ if (currentBlock.contains(from)) {
+ const int charsDelta = charsAdded - charsRemoved;
+ for (QTextLayout::FormatRange &range : ranges)
+ formatsChanged |= adjustRange(range, from - currentBlock.position(), charsDelta);
}
QTextCharFormat emptyFormat;
QTextLayout::FormatRange r;
- QVector<QTextLayout::FormatRange> new_ranges;
+ QVector<QTextLayout::FormatRange> newRanges;
int i = 0;
while (i < formatChanges.count()) {
@@ -148,19 +140,19 @@ void SyntaxHighlighterPrivate::applyFormatChanges(int from, int charsRemoved, in
r.length = i - r.start;
- new_ranges << r;
+ newRanges << r;
}
- formatsChanged = formatsChanged || (new_ranges.size() != old_ranges.size());
+ formatsChanged = formatsChanged || (newRanges.size() != oldRanges.size());
- for (int i = 0; !formatsChanged && i < new_ranges.size(); ++i) {
- const QTextLayout::FormatRange &o = old_ranges.at(i);
- const QTextLayout::FormatRange &n = new_ranges.at(i);
+ for (int i = 0; !formatsChanged && i < newRanges.size(); ++i) {
+ const QTextLayout::FormatRange &o = oldRanges.at(i);
+ const QTextLayout::FormatRange &n = newRanges.at(i);
formatsChanged = (o.start != n.start || o.length != n.length || o.format != n.format);
}
if (formatsChanged) {
- ranges.append(new_ranges);
+ ranges.append(newRanges);
layout->setFormats(ranges);
doc->markContentsDirty(currentBlock.position(), currentBlock.length());
}