Added support for reading gzipped glabels files.

- Use zlib to uncompress input
This commit is contained in:
Jim Evins
2015-08-25 02:09:18 -04:00
parent 592aa32b90
commit 5dc773579b
4 changed files with 73 additions and 3 deletions
+1
View File
@@ -17,6 +17,7 @@ set (Unique_Package_Name ${Package_Name}-${API_Version})
find_package(Qt4 4.8.4 REQUIRED QtCore QtGui QtXml) find_package(Qt4 4.8.4 REQUIRED QtCore QtGui QtXml)
find_package(ZLIB REQUIRED)
add_definitions (-g) add_definitions (-g)
+2
View File
@@ -93,6 +93,7 @@ include (${QT_USE_FILE})
include_directories ( include_directories (
${ZLIB_INCLUDE_DIRS}
${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}
${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}
${glabels_qt_SOURCE_DIR} ${glabels_qt_SOURCE_DIR}
@@ -107,6 +108,7 @@ add_executable (glabels-qt ${glabels_sources} ${glabels_moc_sources} ${glabels_q
target_link_libraries (glabels-qt target_link_libraries (glabels-qt
libglabels libglabels
${QT_LIBRARIES} ${QT_LIBRARIES}
${ZLIB_LIBRARIES}
) )
+69 -3
View File
@@ -31,6 +31,8 @@
#include "libglabels/XmlUtil.h" #include "libglabels/XmlUtil.h"
#include <QFile> #include <QFile>
#include <QByteArray>
#include <zlib.h>
#include <QtDebug> #include <QtDebug>
@@ -38,20 +40,34 @@ glabels::LabelModel* glabels::XmlLabel::readFile( const QString& fileName )
{ {
QFile file( fileName ); QFile file( fileName );
if ( !file.open( QFile::ReadOnly | QFile::Text) ) if ( !file.open( QFile::ReadOnly ) )
{ {
qWarning() << "Error: Cannot read file " << qPrintable(fileName) qWarning() << "Error: Cannot read file " << qPrintable(fileName)
<< ": " << file.errorString(); << ": " << file.errorString();
return 0; return 0;
} }
QDomDocument doc; QDomDocument doc;
bool success;
QString errorString; QString errorString;
int errorLine; int errorLine;
int errorColumn; int errorColumn;
if ( !doc.setContent( &file, false, &errorString, &errorLine, &errorColumn ) ) QByteArray rawData = file.readAll();
if ( ((rawData[0]&0xFF) == 0x1F) && ((rawData[1]&0xFF) == 0x8b) ) // gzip magic number 0x1F, 0x8B
{
// gzip compressed format
QByteArray unzippedData;
gunzip( rawData, unzippedData );
success = doc.setContent( unzippedData, false, &errorString, &errorLine, &errorColumn );
}
else
{
// plain text
success = doc.setContent( rawData, false, &errorString, &errorLine, &errorColumn );
}
if ( !success )
{ {
qWarning() << "Error: Parse error at line " << errorLine qWarning() << "Error: Parse error at line " << errorLine
<< "column " << errorColumn << "column " << errorColumn
@@ -59,6 +75,7 @@ glabels::LabelModel* glabels::XmlLabel::readFile( const QString& fileName )
return 0; return 0;
} }
QDomElement root = doc.documentElement(); QDomElement root = doc.documentElement();
if ( root.tagName() != "Glabels-document" ) if ( root.tagName() != "Glabels-document" )
{ {
@@ -124,6 +141,55 @@ void glabels::XmlLabel::writeBuffer( const LabelModel* label, QString& buffer )
} }
void glabels::XmlLabel::gunzip( const QByteArray& data, QByteArray& result )
{
result.clear();
if (data.size() <= 4) {
qWarning("XmlLabel::gunzip: Input data is truncated");
return;
}
// setup stream for inflate()
z_stream strm;
strm.zalloc = Z_NULL;
strm.zfree = Z_NULL;
strm.opaque = Z_NULL;
strm.avail_in = data.size();
strm.next_in = (Bytef*)(data.data());
int ret = inflateInit2(&strm, MAX_WBITS + 16); // gzip decoding
if (ret != Z_OK)
{
return;
}
static const int CHUNK_SIZE = 1024;
char out[CHUNK_SIZE];
// run inflate(), one chunk at a time
do {
strm.avail_out = CHUNK_SIZE;
strm.next_out = (Bytef*)(out);
ret = inflate(&strm, Z_NO_FLUSH);
Q_ASSERT(ret != Z_STREAM_ERROR); // state not clobbered
if ( (ret == Z_NEED_DICT) || (ret == Z_DATA_ERROR) || (ret == Z_MEM_ERROR) )
{
// clean up
inflateEnd(&strm);
return;
}
result.append(out, CHUNK_SIZE - strm.avail_out);
} while (strm.avail_out == 0);
// clean up
inflateEnd(&strm);
}
glabels::LabelModel* glabels::XmlLabel::parseRootNode( const QDomElement &node ) glabels::LabelModel* glabels::XmlLabel::parseRootNode( const QDomElement &node )
{ {
using namespace libglabels; using namespace libglabels;
+1
View File
@@ -52,6 +52,7 @@ namespace glabels
static void writeBuffer( const LabelModel* label, QString& buffer ); static void writeBuffer( const LabelModel* label, QString& buffer );
private: private:
static void gunzip( const QByteArray& gzippedData, QByteArray& data );
static LabelModel* parseRootNode( const QDomElement &node ); static LabelModel* parseRootNode( const QDomElement &node );
static void parseObjectsNode( const QDomElement &node, LabelModel* label ); static void parseObjectsNode( const QDomElement &node, LabelModel* label );
static void parseObjectBoxNode( const QDomElement &node, LabelModel* label ); static void parseObjectBoxNode( const QDomElement &node, LabelModel* label );