Skip to content

Commit 4ae9241

Browse files
committed
[processing] Allow providers to determine default vector/raster file
to use for their algorithm's parameters Because some providers do not have support for all output types, we need to give providers a way to restrict the default format choices to those which are supported by the provider.
1 parent 2a280d6 commit 4ae9241

File tree

7 files changed

+186
-13
lines changed

7 files changed

+186
-13
lines changed

python/core/processing/qgsprocessingparameters.sip

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -357,9 +357,18 @@ class QgsProcessingParameterDefinition
357357
%Docstring
358358
Returns a pointer to the algorithm which owns this parameter. May be None
359359
for non-owned parameters.
360+
.. seealso:: provider()
360361
:rtype: QgsProcessingAlgorithm
361362
%End
362363

364+
QgsProcessingProvider *provider() const;
365+
%Docstring
366+
Returns a pointer to the provider for the algorithm which owns this parameter. May be None
367+
for non-owned parameters or algorithms.
368+
.. seealso:: algorithm()
369+
:rtype: QgsProcessingProvider
370+
%End
371+
363372
protected:
364373

365374

python/core/processing/qgsprocessingprovider.sip

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,7 @@ class QgsProcessingProvider : QObject
101101
virtual QStringList supportedOutputVectorLayerExtensions() const;
102102
%Docstring
103103
Returns a list of the vector format file extensions supported by this provider.
104+
.. seealso:: defaultVectorFileExtension()
104105
.. seealso:: supportedOutputRasterLayerExtensions()
105106
.. seealso:: supportedOutputTableExtensions()
106107
.. seealso:: supportsNonFileBasedOutput()
@@ -115,6 +116,35 @@ class QgsProcessingProvider : QObject
115116
:rtype: list of str
116117
%End
117118

119+
virtual QString defaultVectorFileExtension( bool hasGeometry = true ) const;
120+
%Docstring
121+
Returns the default file extension to use for vector outputs created by the
122+
provider.
123+
124+
If ``hasGeometry`` is true then the output file format must have support for
125+
geometry. If ``hasGeometry`` is false then non-spatial formats can be used.
126+
127+
The default implementation returns the user's default Processing vector output format
128+
setting.
129+
130+
.. seealso:: supportedOutputVectorLayerExtensions()
131+
.. seealso:: defaultRasterFileExtension()
132+
:rtype: str
133+
%End
134+
135+
virtual QString defaultRasterFileExtension() const;
136+
%Docstring
137+
Returns the default file extension to use for raster outputs created by the
138+
provider.
139+
140+
The default implementation returns the user's default Processing raster output format
141+
setting.
142+
143+
.. seealso:: supportedOutputRasterLayerExtensions()
144+
.. seealso:: defaultVectorFileExtension()
145+
:rtype: str
146+
%End
147+
118148
virtual bool supportsNonFileBasedOutput() const;
119149
%Docstring
120150
Returns true if the provider supports non-file based outputs (such as memory layers

src/core/processing/qgsprocessingparameters.cpp

Lines changed: 38 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,10 @@
1616
***************************************************************************/
1717

1818
#include "qgsprocessingparameters.h"
19+
#include "qgsprocessingprovider.h"
1920
#include "qgsprocessingcontext.h"
2021
#include "qgsprocessingutils.h"
22+
#include "qgsprocessingalgorithm.h"
2123
#include "qgsvectorlayerfeatureiterator.h"
2224
#include "qgsprocessingoutputs.h"
2325
#include "qgssettings.h"
@@ -1242,6 +1244,11 @@ QgsProcessingAlgorithm *QgsProcessingParameterDefinition::algorithm() const
12421244
return mAlgorithm;
12431245
}
12441246

