UnifiedDiffEditor: Move showing diff into separate thread

Before, when all the data was finished, we called showDiff()
in main thread. This consisted of 2 parts:

1. Calculating some extra data and generating actual text
   for UnifiedDiffEditor out of input data.
2. Calling setPlainText() with generated text.

For a really big diffs this could freeze the main thread for a
couple of seconds. Like e.g. 05c35356ab
(initial Creator import) - it contained 7 million characters,
part 1. took about 500 ms and part 2. took about 2.5 seconds.

This two tasks are now done in separate thread.
However, since we can't call TextEditorWidget::setPlainText()
directly from non-GUI thread, we create a separate
TextDocument object in the worker thread, fill it with
generated diff input and move the TextDocument object
into the main thread as a result of async computation.
In main thread we replace TextDocument object of the
TextEditorWidget with the one generated in other thread.
This replacement is very fast.

Change-Id: I49a717ced1dc2d5b8946e0fd6bee244b25071f35
Reviewed-by: David Schulz <david.schulz@qt.io>
Reviewed-by: Orgad Shaneh <orgads@gmail.com>
This commit is contained in:
Jarek Kobus
2022-09-22 13:48:54 +02:00
parent 5c0cafa68e
commit 054d7d65d2
6 changed files with 206 additions and 39 deletions

View File

@@ -6,6 +6,8 @@
#include "selectabletexteditorwidget.h"
#include "diffeditorwidgetcontroller.h"
#include <QFutureWatcher>
namespace Core { class IContext; }
namespace TextEditor {
@@ -38,7 +40,8 @@ public:
class UnifiedDiffData
{
public:
UnifiedDiffOutput showDiff(const DiffEditorInput &input);
UnifiedDiffOutput showDiff(QFutureInterface<void> &fi, int progressMin, int progressMax,
const DiffEditorInput &input);
// block number, visual line number, chunk row number
QMap<int, QPair<int, int>> m_leftLineNumbers;
@@ -67,6 +70,7 @@ class UnifiedDiffEditorWidget final : public SelectableTextEditorWidget
Q_OBJECT
public:
UnifiedDiffEditorWidget(QWidget *parent = nullptr);
~UnifiedDiffEditorWidget();
void setDocument(DiffEditorDocument *document);
DiffEditorDocument *diffDocument() const;
@@ -110,6 +114,16 @@ private:
UnifiedDiffData m_data;
DiffEditorWidgetController m_controller;
QByteArray m_state;
struct ShowResult
{
QSharedPointer<TextEditor::TextDocument> textDocument;
UnifiedDiffData diffData;
QHash<int, int> foldingIndent;
QMap<int, QList<DiffSelection>> selections;
};
std::unique_ptr<QFutureWatcher<ShowResult>> m_watcher;
};
} // namespace Internal