这是indexloc提供的服务,不要输入任何密码
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 20 additions & 6 deletions core_lib/src/qminiz.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,19 +23,33 @@ GNU General Public License for more details.
#include "util.h"


bool MiniZ::isZip(const QString& sZipFilePath)
Status MiniZ::sanityCheck(const QString& sZipFilePath)
{
mz_zip_archive* mz = new mz_zip_archive;
OnScopeExit(delete mz);
mz_zip_zero_struct(mz);
QByteArray utf8Bytes = sZipFilePath.toUtf8();
mz_bool ok = mz_zip_reader_init_file(mz, utf8Bytes.constData(), 0);
if (!ok) return false;
mz_bool readOk = mz_zip_reader_init_file(mz, utf8Bytes.constData(), 0);

int num = mz_zip_reader_get_num_files(mz);
mz_zip_error read_err = mz_zip_get_last_error(mz);

mz_bool closeOk = mz_zip_reader_end(mz);

mz_zip_error close_err = mz_zip_get_last_error(mz);

mz_zip_reader_end(mz);
return (num > 0);
if (!readOk || !closeOk) {
DebugDetails dd;
if (read_err != MZ_ZIP_NO_ERROR) {
dd << QString("Miniz found an error while reading the file. - %1, %2").arg(static_cast<int>(read_err)).arg(mz_zip_get_error_string(read_err));
}
if (close_err != MZ_ZIP_NO_ERROR) {
dd << QString("Miniz found an error while closing file file. - %1, %2").arg(static_cast<int>(close_err)).arg(mz_zip_get_error_string(close_err));
}
return Status(Status::ERROR_MINIZ_FAIL, dd);
}


return Status::OK;
}

size_t MiniZ::istreamReadCallback(void *pOpaque, mz_uint64 file_ofs, void * pBuf, size_t n)
Expand Down
2 changes: 1 addition & 1 deletion core_lib/src/qminiz.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ GNU General Public License for more details.

