ProjectExplorer: optimize file state highlight in project tree

In general file operations are way more expensive on windows compared to
linux. The current implementation of the modification state highlight of
a file in the project tree tries to get the responsible version control
system in the data function. This is called pretty often and the code
that tries to detect which version control system is used iterates over
a lot of directories. This results in notable hickups when loading and
browsing a fully expanded Qt Creator project tree here.

Reduce the number of file operations by caching the file state inside
the FileNode.

Change-Id: I7d7a82b296494f964ae9259c2e10c1da2ae4aa3a
Reviewed-by: Orgad Shaneh <orgads@gmail.com>
This commit is contained in:
David Schulz
2024-10-14 12:47:56 +02:00
parent bccbaf9a22
commit 2ead91358b
3 changed files with 22 additions and 9 deletions

View File

@@ -471,12 +471,16 @@ void FlatModel::handleProjectAdded(Project *project)
void FlatModel::updateVCStatusFor(const Utils::FilePath root, const QStringList &files)
{
std::for_each(std::begin(files), std::end(files), [root, this](const QString &file) {
const Node *node = ProjectTree::nodeForFile(root.pathAppended(file));
const FilePath filePath = root.pathAppended(file);
Node *node = ProjectTree::nodeForFile(filePath);
if (!node)
return;
FileNode *fileNode = node->asFileNode();
if (!fileNode)
return;
const QModelIndex index = indexForNode(node);
fileNode->resetModificationState();
const QModelIndex index = indexForNode(fileNode);
emit dataChanged(index, index, {Qt::ForegroundRole});
});
}

View File

@@ -266,12 +266,14 @@ Core::IVersionControl::FileState FileNode::modificationState() const
if (isGenerated())
return Core::IVersionControl::FileState::NoModification;
const FilePath file = filePath();
const FilePath dir = file.absolutePath();
if (!m_modificationState) {
const FilePath dir = filePath().absolutePath();
if (Core::IVersionControl *vc = Core::VcsManager::findVersionControlForDirectory(dir))
return vc->modificationState(file);
return Core::IVersionControl::FileState::NoModification;
m_modificationState = vc->modificationState(filePath());
else
m_modificationState = Core::IVersionControl::FileState::NoModification;
}
return *m_modificationState;
}
bool FileNode::useUnavailableMarker() const
@@ -284,6 +286,11 @@ void FileNode::setUseUnavailableMarker(bool useUnavailableMarker)
m_useUnavailableMarker = useUnavailableMarker;
}
void FileNode::resetModificationState()
{
m_modificationState.reset();
}
/*!
Returns \c true if the file is automatically generated by a compile step.
*/

View File

@@ -204,6 +204,7 @@ public:
void setHasError(const bool error) const;
Core::IVersionControl::FileState modificationState() const;
void resetModificationState();
QIcon icon() const;
void setIcon(const QIcon icon);
@@ -213,6 +214,7 @@ public:
private:
FileType m_fileType;
mutable std::optional<Core::IVersionControl::FileState> m_modificationState;
mutable QIcon m_icon;
mutable bool m_hasError = false;
bool m_useUnavailableMarker = false;