Skip to content
Permalink
Browse files

Add explicit settings for ellipsoid, distance and area units to QgsPr…

…ocessingContext

to avoid having to always retrieve these via the context's project (which may
not be available in some circumstances)

Refs #37988
  • Loading branch information
nyalldawson committed Jul 29, 2020
1 parent 0f7a946 commit 03854a41b0f88d9f97f9932d121924ddfac4f8f0
@@ -73,8 +73,8 @@ Returns the project in which the algorithm is being executed.
%Docstring
Sets the ``project`` in which the algorithm will be executed.

This also automatically sets the :py:func:`~QgsProcessingContext.transformContext` to match
the project's transform context.
This also automatically sets the :py:func:`~QgsProcessingContext.transformContext`, :py:func:`~QgsProcessingContext.ellipsoid`, :py:func:`~QgsProcessingContext.distanceUnit` and
:py:func:`~QgsProcessingContext.areaUnit` to match the project's settings.

.. seealso:: :py:func:`project`
%End
@@ -105,6 +105,74 @@ Note that setting a project for the context will automatically set the coordinat
context.

.. seealso:: :py:func:`transformContext`
%End

QString ellipsoid() const;
%Docstring
Returns the ellipsoid to use for distance and area calculations.

.. seealso:: :py:func:`setEllipsoid`

.. versionadded:: 3.16
%End

void setEllipsoid( const QString &ellipsoid );
%Docstring
Sets a specified ``ellipsoid`` to use for distance and area calculations.

If not explicitly set, the ellipsoid will default to the :py:func:`~QgsProcessingContext.project`'s ellipsoid setting.

.. seealso:: :py:func:`ellipsoid`

.. versionadded:: 3.16
%End

QgsUnitTypes::DistanceUnit distanceUnit() const;
%Docstring
Returns the distance unit to use for distance calculations.

.. seealso:: :py:func:`setDistanceUnit`

.. seealso:: :py:func:`areaUnit`

.. versionadded:: 3.16
%End

void setDistanceUnit( QgsUnitTypes::DistanceUnit unit );
%Docstring
Sets the ``unit`` to use for distance calculations.

If not explicitly set, the unit will default to the :py:func:`~QgsProcessingContext.project`'s distance unit setting.

.. seealso:: :py:func:`distanceUnit`

.. seealso:: :py:func:`setAreaUnit`

.. versionadded:: 3.16
%End

QgsUnitTypes::AreaUnit areaUnit() const;
%Docstring
Returns the area unit to use for area calculations.

.. seealso:: :py:func:`setAreaUnit`

.. seealso:: :py:func:`distanceUnit`

.. versionadded:: 3.16
%End

void setAreaUnit( QgsUnitTypes::AreaUnit areaUnit );
%Docstring
Sets the ``unit`` to use for area calculations.

If not explicitly set, the unit will default to the :py:func:`~QgsProcessingContext.project`'s area unit setting.

.. seealso:: :py:func:`areaUnit`

.. seealso:: :py:func:`setDistanceUnit`

.. versionadded:: 3.16
%End

QgsMapLayerStore *temporaryLayerStore();
@@ -110,7 +110,35 @@ QgsMapLayer *QgsProcessingContext::takeResultLayer( const QString &id )
return tempLayerStore.takeMapLayer( tempLayerStore.mapLayer( id ) );
}

QString QgsProcessingContext::ellipsoid() const
{
return mEllipsoid;
}

void QgsProcessingContext::setEllipsoid( const QString &ellipsoid )
{
mEllipsoid = ellipsoid;
}

QgsUnitTypes::DistanceUnit QgsProcessingContext::distanceUnit() const
{
return mDistanceUnit;
}

void QgsProcessingContext::setDistanceUnit( QgsUnitTypes::DistanceUnit unit )
{
mDistanceUnit = unit;
}

QgsUnitTypes::AreaUnit QgsProcessingContext::areaUnit() const
{
return mAreaUnit;
}

void QgsProcessingContext::setAreaUnit( QgsUnitTypes::AreaUnit areaUnit )
{
mAreaUnit = areaUnit;
}

QgsProcessingLayerPostProcessorInterface *QgsProcessingContext::LayerDetails::postProcessor() const
{
@@ -78,6 +78,11 @@ class CORE_EXPORT QgsProcessingContext
mTransformErrorCallback = other.mTransformErrorCallback;
mDefaultEncoding = other.mDefaultEncoding;
mFeedback = other.mFeedback;
mPreferredVectorFormat = other.mPreferredVectorFormat;
mPreferredRasterFormat = other.mPreferredRasterFormat;
mEllipsoid = other.mEllipsoid;
mDistanceUnit = other.mDistanceUnit;
mAreaUnit = other.mAreaUnit;
}

