File indexing completed on 2024-05-05 03:50:59

0001 // SPDX-License-Identifier: LGPL-2.1-or-later
0002 //
0003 // SPDX-FileCopyrightText: 2011 Thibaut Gridel <tgridel@free.fr>
0004 
0005 #include "KmlRunner.h"
0006 
0007 #include "GeoDataDocument.h"
0008 #include "KmlParser.h"
0009 #include "MarbleDebug.h"
0010 #include <MarbleZipReader.h>
0011 
0012 #include <QBuffer>
0013 #include <QFile>
0014 #include <QFileInfo>
0015 
0016 namespace Marble
0017 {
0018 
0019 KmlRunner::KmlRunner(QObject *parent) :
0020     ParsingRunner(parent)
0021 {
0022 }
0023 
0024 KmlRunner::~KmlRunner()
0025 {
0026 }
0027 
0028 GeoDataDocument *KmlRunner::parseFile(const QString &fileName, DocumentRole role, QString &error)
0029 {
0030     QFile file(fileName);
0031     if (!file.open(QFile::ReadOnly)) {
0032         error = QStringLiteral("Cannot open file %1").arg(fileName);
0033         mDebug() << error;
0034         return nullptr;
0035     }
0036 
0037     QBuffer buffer;
0038     QIODevice* device = nullptr;
0039 
0040     if (fileName.toLower().endsWith(QLatin1String(".kmz"))) {
0041         MarbleZipReader zipReader(&file);
0042 
0043         QStringList kmlFiles;
0044         for(const MarbleZipReader::FileInfo &zipFileInfo : zipReader.fileInfoList()) {
0045             if (zipFileInfo.filePath.toLower().endsWith(QLatin1String(".kml"))) {
0046                 kmlFiles.append(zipFileInfo.filePath);
0047             }
0048         }
0049         if (kmlFiles.empty()) {
0050             error = QStringLiteral("File %1 does not contain any KML files").arg(fileName);
0051             mDebug() << error;
0052             return nullptr;
0053         } else if (kmlFiles.size() > 1) {
0054             mDebug() << QStringLiteral("File %1 contains multiple KML files").arg(fileName);
0055         }
0056 
0057         QByteArray const data = zipReader.fileData(kmlFiles[0]);
0058         buffer.setData(data);
0059         buffer.open(QBuffer::ReadOnly);
0060         device = &buffer;
0061     } else {
0062         device = &file;
0063     }
0064 
0065     KmlParser parser;
0066     if (!parser.read(device)) {
0067         error = parser.errorString();
0068         mDebug() << error;
0069         return nullptr;
0070     }
0071 
0072     GeoDocument* document = parser.releaseDocument();
0073     Q_ASSERT( document );
0074     GeoDataDocument* doc = static_cast<GeoDataDocument*>(document);
0075     doc->setDocumentRole( role );
0076     doc->setFileName(fileName);
0077 
0078     file.close();
0079     return doc;
0080 }
0081 
0082 }
0083 
0084 #include "moc_KmlRunner.cpp"