Is it possible to compress PDF using QT?
-
I create a pdf containing images using QPdfWriter and QPainter, but the pdf size is too large. I'm trying to find a way to compress it so it takes less space. Is it possible to do it in Qt?
@netpulsar Do you mean to compress the whole PDF file?
-
@netpulsar
You could link with a compression library. zlib is generic for C++, I believe Quazip is integrated Qt compression. Or just run an external compressor on the file. You talk aboutQPdfWriter
so it's not clear where you want to put the reading side for the compressed file. A PDF file containing images is still likely to be "large". -
Apologies for my unclear question. I want to compress the pdf file but to a pdf format and I want my Qt application to do it. I don't want to use an external compressor.
Basically I have charts drawn in my Qt app and I need to save them to a pdf file. I do it using Item::grabToImage(). Here is a sample of my code. Maybe you know a way to do it so the resulting pdf has a smaller size?
void PdfExporter::saveToPdf(QQuickItem *chartItem,
QString fileName,
bool start,
int maxValue,
QString aisleName,
QString aChartTypeName)
{
qDebug() << "START" << Qt::endl;
if (chartItem) {
if (start) {
#if linux
fileName.replace(0, strlen("file://"), "");
#else
fileName.replace(0, strlen("file:///"), "");
#endif
mFileName = fileName;
mPdfWriter = new QPdfWriter(fileName);
mPdfWriter->setPageSize(QPageSize::A4);
mPdfWriter->setResolution(300);mPainter.begin(mPdfWriter); mMoveBy = 200; mMaxNumberOfSliderMoves = maxValue; mCurrentNumberOfSliderMoves = 0; } QCoreApplication::processEvents(); QSize imageSize(5760, 1620); mGrabResult = chartItem->grabToImage(imageSize); if (mGrabResult.get() != nullptr) { connect(mGrabResult.get(), &QQuickItemGrabResult::ready, this, [this, aisleName, aChartTypeName]() { QImage image = mGrabResult->image().scaledToWidth(mPdfWriter->width()); if (aisleName != nullptr) { mPainter.setFont(QFont("Helvetica", 11)); mPainter.drawText(20, 160, aisleName); } if (aChartTypeName != nullptr) { mPainter.setFont(QFont("Helvetica", 7)); mPainter.drawText(image.width() / 2 - 160, mMoveBy - 10, aChartTypeName); } mPainter.drawImage(0, mMoveBy, image); mMoveBy += image.height() + 80; mGrabResult.get()->disconnect(); emit nextChartSignal(); }); } }
}
-
Apologies for my unclear question. I want to compress the pdf file but to a pdf format and I want my Qt application to do it. I don't want to use an external compressor.
Basically I have charts drawn in my Qt app and I need to save them to a pdf file. I do it using Item::grabToImage(). Here is a sample of my code. Maybe you know a way to do it so the resulting pdf has a smaller size?
void PdfExporter::saveToPdf(QQuickItem *chartItem,
QString fileName,
bool start,
int maxValue,
QString aisleName,
QString aChartTypeName)
{
qDebug() << "START" << Qt::endl;
if (chartItem) {
if (start) {
#if linux
fileName.replace(0, strlen("file://"), "");
#else
fileName.replace(0, strlen("file:///"), "");
#endif
mFileName = fileName;
mPdfWriter = new QPdfWriter(fileName);
mPdfWriter->setPageSize(QPageSize::A4);
mPdfWriter->setResolution(300);mPainter.begin(mPdfWriter); mMoveBy = 200; mMaxNumberOfSliderMoves = maxValue; mCurrentNumberOfSliderMoves = 0; } QCoreApplication::processEvents(); QSize imageSize(5760, 1620); mGrabResult = chartItem->grabToImage(imageSize); if (mGrabResult.get() != nullptr) { connect(mGrabResult.get(), &QQuickItemGrabResult::ready, this, [this, aisleName, aChartTypeName]() { QImage image = mGrabResult->image().scaledToWidth(mPdfWriter->width()); if (aisleName != nullptr) { mPainter.setFont(QFont("Helvetica", 11)); mPainter.drawText(20, 160, aisleName); } if (aChartTypeName != nullptr) { mPainter.setFont(QFont("Helvetica", 7)); mPainter.drawText(image.width() / 2 - 160, mMoveBy - 10, aChartTypeName); } mPainter.drawImage(0, mMoveBy, image); mMoveBy += image.height() + 80; mGrabResult.get()->disconnect(); emit nextChartSignal(); }); } }
}
@netpulsar
The first thing I would test is simply create the original PDF and ZIP the whole file externally. How much does that save? Because if it's not much you won't achieve better than that.I see references that something like Adobe Acrobat Pro has various compression options when producing PDF. Don't know how good they are, may be good for images. But I don't think
QPdfWriter
is going to offer this. One suggestion is to reduce resolution to 150. -
Changing the DPI to 150 makes the image quality really bad, I tried 200 and it kinda helped, reduced the size by about 30%. I tried to ZIP the whole file and in compressed the size was about half. But I don't want to have it zipped I just want to reduce the size of the pdf. There are pdf compressors online and they reduce my pdf file by 90% but I want to do it with my Qt app. If it can be done online I guess there should be a way to do it with C++ also.
-
Changing the DPI to 150 makes the image quality really bad, I tried 200 and it kinda helped, reduced the size by about 30%. I tried to ZIP the whole file and in compressed the size was about half. But I don't want to have it zipped I just want to reduce the size of the pdf. There are pdf compressors online and they reduce my pdf file by 90% but I want to do it with my Qt app. If it can be done online I guess there should be a way to do it with C++ also.
@netpulsar said in Is it possible to compress PDF using QT?:
I guess there should be a way to do it with C++
Yes, but currently not with QtPdf afaics.
-
@netpulsar said in Is it possible to compress PDF using QT?:
I guess there should be a way to do it with C++
Yes, but currently not with QtPdf afaics.
@Christian-Ehrlicher , @netpulsar
I saidQuaZip
earlier.
QPdfWriter::QPdfWriter(QIODevice *device) writes to aQIODevice
.
QuaZip
's QuaZIODevice Class providesQIODevice
to compress/decompress.
Put those two together and you should be able to read/write (from Qt QuaZip) a compressed PDF. -
@Christian-Ehrlicher , @netpulsar
I saidQuaZip
earlier.
QPdfWriter::QPdfWriter(QIODevice *device) writes to aQIODevice
.
QuaZip
's QuaZIODevice Class providesQIODevice
to compress/decompress.
Put those two together and you should be able to read/write (from Qt QuaZip) a compressed PDF.@netpulsar
I've used 7zip (with QProcess) and it's much faster than QuaZip. But of course there will be no pdf file as a result.
https://www.7-zip.org/download.html -
The most likely reason why the PDF is so large is because your chart is saved as a bitmap, i.e. individual pixels. PDFs can also store vector graphics which will be a lot more space efficient. But, I am not sure how this could be achieved with QPdfWriter.
Bitmaps inside PDFs can also be stored in a compressed format. Maybe it would help drawing to a QPixmap, saving it as PNG (or similar) and embedding that file into the PDF. Again, I am not sure how this could be achieved with QPdfWriter.