diff --git a/launcher/FileIgnoreProxy.cpp b/launcher/FileIgnoreProxy.cpp index 1f6b664c2..556e992c2 100644 --- a/launcher/FileIgnoreProxy.cpp +++ b/launcher/FileIgnoreProxy.cpp @@ -262,9 +262,19 @@ bool FileIgnoreProxy::filterAcceptsRow(int sourceRow, const QModelIndex& sourceP QFileSystemModel* fsm = qobject_cast(sourceModel()); auto fileInfo = fsm->fileInfo(index); + return !ignoreFile(fileInfo); +} + +bool FileIgnoreProxy::ignoreFile(QFileInfo fileInfo) const +{ auto fileName = fileInfo.fileName(); auto path = relPath(fileInfo.absoluteFilePath()); - return !(path.startsWith("..") || // just in case ignore files outside the gameroot - std::any_of(m_ignoreFiles.cbegin(), m_ignoreFiles.cend(), [fileName](auto iFileName) { return fileName == iFileName; }) || - std::any_of(m_ignoreFilePaths.cbegin(), m_ignoreFilePaths.cend(), [path](auto iPath) { return path == iPath; })); + return (path.startsWith("..") || // just in case ignore files outside the gameroot + std::any_of(m_ignoreFiles.cbegin(), m_ignoreFiles.cend(), [fileName](auto iFileName) { return fileName == iFileName; }) || + m_ignoreFilePaths.covers(path)); +} + +bool FileIgnoreProxy::filterFile(const QString& fileName) const +{ + return blocked.covers(fileName) || ignoreFile(QFileInfo(QDir(root), fileName)); } diff --git a/launcher/FileIgnoreProxy.h b/launcher/FileIgnoreProxy.h index dbd353e0b..e01a2651e 100644 --- a/launcher/FileIgnoreProxy.h +++ b/launcher/FileIgnoreProxy.h @@ -36,6 +36,7 @@ #pragma once +#include #include #include "SeparatorPrefixTree.h" @@ -66,15 +67,19 @@ class FileIgnoreProxy : public QSortFilterProxyModel { // list of file names that need to be removed completely from model inline QStringList& ignoreFilesWithName() { return m_ignoreFiles; } // list of relative paths that need to be removed completely from model - inline QStringList& ignoreFilesWithPath() { return m_ignoreFilePaths; } + inline SeparatorPrefixTree<'/'>& ignoreFilesWithPath() { return m_ignoreFilePaths; } + + bool filterFile(const QString& fileName) const; protected: bool filterAcceptsColumn(int source_column, const QModelIndex& source_parent) const; bool filterAcceptsRow(int source_row, const QModelIndex& source_parent) const; + bool ignoreFile(QFileInfo file) const; + private: const QString root; SeparatorPrefixTree<'/'> blocked; QStringList m_ignoreFiles; - QStringList m_ignoreFilePaths; + SeparatorPrefixTree<'/'> m_ignoreFilePaths; }; diff --git a/launcher/ui/dialogs/ExportInstanceDialog.cpp b/launcher/ui/dialogs/ExportInstanceDialog.cpp index 8d0e05a20..cc41c394d 100644 --- a/launcher/ui/dialogs/ExportInstanceDialog.cpp +++ b/launcher/ui/dialogs/ExportInstanceDialog.cpp @@ -40,6 +40,7 @@ #include #include #include +#include "FileIgnoreProxy.h" #include "ui_ExportInstanceDialog.h" #include @@ -49,6 +50,7 @@ #include #include #include +#include #include "Application.h" #include "SeparatorPrefixTree.h" @@ -62,7 +64,7 @@ ExportInstanceDialog::ExportInstanceDialog(InstancePtr instance, QWidget* parent proxyModel = new FileIgnoreProxy(root, this); proxyModel->setSourceModel(model); auto prefix = QDir(instance->instanceRoot()).relativeFilePath(instance->gameRoot()); - proxyModel->ignoreFilesWithPath().append({ FS::PathCombine(prefix, "logs"), FS::PathCombine(prefix, "crash-reports") }); + proxyModel->ignoreFilesWithPath().insert({ FS::PathCombine(prefix, "logs"), FS::PathCombine(prefix, "crash-reports") }); proxyModel->ignoreFilesWithName().append({ ".DS_Store", "thumbs.db", "Thumbs.db" }); loadPackIgnore(); @@ -137,11 +139,9 @@ bool ExportInstanceDialog::doExport() SaveIcon(m_instance); - auto & blocked = proxyModel->blockedPaths(); - using std::placeholders::_1; auto files = QFileInfoList(); if (!MMCZip::collectFileListRecursively(m_instance->instanceRoot(), nullptr, &files, - std::bind(&SeparatorPrefixTree<'/'>::covers, blocked, _1))) { + std::bind(&FileIgnoreProxy::filterFile, proxyModel, std::placeholders::_1))) { QMessageBox::warning(this, tr("Error"), tr("Unable to export instance")); return false; } diff --git a/launcher/ui/dialogs/ExportMrPackDialog.cpp b/launcher/ui/dialogs/ExportMrPackDialog.cpp index f1d2610a6..b302f7ba5 100644 --- a/launcher/ui/dialogs/ExportMrPackDialog.cpp +++ b/launcher/ui/dialogs/ExportMrPackDialog.cpp @@ -52,7 +52,7 @@ ExportMrPackDialog::ExportMrPackDialog(InstancePtr instance, QWidget* parent) // use the game root - everything outside cannot be exported const QDir root(instance->gameRoot()); proxy = new FileIgnoreProxy(instance->gameRoot(), this); - proxy->ignoreFilesWithPath().append({ "logs", "crash-reports" }); + proxy->ignoreFilesWithPath().insert({ "logs", "crash-reports" }); proxy->ignoreFilesWithName().append({ ".DS_Store", "thumbs.db", "Thumbs.db" }); proxy->setSourceModel(model); @@ -100,7 +100,7 @@ void ExportMrPackDialog::done(int result) return; ModrinthPackExportTask task(ui->name->text(), ui->version->text(), ui->summary->text(), instance, output, - [this](const QString& path) { return proxy->blockedPaths().covers(path); }); + std::bind(&FileIgnoreProxy::filterFile, proxy, std::placeholders::_1)); connect(&task, &Task::failed, [this](const QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->show(); });