1247+
QgsProcessingProvider *QgsProcessingParameterDefinition::provider() const
1248+
{
1249+
return mAlgorithm ? mAlgorithm->provider() : nullptr;
1250+
}
1251+
12451252
QgsProcessingParameterBoolean::QgsProcessingParameterBoolean( const QString &name, const QString &description, const QVariant &defaultValue, bool optional )
12461253
: QgsProcessingParameterDefinition( name, description, defaultValue, optional )
12471254
{}
@@ -3092,14 +3099,21 @@ QgsProcessingOutputDefinition *QgsProcessingParameterFeatureSink::toOutputDefini
30923099

30933100
QString QgsProcessingParameterFeatureSink::defaultFileExtension() const
30943101
{
3095-
QgsSettings settings;
3096-
if ( hasGeometry() )
3102+
if ( QgsProcessingProvider *p = provider() )
30973103
{
3098-
return settings.value( QStringLiteral( "Processing/DefaultOutputVectorLayerExt" ), QStringLiteral( "shp" ), QgsSettings::Core ).toString();
3104+
return p->defaultVectorFileExtension( hasGeometry() );
30993105
}
31003106
else
31013107
{
3102-
return QStringLiteral( "dbf" );
3108+
QgsSettings settings;
3109+
if ( hasGeometry() )
3110+
{
3111+
return settings.value( QStringLiteral( "Processing/DefaultOutputVectorLayerExt" ), QStringLiteral( "shp" ), QgsSettings::Core ).toString();
3112+
}
3113+
else
3114+
{
3115+
return QStringLiteral( "dbf" );
3116+
}
31033117
}
31043118
}
31053119

@@ -3245,8 +3259,15 @@ QgsProcessingOutputDefinition *QgsProcessingParameterRasterDestination::toOutput
32453259

32463260
QString QgsProcessingParameterRasterDestination::defaultFileExtension() const
32473261
{
3248-
QgsSettings settings;
3249-
return settings.value( QStringLiteral( "Processing/DefaultOutputRasterLayerExt" ), QStringLiteral( "tif" ), QgsSettings::Core ).toString();
3262+
if ( QgsProcessingProvider *p = provider() )
3263+
{
3264+
return p->defaultRasterFileExtension();
3265+
}
3266+
else
3267+
{
3268+
QgsSettings settings;
3269+
return settings.value( QStringLiteral( "Processing/DefaultOutputRasterLayerExt" ), QStringLiteral( "tif" ), QgsSettings::Core ).toString();
3270+
}
32503271
}
32513272

32523273
QgsProcessingParameterRasterDestination *QgsProcessingParameterRasterDestination::fromScriptCode( const QString &name, const QString &description, bool isOptional, const QString &definition )
@@ -3541,14 +3562,21 @@ QgsProcessingOutputDefinition *QgsProcessingParameterVectorDestination::toOutput
35413562

35423563
QString QgsProcessingParameterVectorDestination::defaultFileExtension() const
35433564
{
3544-
QgsSettings settings;
3545-
if ( hasGeometry() )
3565+
if ( QgsProcessingProvider *p = provider() )
35463566
{
3547-
return settings.value( QStringLiteral( "Processing/DefaultOutputVectorLayerExt" ), QStringLiteral( "shp" ), QgsSettings::Core ).toString();
3567+
return p->defaultVectorFileExtension( hasGeometry() );
35483568
}
35493569
else
35503570
{
3551-
return QStringLiteral( "dbf" );
3571+
QgsSettings settings;
3572+
if ( hasGeometry() )
3573+
{
3574+
return settings.value( QStringLiteral( "Processing/DefaultOutputVectorLayerExt" ), QStringLiteral( "shp" ), QgsSettings::Core ).toString();
3575+
}
3576+
else
3577+
{
3578+
return QStringLiteral( "dbf" );
3579+
}
35523580
}
35533581
}
35543582

src/core/processing/qgsprocessingparameters.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ class QgsFeatureSink;
3434
class QgsProcessingFeatureSource;
3535
class QgsProcessingOutputDefinition;
3636
class QgsProcessingFeedback;
37+
class QgsProcessingProvider;
3738

