Skip to content
Permalink
Browse files

[FEATURE] Give access to geometry errors

When methods are called that use GEOS to create new geometries, the
result geometries now contain information about what has gone wrong in
case of an error.

In practice, this means it's possible to give more detailed information
in place (and not only in the message log) when things like processing
algorithms fail.
  • Loading branch information
m-kuhn committed Jul 17, 2017
1 parent db11185 commit 2b2d5e3637949b0059004392ab57c6eeee865039
Showing with 199 additions and 33 deletions.
  1. +64 −6 python/core/geometry/qgsgeometry.sip
  2. +60 −19 src/core/geometry/qgsgeometry.cpp
  3. +75 −8 src/core/geometry/qgsgeometry.h
@@ -716,6 +716,12 @@ Returns a simplified version of this geometry using a specified tolerance value
QgsGeometry centroid() const;
%Docstring
Returns the center of mass of a geometry.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.

.. note::

for line based geometries, the center point of the line is returned,
@@ -730,6 +736,12 @@ Returns a simplified version of this geometry using a specified tolerance value
Returns a point guaranteed to lie on the surface of a geometry. While the centroid()
of a geometry may be located outside of the geometry itself (e.g., for concave shapes),
the point on surface will always be inside the geometry.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.

.. seealso:: centroid()
.. seealso:: poleOfInaccessibility()
:rtype: QgsGeometry
@@ -752,7 +764,12 @@ Returns a simplified version of this geometry using a specified tolerance value

QgsGeometry convexHull() const;
%Docstring
Returns the smallest convex polygon that contains all the points in the geometry.
Returns the smallest convex polygon that contains all the points in the geometry.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.
:rtype: QgsGeometry
%End

@@ -799,14 +816,25 @@ Returns the smallest convex polygon that contains all the points in the geometry

Curved geometries will be segmentized before subdivision.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.

.. versionadded:: 3.0
:rtype: QgsGeometry
%End

QgsGeometry interpolate( double distance ) const;
%Docstring
Return interpolated point on line at distance
.. versionadded:: 1.9
Return interpolated point on line at distance.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.

.. versionadded:: 2.0
.. seealso:: lineLocatePoint()
:rtype: QgsGeometry
%End
@@ -841,7 +869,12 @@ Returns the smallest convex polygon that contains all the points in the geometry

QgsGeometry intersection( const QgsGeometry &geometry ) const;
%Docstring
Returns a geometry representing the points shared by this geometry and other.
Returns a geometry representing the points shared by this geometry and other.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.
:rtype: QgsGeometry
%End

@@ -859,6 +892,12 @@ Returns a geometry representing the points shared by this geometry and other.
%Docstring
Returns a geometry representing all the points in this geometry and other (a
union geometry operation).

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.

.. note::

this operation is not called union since its a reserved word in C++.
@@ -878,13 +917,23 @@ Returns a geometry representing the points shared by this geometry and other.

QgsGeometry difference( const QgsGeometry &geometry ) const;
%Docstring
Returns a geometry representing the points making up this geometry that do not make up other.
Returns a geometry representing the points making up this geometry that do not make up other.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.
:rtype: QgsGeometry
%End

QgsGeometry symDifference( const QgsGeometry &geometry ) const;
%Docstring
Returns a geometry representing the points making up this geometry that do not make up other.
Returns a geometry representing the points making up this geometry that do not make up other.

If the input is a NULL geometry, the output will also be a NULL geometry.

If an error was encountered while creating the result, more information can be retrieved
by calling `error()` on the returned geometry.
:rtype: QgsGeometry
%End

@@ -1184,6 +1233,15 @@ Ring 0 is outer ring and can't be deleted.
:rtype: int
%End

QString error() const;
%Docstring
Returns an error string referring to an error that was produced
when this geometry was created.

.. versionadded:: 3.0
:rtype: str
%End


static QgsGeometry fromQPointF( QPointF point );
%Docstring
@@ -51,6 +51,7 @@ struct QgsGeometryPrivate
~QgsGeometryPrivate() { delete geometry; }
QAtomicInt ref;
QgsAbstractGeometry *geometry = nullptr;
QString error;
};

QgsGeometry::QgsGeometry(): d( new QgsGeometryPrivate() )
@@ -1586,10 +1587,13 @@ QgsGeometry QgsGeometry::centroid() const