/**
@@ -101,16 +106,24 @@ class CORE_EXPORT QgsProcessingContext
/**
* Sets the \a project in which the algorithm will be executed.
*
* This also automatically sets the transformContext() to match
* the project's transform context.
* This also automatically sets the transformContext(), ellipsoid(), distanceUnit() and
* areaUnit() to match the project's settings.
*
* \see project()
*/
void setProject( QgsProject *project )
{
mProject = project;
if ( mProject )
{
mTransformContext = mProject->transformContext();
if ( mEllipsoid.isEmpty() )
mEllipsoid = mProject->ellipsoid();
if ( mDistanceUnit == QgsUnitTypes::DistanceUnknownUnit )
mDistanceUnit = mProject->distanceUnits();
if ( mAreaUnit == QgsUnitTypes::AreaUnknownUnit )
mAreaUnit = mProject->areaUnits();
}
}

/**
@@ -144,6 +157,64 @@ class CORE_EXPORT QgsProcessingContext
*/
void setTransformContext( const QgsCoordinateTransformContext &context ) { mTransformContext = context; }

/**
* Returns the ellipsoid to use for distance and area calculations.
*
* \see setEllipsoid()
* \since QGIS 3.16
*/
QString ellipsoid() const;

/**
* Sets a specified \a ellipsoid to use for distance and area calculations.
*
* If not explicitly set, the ellipsoid will default to the project()'s ellipsoid setting.
*
* \see ellipsoid()
* \since QGIS 3.16
*/
void setEllipsoid( const QString &ellipsoid );

/**
* Returns the distance unit to use for distance calculations.
*
* \see setDistanceUnit()
* \see areaUnit()
* \since QGIS 3.16
*/
QgsUnitTypes::DistanceUnit distanceUnit() const;

/**
* Sets the \a unit to use for distance calculations.
*
* If not explicitly set, the unit will default to the project()'s distance unit setting.
*
* \see distanceUnit()
* \see setAreaUnit()
* \since QGIS 3.16
*/
void setDistanceUnit( QgsUnitTypes::DistanceUnit unit );

/**
* Returns the area unit to use for area calculations.
*
* \see setAreaUnit()
* \see distanceUnit()
* \since QGIS 3.16
*/
QgsUnitTypes::AreaUnit areaUnit() const;

/**
* Sets the \a unit to use for area calculations.
*
* If not explicitly set, the unit will default to the project()'s area unit setting.
*
* \see areaUnit()
* \see setDistanceUnit()
* \since QGIS 3.16
*/
void setAreaUnit( QgsUnitTypes::AreaUnit areaUnit );

/**
* Returns a reference to the layer store used for storing temporary layers during
* algorithm execution.
@@ -535,6 +606,11 @@ class CORE_EXPORT QgsProcessingContext
QgsProcessingContext::Flags mFlags = QgsProcessingContext::Flags();
QPointer< QgsProject > mProject;
QgsCoordinateTransformContext mTransformContext;

QString mEllipsoid;
QgsUnitTypes::DistanceUnit mDistanceUnit = QgsUnitTypes::DistanceUnknownUnit;
QgsUnitTypes::AreaUnit mAreaUnit = QgsUnitTypes::AreaUnknownUnit;

//! Temporary project owned by the context, used for storing temporarily loaded map layers
QgsMapLayerStore tempLayerStore;
QgsExpressionContext mExpressionContext;
@@ -956,9 +956,28 @@ void TestQgsProcessing::context()
context.setFlags( QgsProcessingContext::Flags( nullptr ) );
QCOMPARE( context.flags(), QgsProcessingContext::Flags( nullptr ) );

QCOMPARE( context.ellipsoid(), QString() );
QCOMPARE( context.distanceUnit(), QgsUnitTypes::DistanceUnknownUnit );
QCOMPARE( context.areaUnit(), QgsUnitTypes::AreaUnknownUnit );

QgsProject p;
p.setEllipsoid( QStringLiteral( "WGS84" ) );
p.setDistanceUnits( QgsUnitTypes::DistanceFeet );
p.setAreaUnits( QgsUnitTypes::AreaHectares );
context.setProject( &p );
QCOMPARE( context.project(), &p );
QCOMPARE( context.ellipsoid(), QStringLiteral( "WGS84" ) );
QCOMPARE( context.distanceUnit(), QgsUnitTypes::DistanceFeet );
QCOMPARE( context.areaUnit(), QgsUnitTypes::AreaHectares );

// if context ellipsoid/units are already set then setting the project shouldn't overwrite them
p.setEllipsoid( QStringLiteral( "WGS84v2" ) );
p.setDistanceUnits( QgsUnitTypes::DistanceMiles );
p.setAreaUnits( QgsUnitTypes::AreaAcres );
context.setProject( &p );
QCOMPARE( context.ellipsoid(), QStringLiteral( "WGS84" ) );
QCOMPARE( context.distanceUnit(), QgsUnitTypes::DistanceFeet );
QCOMPARE( context.areaUnit(), QgsUnitTypes::AreaHectares );

context.setInvalidGeometryCheck( QgsFeatureRequest::GeometrySkipInvalid );
QCOMPARE( context.invalidGeometryCheck(), QgsFeatureRequest::GeometrySkipInvalid );

0 comments on commit 03854a4

Please sign in to comment.
You can’t perform that action at this time.