Make QgsLayoutExporter::generateFileName virtual, so exporter

subclasses can be made which customise the generated file names
This commit is contained in:
Nyall Dawson 2017-12-11 18:50:28 +10:00
parent 48b6e02c8f
commit 8b1e057d2c
4 changed files with 102 additions and 11 deletions

View File

@ -21,11 +21,42 @@ class QgsLayoutExporter
%End %End
public: public:
struct PageExportDetails
{
QString directory;
%Docstring
Target folder
%End
QString baseName;
%Docstring
Base part of filename (i.e. file name without extension or '.')
%End
QString extension;
%Docstring
File suffix/extension (without the leading '.')
%End
int page;
%Docstring
Page number, where 0 = first page.
%End
};
QgsLayoutExporter( QgsLayout *layout ); QgsLayoutExporter( QgsLayout *layout );
%Docstring %Docstring
Constructor for QgsLayoutExporter, for the specified ``layout``. Constructor for QgsLayoutExporter, for the specified ``layout``.
%End %End
virtual ~QgsLayoutExporter();
QgsLayout *layout() const;
%Docstring
Returns the layout linked to this exporter.
:rtype: QgsLayout
%End
void renderPage( QPainter *painter, int page ) const; void renderPage( QPainter *painter, int page ) const;
%Docstring %Docstring
Renders a full page to a destination ``painter``. Renders a full page to a destination ``painter``.
@ -207,6 +238,15 @@ Resolution to export layout at
The ``dpi`` argument can be set to the actual DPI of exported file, or left as -1 to use the layout's default DPI. The ``dpi`` argument can be set to the actual DPI of exported file, or left as -1 to use the layout's default DPI.
%End %End
protected:
virtual QString generateFileName( const PageExportDetails &details ) const;
%Docstring
Generates the file name for a page during export.
Subclasses can override this method to customise page file naming.
:rtype: str
%End
}; };

View File

