aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSefa Eyeoglu <contact@scrumplex.net>2022-01-28 12:37:22 +0100
committerSefa Eyeoglu <contact@scrumplex.net>2022-01-31 21:40:59 +0100
commita8089b76c0e7961e31b96cdd203e3c345183645b (patch)
tree973a74a6d2cfe0222e1dddcdbf6c706e7794d0e0
parent71516e6c728a6b7429c04f297f6b0f3710bfa3c3 (diff)
downloadPrismLauncher-a8089b76c0e7961e31b96cdd203e3c345183645b.tar.gz
PrismLauncher-a8089b76c0e7961e31b96cdd203e3c345183645b.tar.bz2
PrismLauncher-a8089b76c0e7961e31b96cdd203e3c345183645b.zip
fix: bring back instance exports
-rw-r--r--launcher/MMCZip.cpp60
-rw-r--r--launcher/MMCZip.h18
-rw-r--r--launcher/ui/dialogs/ExportInstanceDialog.cpp11
3 files changed, 85 insertions, 4 deletions
diff --git a/launcher/MMCZip.cpp b/launcher/MMCZip.cpp
index 9b8b7908..90e586d8 100644
--- a/launcher/MMCZip.cpp
+++ b/launcher/MMCZip.cpp
@@ -311,3 +311,63 @@ bool MMCZip::extractFile(QString fileCompressed, QString file, QString target)
}
return MMCZip::extractRelFile(&zip, file, target);
}
+
+bool MMCZip::collectFileListRecursively(const QString& rootDir, const QString& subDir, QFileInfoList *files,
+ MMCZip::FilterFunction excludeFilter) {
+ QDir rootDirectory(rootDir);
+ if (!rootDirectory.exists()) return false;
+
+ QDir directory;
+ if (subDir == nullptr)
+ directory = rootDirectory;
+ else
+ directory = QDir(subDir);
+
+ if (!directory.exists()) return false; // shouldn't ever happen
+
+ // recurse directories
+ QFileInfoList entries = directory.entryInfoList(QDir::AllDirs | QDir::NoDotAndDotDot | QDir::Hidden);
+ for (const auto& e: entries) {
+ if (!collectFileListRecursively(rootDir, e.filePath(), files, excludeFilter))
+ return false;
+ }
+
+ // collect files
+ entries = directory.entryInfoList(QDir::Files);
+ for (const auto& e: entries) {
+ QString relativeFilePath = rootDirectory.relativeFilePath(e.absoluteFilePath());
+ if (excludeFilter && excludeFilter(relativeFilePath)) {
+ qDebug() << "Skipping file " << relativeFilePath;
+ continue;
+ }
+
+ files->append(e.filePath()); // we want the original paths for MMCZip::compressDirFiles
+ }
+ return true;
+}
+
+bool MMCZip::compressDirFiles(QString fileCompressed, QString dir, QFileInfoList files)
+{
+ QuaZip zip(fileCompressed);
+ QDir().mkpath(QFileInfo(fileCompressed).absolutePath());
+ if(!zip.open(QuaZip::mdCreate)) {
+ QFile::remove(fileCompressed);
+ return false;
+ }
+
+ QDir directory(dir);
+ if (!directory.exists()) return false;
+
+ for (auto e : files) {
+ auto filePath = directory.relativeFilePath(e.absoluteFilePath());
+ if( !JlCompress::compressFile(&zip, e.absoluteFilePath(), filePath)) return false;
+ }
+
+ zip.close();
+ if(zip.getZipError()!=0) {
+ QFile::remove(fileCompressed);
+ return false;
+ }
+
+ return true;
+}
diff --git a/launcher/MMCZip.h b/launcher/MMCZip.h
index c8e830ab..29ae2a63 100644
--- a/launcher/MMCZip.h
+++ b/launcher/MMCZip.h
@@ -90,4 +90,22 @@ namespace MMCZip
*/
bool extractFile(QString fileCompressed, QString file, QString dir);
+ /**
+ * Populate a QFileInfoList with a directory tree recursively, while allowing to excludeFilter what shouldn't be included.
+ * \param rootDir directory to start off
+ * \param subDir subdirectory, should be nullptr for first invocation
+ * \param files resulting list of QFileInfo
+ * \param excludeFilter function to excludeFilter which files shouldn't be included (returning true means to excude)
+ * \return true for success or false for failure
+ */
+ bool collectFileListRecursively(const QString &rootDir, const QString &subDir, QFileInfoList *files, FilterFunction excludeFilter);
+
+ /**
+ * Compress directory, by providing a list of files to compress
+ * \param fileCompressed target archive file
+ * \param dir directory that will be compressed (to compress with relative paths)
+ * \param files list of files to compress
+ * \return true for success or false for failure
+ */
+ bool compressDirFiles(QString fileCompressed, QString dir, QFileInfoList files);
}
diff --git a/launcher/ui/dialogs/ExportInstanceDialog.cpp b/launcher/ui/dialogs/ExportInstanceDialog.cpp
index fb9c6542..f3bf7abe 100644
--- a/launcher/ui/dialogs/ExportInstanceDialog.cpp
+++ b/launcher/ui/dialogs/ExportInstanceDialog.cpp
@@ -403,10 +403,13 @@ bool ExportInstanceDialog::doExport()
auto & blocked = proxyModel->blockedPaths();
using std::placeholders::_1;
- QMessageBox::warning(this, tr("Error"), tr("Unable to export instance"));
- return false;
- // TODO Reimplement custom compressDir:
- if (!JlCompress::compressDir(output, m_instance->instanceRoot(), name, std::bind(&SeparatorPrefixTree<'/'>::covers, blocked, _1)))
+ auto files = QFileInfoList();
+ if (!MMCZip::collectFileListRecursively(m_instance->instanceRoot(), nullptr, &files,
+ std::bind(&SeparatorPrefixTree<'/'>::covers, blocked, _1))) {
+ QMessageBox::warning(this, tr("Error"), tr("Unable to export instance"));
+ return false;
+ }
+ if (!MMCZip::compressDirFiles(output, m_instance->instanceRoot(), files))
{
QMessageBox::warning(this, tr("Error"), tr("Unable to export instance"));
return false;