namespace MiniZ
{
bool isZip(const QString& sZipFilePath);
Status sanityCheck(const QString& sZipFilePath);
size_t istreamReadCallback(void *pOpaque, mz_uint64 file_ofs, void * pBuf, size_t n);
Status compressFolder(QString zipFilePath, QString srcFolderPath, const QStringList& fileList, QString mimetype);
Status uncompressFolder(QString zipFilePath, QString destPath);
Expand Down
72 changes: 56 additions & 16 deletions core_lib/src/structure/filemanager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -50,10 +50,10 @@ Object* FileManager::load(const QString& sFileName)
QString strDataFolder;

// Test file format: new zipped .pclx or old .pcl?
bool oldFormat = isOldForamt(sFileName);
dd << QString("Is old format: ").append(oldFormat ? "true" : "false");
bool isArchive = isArchiveFormat(sFileName);
QString isArchiveStr = "Is archive: " + QString(isArchive);

if (oldFormat)
if (!isArchive)
{
dd << "Recognized Old Pencil2D File Format (*.pcl) !";

Expand All @@ -64,7 +64,15 @@ Object* FileManager::load(const QString& sFileName)
{
dd << "Recognized New zipped Pencil2D File Format (*.pclx) !";

unzip(sFileName, obj->workingDir());
Status sanityCheck = MiniZ::sanityCheck(sFileName);

// Let's check if we can read the file before we try to unzip.
if (!sanityCheck.ok()) {
dd.collect(sanityCheck.details());
} else {
Status unzipStatus = unzip(sFileName, obj->workingDir());
dd.collect(unzipStatus.details());
}

strMainXMLFile = QDir(obj->workingDir()).filePath(PFF_XML_FILE_NAME);
strDataFolder = QDir(obj->workingDir()).filePath(PFF_DATA_DIR);
Expand Down Expand Up @@ -198,9 +206,12 @@ bool FileManager::loadObjectOldWay(Object* object, const QDomElement& root)
return object->loadXML(root, [this] { progressForward(); });
}

bool FileManager::isOldForamt(const QString& fileName) const
bool FileManager::isArchiveFormat(const QString& fileName) const
{
return !(MiniZ::isZip(fileName));
if (QFileInfo(fileName).suffix().compare(PFF_BIG_LETTER_EXTENSION, Qt::CaseInsensitive) != 0) {
return false;
}
return true;
}

Status FileManager::save(const Object* object, const QString& sFileName)
Expand Down Expand Up @@ -255,8 +266,8 @@ Status FileManager::save(const Object* object, const QString& sFileName)
QString sMainXMLFile;
QString sDataFolder;

const bool isOldType = sFileName.endsWith(PFF_OLD_EXTENSION);
if (isOldType)
bool isArchive = isArchiveFormat(sFileName);
if (!isArchive)
{
dd << "Old Pencil2D File Format (*.pcl) !";

Expand All @@ -266,6 +277,7 @@ Status FileManager::save(const Object* object, const QString& sFileName)
else
{
dd << "New zipped Pencil2D File Format (*.pclx) !";
dd.collect(MiniZ::sanityCheck(sFileName).details());

sTempWorkingFolder = object->workingDir();
Q_ASSERT(QDir(sTempWorkingFolder).exists());
Expand Down Expand Up @@ -311,12 +323,17 @@ Status FileManager::save(const Object* object, const QString& sFileName)

progressForward();

if (!isOldType)
if (isArchive)
{
dd << "Miniz";

QString sBackupFile = backupPreviousFile(sFileName);

if (!saveOk) {
return Status(Status::FAIL, dd,
tr("Internal Error"),
tr("An internal error occurred. Your file may not be saved successfully."));
}

dd << "Miniz";
Status stMiniz = MiniZ::compressFolder(sFileName, sTempWorkingFolder, filesToZip, "application/x-pencil2d-pclx");
if (!stMiniz.ok())
{
Expand Down Expand Up @@ -541,16 +558,38 @@ void FileManager::handleOpenProjectError(Status::ErrorCode error, const DebugDet
removePFFTmpDirectory(mstrLastTempFolder);
}

int FileManager::countExistingBackups(const QString& fileName) const
{
QFileInfo fileInfo(fileName);
QDir directory(fileInfo.absoluteDir());
const QString& baseName = fileInfo.completeBaseName();

int backupCount = 0;
for (QFileInfo dirFileInfo : directory.entryInfoList(QDir::Filter::Files)) {
QString searchFileBaseName = dirFileInfo.completeBaseName();
if (baseName.compare(searchFileBaseName) == 0 && searchFileBaseName.contains(PFF_BACKUP_IDENTIFIER)) {
backupCount++;
}
}

return backupCount;
}

QString FileManager::backupPreviousFile(const QString& fileName)
{
if (!QFile::exists(fileName))
return "";

QFileInfo info(fileName);
QString sBackupFile = info.completeBaseName() + ".backup." + info.suffix();
QString sBackupFileFullPath = QDir(info.absolutePath()).filePath(sBackupFile);
QFileInfo fileInfo(fileName);
QString baseName = fileInfo.completeBaseName();

int backupCount = countExistingBackups(fileName) + 1; // start index 1
QString countStr = QString::number(backupCount);

QString sBackupFile = baseName + "." + PFF_BACKUP_IDENTIFIER + countStr + "." + fileInfo.suffix();
QString sBackupFileFullPath = QDir(fileInfo.absolutePath()).filePath(sBackupFile);

bool ok = QFile::rename(info.absoluteFilePath(), sBackupFileFullPath);
bool ok = QFile::copy(fileInfo.absoluteFilePath(), sBackupFileFullPath);
if (!ok)
{
FILEMANAGER_LOG("Cannot backup the previous file");
Expand Down Expand Up @@ -681,7 +720,7 @@ Status FileManager::writePalette(const Object* object, const QString& dataFolder
return Status::OK;
}

void FileManager::unzip(const QString& strZipFile, const QString& strUnzipTarget)
Status FileManager::unzip(const QString& strZipFile, const QString& strUnzipTarget)
{
// removes the previous directory first - better approach
removePFFTmpDirectory(strUnzipTarget);
Expand All @@ -690,6 +729,7 @@ void FileManager::unzip(const QString& strZipFile, const QString& strUnzipTarget
Q_ASSERT(s.ok());

mstrLastTempFolder = strUnzipTarget;
return s;
}

QList<ColorRef> FileManager::loadPaletteFile(QString strFilename)
Expand Down
5 changes: 3 additions & 2 deletions core_lib/src/structure/filemanager.h
Original file line number Diff line number Diff line change
Expand Up @@ -55,11 +55,11 @@ class FileManager : public QObject
void progressRangeChanged(int maxValue);

private:
void unzip(const QString& strZipFile, const QString& strUnzipTarget);
Status unzip(const QString& strZipFile, const QString& strUnzipTarget);

bool loadObject(Object*, const QDomElement& root);
bool loadObjectOldWay(Object*, const QDomElement& root);
bool isOldForamt(const QString& fileName) const;
bool isArchiveFormat(const QString& fileName) const;
bool loadPalette(Object*);
Status writeKeyFrameFiles(const Object* obj, const QString& dataFolder, QStringList& filesWritten);
Status writeMainXml(const Object* obj, const QString& mainXmlPath, QStringList& filesWritten);
Expand All @@ -73,6 +73,7 @@ class FileManager : public QObject

QString backupPreviousFile(const QString& fileName);
void deleteBackupFile(const QString& fileName);
int countExistingBackups(const QString& fileName) const;

void progressForward();

Expand Down
1 change: 1 addition & 0 deletions core_lib/src/util/fileformat.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ GNU General Public License for more details.
#define PFF_OLD_BIG_LETTER_EXTENSION "PCL"
#define PFF_EXTENSION ".pclx"
#define PFF_BIG_LETTER_EXTENSION "PCLX"
#define PFF_BACKUP_IDENTIFIER "backup"

#define PFF_OPEN_PROJECT_EXT_FILTER \
QCoreApplication::translate("FileFormat", "Pencil2D formats") + " (*.pclx *.pcl);;" + QCoreApplication::translate("FileFormat", "Pencil2D Project") + " (*.pclx);;" + QCoreApplication::translate("FileFormat", "Legacy Pencil2D Project") + " (*.pcl)"
Expand Down