27 #include <QImageWriter>
31 QString QgsLayoutAtlasToImageAlgorithm::name()
const
33 return QStringLiteral(
"atlaslayouttoimage" );
36 QString QgsLayoutAtlasToImageAlgorithm::displayName()
const
38 return QObject::tr(
"Export atlas layout as image" );
41 QStringList QgsLayoutAtlasToImageAlgorithm::tags()
const
43 return QObject::tr(
"layout,atlas,composer,composition,save,png,jpeg,jpg" ).split(
',' );
46 QString QgsLayoutAtlasToImageAlgorithm::group()
const
48 return QObject::tr(
"Cartography" );
51 QString QgsLayoutAtlasToImageAlgorithm::groupId()
const
53 return QStringLiteral(
"cartography" );
56 QString QgsLayoutAtlasToImageAlgorithm::shortDescription()
const
58 return QObject::tr(
"Exports an atlas layout as a set of images." );
61 QString QgsLayoutAtlasToImageAlgorithm::shortHelpString()
const
63 return QObject::tr(
"This algorithm outputs an atlas layout to a set of image files (e.g. PNG or JPEG images).\n\n"
64 "If a coverage layer is set, the selected layout's atlas settings exposed in this algorithm "
65 "will be overwritten. In this case, an empty filter or sort by expression will turn those "
69 void QgsLayoutAtlasToImageAlgorithm::initAlgorithm(
const QVariantMap & )
74 addParameter(
new QgsProcessingParameterExpression( QStringLiteral(
"FILTER_EXPRESSION" ), QObject::tr(
"Filter expression" ), QString(), QStringLiteral(
"COVERAGE_LAYER" ),
true ) );
75 addParameter(
new QgsProcessingParameterExpression( QStringLiteral(
"SORTBY_EXPRESSION" ), QObject::tr(
"Sort expression" ), QString(), QStringLiteral(
"COVERAGE_LAYER" ),
true ) );
76 addParameter(
new QgsProcessingParameterBoolean( QStringLiteral(
"SORTBY_REVERSE" ), QObject::tr(
"Reverse sort order (used when a sort expression is provided)" ),
false,
true ) );
78 addParameter(
new QgsProcessingParameterExpression( QStringLiteral(
"FILENAME_EXPRESSION" ), QObject::tr(
"Output filename expression" ), QStringLiteral(
"'output_'||@atlas_featurenumber" ), QStringLiteral(
"COVERAGE_LAYER" ) ) );
82 std::unique_ptr< QgsProcessingParameterMultipleLayers > layersParam = std::make_unique< QgsProcessingParameterMultipleLayers>( QStringLiteral(
"LAYERS" ), QObject::tr(
"Map layers to assign to unlocked map item(s)" ),
QgsProcessing::TypeMapLayer, QVariant(),
true );
84 addParameter( layersParam.release() );
86 QStringList imageFormats;
87 const QList<QByteArray> supportedImageFormats { QImageWriter::supportedImageFormats() };
88 for (
const QByteArray &format : supportedImageFormats )
90 if ( format == QByteArray(
"svg" ) )
92 imageFormats << QString( format );
94 std::unique_ptr< QgsProcessingParameterEnum > extensionParam = std::make_unique< QgsProcessingParameterEnum >( QStringLiteral(
"EXTENSION" ), QObject::tr(
"Image format" ), imageFormats,
false, imageFormats.indexOf( QLatin1String(
"png" ) ) );
96 addParameter( extensionParam.release() );
98 std::unique_ptr< QgsProcessingParameterNumber > dpiParam = std::make_unique< QgsProcessingParameterNumber >( QStringLiteral(
"DPI" ), QObject::tr(
"DPI (leave blank for default layout DPI)" ),
QgsProcessingParameterNumber::Double, QVariant(),
true, 0 );
100 addParameter( dpiParam.release() );
102 std::unique_ptr< QgsProcessingParameterBoolean > appendGeorefParam = std::make_unique< QgsProcessingParameterBoolean >( QStringLiteral(
"GEOREFERENCE" ), QObject::tr(
"Generate world file" ),
true );
104 addParameter( appendGeorefParam.release() );
106 std::unique_ptr< QgsProcessingParameterBoolean > exportRDFParam = std::make_unique< QgsProcessingParameterBoolean >( QStringLiteral(
"INCLUDE_METADATA" ), QObject::tr(
"Export RDF metadata (title, author, etc.)" ),
true );
108 addParameter( exportRDFParam.release() );
110 std::unique_ptr< QgsProcessingParameterBoolean > antialias = std::make_unique< QgsProcessingParameterBoolean >( QStringLiteral(
"ANTIALIAS" ), QObject::tr(
"Enable antialiasing" ),
true );
112 addParameter( antialias.release() );
115 QgsProcessingAlgorithm::Flags QgsLayoutAtlasToImageAlgorithm::flags()
const
120 QgsLayoutAtlasToImageAlgorithm *QgsLayoutAtlasToImageAlgorithm::createInstance()
const
122 return new QgsLayoutAtlasToImageAlgorithm();
128 QgsPrintLayout *l = parameterAsLayout( parameters, QStringLiteral(
"LAYOUT" ), context );
130 throw QgsProcessingException( QObject::tr(
"Cannot find layout with name \"%1\"" ).arg( parameters.value( QStringLiteral(
"LAYOUT" ) ).toString() ) );
132 std::unique_ptr< QgsPrintLayout > layout( l->
clone() );
135 QString expression, error;
136 QgsVectorLayer *layer = parameterAsVectorLayer( parameters, QStringLiteral(
"COVERAGE_LAYER" ), context );
142 expression = parameterAsString( parameters, QStringLiteral(
"FILTER_EXPRESSION" ), context );
145 if ( !expression.isEmpty() && !error.isEmpty() )
151 expression = parameterAsString( parameters, QStringLiteral(
"SORTBY_EXPRESSION" ), context );
152 if ( !expression.isEmpty() )
154 const bool sortByReverse = parameterAsBool( parameters, QStringLiteral(
"SORTBY_REVERSE" ), context );
169 expression = parameterAsString( parameters, QStringLiteral(
"FILENAME_EXPRESSION" ), context );
171 if ( !error.isEmpty() )
176 const QString directory = parameterAsFileOutput( parameters, QStringLiteral(
"FOLDER" ), context );
177 const QString fileName = QDir( directory ).filePath( QStringLiteral(
"atlas" ) );
179 QStringList imageFormats;
180 const QList<QByteArray> supportedImageFormats { QImageWriter::supportedImageFormats() };
181 for (
const QByteArray &format : supportedImageFormats )
183 if ( format == QByteArray(
"svg" ) )
185 imageFormats << QString( format );
187 const int idx = parameterAsEnum( parameters, QStringLiteral(
"EXTENSION" ), context );
188 const QString extension =
'.' + imageFormats.at( idx );
192 if ( parameters.value( QStringLiteral(
"DPI" ) ).isValid() )
194 settings.
dpi = parameterAsDouble( parameters, QStringLiteral(
"DPI" ), context );
197 settings.
exportMetadata = parameterAsBool( parameters, QStringLiteral(
"INCLUDE_METADATA" ), context );
198 settings.
generateWorldFile = parameterAsBool( parameters, QStringLiteral(
"GEOREFERENCE" ), context );
200 if ( parameterAsBool( parameters, QStringLiteral(
"ANTIALIAS" ), context ) )
207 const QList< QgsMapLayer * > layers = parameterAsLayerList( parameters, QStringLiteral(
"LAYERS" ), context );
208 if ( layers.size() > 0 )
210 const QList<QGraphicsItem *> items = layout->items();
211 for ( QGraphicsItem *graphicsItem : items )
225 feedback->
pushInfo( QObject::tr(
"Exporting %n atlas feature(s)",
"", atlas->
count() ) );
230 feedback->
pushInfo( QObject::tr(
"Successfully exported layout to %1" ).arg( QDir::toNativeSeparators( directory ) ) );
235 throw QgsProcessingException( QObject::tr(
"Cannot write to %1.\n\nThis file may be open in another application." ).arg( QDir::toNativeSeparators( directory ) ) );
239 "resulted in a memory overflow.\n\n"
240 "Please try a lower resolution or a smaller paper size." ) );
254 feedback->
reportError( QObject::tr(
"No atlas features found" ) );
260 outputs.insert( QStringLiteral(
"FOLDER" ), directory );