@ -31,6 +31,11 @@ QgsLayoutExporter::QgsLayoutExporter( QgsLayout *layout )
} }
QgsLayout *QgsLayoutExporter::layout() const
{
return mLayout;
}
void QgsLayoutExporter::renderPage( QPainter *painter, int page ) const void QgsLayoutExporter::renderPage( QPainter *painter, int page ) const
{ {
if ( !mLayout ) if ( !mLayout )
@ -169,9 +174,11 @@ QgsLayoutExporter::ExportResult QgsLayoutExporter::exportToImage( const QString
} }
QFileInfo fi( filePath ); QFileInfo fi( filePath );
QString path = fi.path();
QString baseName = fi.baseName(); PageExportDetails pageDetails;
QString extension = fi.completeSuffix(); pageDetails.directory = fi.path();
pageDetails.baseName = fi.baseName();
pageDetails.extension = fi.completeSuffix();
LayoutContextSettingsRestorer dpiRestorer( mLayout ); LayoutContextSettingsRestorer dpiRestorer( mLayout );
( void )dpiRestorer; ( void )dpiRestorer;
@ -207,7 +214,8 @@ QgsLayoutExporter::ExportResult QgsLayoutExporter::exportToImage( const QString
if ( skip ) if ( skip )
continue; // should skip this page, e.g. null size continue; // should skip this page, e.g. null size
QString outputFilePath = generateFileName( path, baseName, extension, page ); pageDetails.page = page;
QString outputFilePath = generateFileName( pageDetails );
if ( image.isNull() ) if ( image.isNull() )
{ {
@ -215,7 +223,7 @@ QgsLayoutExporter::ExportResult QgsLayoutExporter::exportToImage( const QString
return MemoryError; return MemoryError;
} }
if ( !saveImage( image, outputFilePath, extension ) ) if ( !saveImage( image, outputFilePath, pageDetails.extension ) )
{ {
mErrorFileName = outputFilePath; mErrorFileName = outputFilePath;
return FileError; return FileError;
@ -509,15 +517,15 @@ QImage QgsLayoutExporter::createImage( const QgsLayoutExporter::ImageExportSetti
} }
} }
QString QgsLayoutExporter::generateFileName( const QString &path, const QString &baseName, const QString &suffix, int page ) const QString QgsLayoutExporter::generateFileName( const PageExportDetails &details ) const
{ {
if ( page == 0 ) if ( details.page == 0 )
{ {
return path + '/' + baseName + '.' + suffix; return details.directory + '/' + details.baseName + '.' + details.extension;
} }
else else
{ {
return path + '/' + baseName + '_' + QString::number( page + 1 ) + '.' + suffix; return details.directory + '/' + details.baseName + '_' + QString::number( details.page + 1 ) + '.' + details.extension;
} }
} }

View File

@ -38,11 +38,34 @@ class CORE_EXPORT QgsLayoutExporter
public: public:
//! Contains details of a page being exported by the class
struct PageExportDetails
{
//! Target folder
QString directory;
//! Base part of filename (i.e. file name without extension or '.')
QString baseName;
//! File suffix/extension (without the leading '.')
QString extension;
//! Page number, where 0 = first page.
int page = 0;
};
/** /**
* Constructor for QgsLayoutExporter, for the specified \a layout. * Constructor for QgsLayoutExporter, for the specified \a layout.
*/ */
QgsLayoutExporter( QgsLayout *layout ); QgsLayoutExporter( QgsLayout *layout );
virtual ~QgsLayoutExporter() = default;
/**
* Returns the layout linked to this exporter.
*/
QgsLayout *layout() const;
/** /**
* Renders a full page to a destination \a painter. * Renders a full page to a destination \a painter.
* *
@ -219,6 +242,14 @@ class CORE_EXPORT QgsLayoutExporter
*/ */
void computeWorldFileParameters( const QRectF &region, double &a, double &b, double &c, double &d, double &e, double &f, double dpi = -1 ) const; void computeWorldFileParameters( const QRectF &region, double &a, double &b, double &c, double &d, double &e, double &f, double dpi = -1 ) const;
protected:
/**
* Generates the file name for a page during export.
*
* Subclasses can override this method to customise page file naming.
*/
virtual QString generateFileName( const PageExportDetails &details ) const;
private: private:
@ -228,8 +259,6 @@ class CORE_EXPORT QgsLayoutExporter
QImage createImage( const ImageExportSettings &settings, int page, QRectF &bounds, bool &skipPage ) const; QImage createImage( const ImageExportSettings &settings, int page, QRectF &bounds, bool &skipPage ) const;
QString generateFileName( const QString &path, const QString &baseName, const QString &suffix, int page ) const;
/** /**
* Saves an image to a file, possibly using format specific options (e.g. LZW compression for tiff) * Saves an image to a file, possibly using format specific options (e.g. LZW compression for tiff)
*/ */

View File

@ -317,6 +317,20 @@ class TestQgsLayoutExporter(unittest.TestCase):
self.assertAlmostEqual(values[4], 1925.000000000000, 2) self.assertAlmostEqual(values[4], 1925.000000000000, 2)
self.assertAlmostEqual(values[5], 3050.000000000000, 2) self.assertAlmostEqual(values[5], 3050.000000000000, 2)
def testPageFileName(self):
l = QgsLayout(QgsProject.instance())
exporter = QgsLayoutExporter(l)
details = QgsLayoutExporter.PageExportDetails()
details.directory = '/tmp/output'
details.baseName = 'my_maps'
details.extension = 'png'
details.page = 0
self.assertEqual(exporter.generateFileName(details), '/tmp/output/my_maps.png')
details.page = 1
self.assertEqual(exporter.generateFileName(details), '/tmp/output/my_maps_2.png')
details.page = 2
self.assertEqual(exporter.generateFileName(details), '/tmp/output/my_maps_3.png')
if __name__ == '__main__': if __name__ == '__main__':
unittest.main() unittest.main()