3839
/**
3940
* \class QgsProcessingFeatureSourceDefinition
@@ -394,9 +395,17 @@ class CORE_EXPORT QgsProcessingParameterDefinition
394395
/**
395396
* Returns a pointer to the algorithm which owns this parameter. May be nullptr
396397
* for non-owned parameters.
398+
* \see provider()
397399
*/
398400
QgsProcessingAlgorithm *algorithm() const;
399401

402+
/**
403+
* Returns a pointer to the provider for the algorithm which owns this parameter. May be nullptr
404+
* for non-owned parameters or algorithms.
405+
* \see algorithm()
406+
*/
407+
QgsProcessingProvider *provider() const;
408+
400409
protected:
401410

402411
//! Parameter name

src/core/processing/qgsprocessingprovider.cpp

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
#include "qgsprocessingprovider.h"
1919
#include "qgsapplication.h"
2020
#include "qgsvectorfilewriter.h"
21+
#include "qgssettings.h"
2122

2223
QgsProcessingProvider::QgsProcessingProvider( QObject *parent SIP_TRANSFERTHIS )
2324
: QObject( parent )
@@ -84,3 +85,22 @@ QStringList QgsProcessingProvider::supportedOutputVectorLayerExtensions() const
8485
return QgsVectorFileWriter::supportedFormatExtensions();
8586
}
8687

88+
QString QgsProcessingProvider::defaultVectorFileExtension( bool hasGeometry ) const
89+
{
90+
QgsSettings settings;
91+
if ( hasGeometry )
92+
{
93+
return settings.value( QStringLiteral( "Processing/DefaultOutputVectorLayerExt" ), QStringLiteral( "shp" ), QgsSettings::Core ).toString();
94+
}
95+
else
96+
{
97+
return QStringLiteral( "dbf" );
98+
}
99+
}
100+
101+
QString QgsProcessingProvider::defaultRasterFileExtension() const
102+
{
103+
QgsSettings settings;
104+
return settings.value( QStringLiteral( "Processing/DefaultOutputRasterLayerExt" ), QStringLiteral( "tif" ), QgsSettings::Core ).toString();
105+
}
106+

src/core/processing/qgsprocessingprovider.h

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,7 @@ class CORE_EXPORT QgsProcessingProvider : public QObject
110110

111111
/**
112112
* Returns a list of the vector format file extensions supported by this provider.
113+
* \see defaultVectorFileExtension()
113114
* \see supportedOutputRasterLayerExtensions()
114115
* \see supportedOutputTableExtensions()
115116
* \see supportsNonFileBasedOutput()
@@ -123,6 +124,33 @@ class CORE_EXPORT QgsProcessingProvider : public QObject
123124
*/
124125
virtual QStringList supportedOutputTableExtensions() const { return QStringList() << QStringLiteral( "csv" ); }
125126