QgsGeos geos( d->geometry );
QgsPoint centroid;
bool ok = geos.centroid( centroid );
QString error;
bool ok = geos.centroid( centroid, &error );
if ( !ok )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( centroid.clone() );
}
@@ -1602,13 +1606,17 @@ QgsGeometry QgsGeometry::pointOnSurface() const
}

QgsGeos geos( d->geometry );
QgsPoint pt;
bool ok = geos.pointOnSurface( pt );
std::unique_ptr<QgsPoint>pt( new QgsPoint() );

QString error;
bool ok = geos.pointOnSurface( *pt.get(), &error );
if ( !ok )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( pt.clone() );
return QgsGeometry( pt.release() );
}

QgsGeometry QgsGeometry::poleOfInaccessibility( double precision, double *distanceToBoundary ) const
@@ -1625,10 +1633,13 @@ QgsGeometry QgsGeometry::convexHull() const
return QgsGeometry();
}
QgsGeos geos( d->geometry );
QgsAbstractGeometry *cHull = geos.convexHull();
QString error;
QgsAbstractGeometry *cHull = geos.convexHull( &error );
if ( !cHull )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( cHull );
}
@@ -1670,11 +1681,14 @@ QgsGeometry QgsGeometry::subdivide( int maxNodes ) const
geom = segmentizedCopy.get();
}

QString error;
QgsGeos geos( geom );
QgsAbstractGeometry *result = geos.subdivide( maxNodes );
QgsAbstractGeometry *result = geos.subdivide( maxNodes, &error );
if ( !result )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( result );
}
@@ -1691,10 +1705,13 @@ QgsGeometry QgsGeometry::interpolate( double distance ) const
line = QgsGeometry( d->geometry->boundary() );

QgsGeos geos( line.geometry() );
QgsAbstractGeometry *result = geos.interpolate( distance );
QString error;
QgsAbstractGeometry *result = geos.interpolate( distance, &error );
if ( !result )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( result );
}
@@ -1780,7 +1797,16 @@ QgsGeometry QgsGeometry::intersection( const QgsGeometry &geometry ) const

QgsGeos geos( d->geometry );

QgsAbstractGeometry *resultGeom = geos.intersection( *( geometry.d->geometry ) );
QString error;
QgsAbstractGeometry *resultGeom = geos.intersection( *( geometry.d->geometry ), &error );

if ( !resultGeom )
{
QgsGeometry geom;
geom.d->error = error;
return geom;
}

return QgsGeometry( resultGeom );
}

@@ -1792,11 +1818,14 @@ QgsGeometry QgsGeometry::combine( const QgsGeometry &geometry ) const
}

QgsGeos geos( d->geometry );
QString error;

QgsAbstractGeometry *resultGeom = geos.combine( *( geometry.d->geometry ) );
QgsAbstractGeometry *resultGeom = geos.combine( *( geometry.d->geometry ), &error );
if ( !resultGeom )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( resultGeom );
}
@@ -1827,10 +1856,13 @@ QgsGeometry QgsGeometry::difference( const QgsGeometry &geometry ) const

QgsGeos geos( d->geometry );

QgsAbstractGeometry *resultGeom = geos.difference( *( geometry.d->geometry ) );
QString error;
QgsAbstractGeometry *resultGeom = geos.difference( *( geometry.d->geometry ), &error );
if ( !resultGeom )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( resultGeom );
}
@@ -1844,10 +1876,14 @@ QgsGeometry QgsGeometry::symDifference( const QgsGeometry &geometry ) const

QgsGeos geos( d->geometry );

QgsAbstractGeometry *resultGeom = geos.symDifference( *( geometry.d->geometry ) );
QString error;

QgsAbstractGeometry *resultGeom = geos.symDifference( *( geometry.d->geometry ), &error );
if ( !resultGeom )
{
return QgsGeometry();
QgsGeometry geom;
geom.d->error = error;
return geom;
}
return QgsGeometry( resultGeom );
}
@@ -2275,6 +2311,11 @@ int QgsGeometry::vertexNrFromVertexId( QgsVertexId id ) const
return -1;
}

QString QgsGeometry::error() const
{
return d->error;
}

void QgsGeometry::convertPointList( const QList<QgsPointXY> &input, QgsPointSequence &output )
{
output.clear();

0 comments on commit 2b2d5e3

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