127+
/**
128+
* Returns the default file extension to use for vector outputs created by the
129+
* provider.
130+
*
131+
* If \a hasGeometry is true then the output file format must have support for
132+
* geometry. If \a hasGeometry is false then non-spatial formats can be used.
133+
*
134+
* The default implementation returns the user's default Processing vector output format
135+
* setting.
136+
*
137+
* \see supportedOutputVectorLayerExtensions()
138+
* \see defaultRasterFileExtension()
139+
*/
140+
virtual QString defaultVectorFileExtension( bool hasGeometry = true ) const;
141+
142+
/**
143+
* Returns the default file extension to use for raster outputs created by the
144+
* provider.
145+
*
146+
* The default implementation returns the user's default Processing raster output format
147+
* setting.
148+
*
149+
* \see supportedOutputRasterLayerExtensions()
150+
* \see defaultVectorFileExtension()
151+
*/
152+
virtual QString defaultRasterFileExtension() const;
153+
126154
/**
127155
* Returns true if the provider supports non-file based outputs (such as memory layers
128156
* or direct database outputs).

tests/src/analysis/testqgsprocessing.cpp

Lines changed: 52 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,41 @@ class DummyAlgorithm : public QgsProcessingAlgorithm
130130
QgsProcessingParameterVectorDestination *p8 = new QgsProcessingParameterVectorDestination( "p8" );
131131
// this should fail - it would result in a duplicate output name
132132
QVERIFY( !addParameter( p8 ) );
133+
134+
// default vector format extension
135+
QgsProcessingParameterFeatureSink *sinkParam = new QgsProcessingParameterFeatureSink( "sink" );
136+
QCOMPARE( sinkParam->defaultFileExtension(), QStringLiteral( "shp" ) ); // before alg is accessible
137+
QVERIFY( !sinkParam->algorithm() );
138+
QVERIFY( !sinkParam->provider() );
139+
addParameter( sinkParam );
140+
QCOMPARE( sinkParam->defaultFileExtension(), QStringLiteral( "shp" ) );
141+
QCOMPARE( sinkParam->algorithm(), this );
142+
QVERIFY( !sinkParam->provider() );
143+
144+
// default raster format extension
145+
QgsProcessingParameterRasterDestination *rasterParam = new QgsProcessingParameterRasterDestination( "raster" );
146+
QCOMPARE( rasterParam->defaultFileExtension(), QStringLiteral( "tif" ) ); // before alg is accessible
147+
addParameter( rasterParam );
148+
QCOMPARE( rasterParam->defaultFileExtension(), QStringLiteral( "tif" ) );
149+
}
150+
151+
void runParameterChecks2()
152+
{
153+
// default vector format extension, taken from provider
154+
QgsProcessingParameterFeatureSink *sinkParam = new QgsProcessingParameterFeatureSink( "sink2" );
155+
QCOMPARE( sinkParam->defaultFileExtension(), QStringLiteral( "shp" ) ); // before alg is accessible
156+
QVERIFY( !sinkParam->algorithm() );
157+
QVERIFY( !sinkParam->provider() );
158+
addParameter( sinkParam );
159+
QCOMPARE( sinkParam->defaultFileExtension(), QStringLiteral( "xshp" ) );
160+
QCOMPARE( sinkParam->algorithm(), this );
161+
QCOMPARE( sinkParam->provider(), provider() );
162+
163+
// default raster format extension
164+
QgsProcessingParameterRasterDestination *rasterParam = new QgsProcessingParameterRasterDestination( "raster2" );
165+
QCOMPARE( rasterParam->defaultFileExtension(), QStringLiteral( "tif" ) ); // before alg is accessible
166+
addParameter( rasterParam );
167+
QCOMPARE( rasterParam->defaultFileExtension(), QStringLiteral( "pcx" ) );
133168
}
134169

135170
void runOutputChecks()
@@ -254,6 +289,16 @@ class DummyProvider : public QgsProcessingProvider
254289

255290
void unload() override { if ( unloaded ) { *unloaded = true; } }
256291

292+
QString defaultVectorFileExtension( bool ) const override
293+
{
294+
return "xshp"; // shape-X. Just like shapefiles, but to the max!
295+
}
296+
297+
QString defaultRasterFileExtension() const override
298+
{
299+
return "pcx"; // next-gen raster storage
300+
}
301+
257302
bool *unloaded = nullptr;
258303

259304
protected:
@@ -273,7 +318,7 @@ class DummyProvider : public QgsProcessingProvider
273318

274319
QString mId;
275320

276-
321+
friend class TestQgsProcessing;
277322
};
278323

279324
class DummyProviderNoLoad : public DummyProvider
@@ -1419,8 +1464,12 @@ void TestQgsProcessing::parameters()
14191464

14201465
void TestQgsProcessing::algorithmParameters()
14211466
{
1422-
DummyAlgorithm alg( "test" );
1423-
alg.runParameterChecks();
1467+
DummyAlgorithm *alg = new DummyAlgorithm( "test" );
1468+
DummyProvider p( "test" );
1469+
alg->runParameterChecks();
1470+
1471+
p.addAlgorithm( alg );
1472+
alg->runParameterChecks2();
14241473
}
14251474

14261475
void TestQgsProcessing::algorithmOutputs()

0 commit comments

Comments
 (0)