Skip to content

Commit

Permalink
[processing] Allow encoding crs into text definitions of points
Browse files Browse the repository at this point in the history
  • Loading branch information
nyalldawson committed Sep 24, 2017
1 parent a4ed721 commit ec44e60
Show file tree
Hide file tree
Showing 2 changed files with 68 additions and 14 deletions.
58 changes: 46 additions & 12 deletions src/core/processing/qgsprocessingparameters.cpp
Expand Up @@ -630,15 +630,36 @@ QgsPointXY QgsProcessingParameters::parameterAsPoint( const QgsProcessingParamet
if ( pointText.isEmpty() )
return QgsPointXY();

QStringList parts = pointText.split( ',' );
if ( parts.count() == 2 )
QRegularExpression rx( "^(.*?)\\s*,\\s*(.*?)\\s*(?:\\[(.*)\\])?\\s*$" );

QString valueAsString = parameterAsString( definition, parameters, context );
QRegularExpressionMatch match = rx.match( valueAsString );
if ( match.hasMatch() )
{
bool xOk = false;
double x = parts.at( 0 ).toDouble( &xOk );
double x = match.captured( 1 ).toDouble( &xOk );
bool yOk = false;
double y = parts.at( 1 ).toDouble( &yOk );
double y = match.captured( 2 ).toDouble( &yOk );

if ( xOk && yOk )
return QgsPointXY( x, y );
{
QgsPointXY pt( x, y );

QgsCoordinateReferenceSystem pointCrs( match.captured( 3 ) );
if ( crs.isValid() && pointCrs.isValid() && crs != pointCrs )
{
QgsCoordinateTransform ct( pointCrs, crs );
try
{
return ct.transform( pt );
}
catch ( QgsCsException & )
{
QgsMessageLog::logMessage( QObject::tr( "Error transforming point geometry" ) );
}
}
return pt;
}
}

return QgsPointXY();
Expand All @@ -657,6 +678,17 @@ QgsCoordinateReferenceSystem QgsProcessingParameters::parameterAsPointCrs( const
}
}

QRegularExpression rx( "^(.*?)\\s*,\\s*(.*?)\\s*(?:\\[(.*)\\])?\\s*$" );

QString valueAsString = parameterAsString( definition, parameters, context );
QRegularExpressionMatch match = rx.match( valueAsString );
if ( match.hasMatch() )
{
QgsCoordinateReferenceSystem crs( match.captured( 3 ) );
if ( crs.isValid() )
return crs;
}

if ( context.project() )
return context.project()->crs();
else
Expand Down Expand Up @@ -1360,13 +1392,15 @@ bool QgsProcessingParameterPoint::checkValueIsAcceptable( const QVariant &input,
return mFlags & FlagOptional;
}

QStringList parts = input.toString().split( ',' );
if ( parts.count() == 2 )
QRegularExpression rx( "^(.*?)\\s*,\\s*(.*?)\\s*(?:\\[(.*)\\])?\\s*$" );

QRegularExpressionMatch match = rx.match( input.toString() );
if ( match.hasMatch() )
{
bool xOk = false;
( void )parts.at( 0 ).toDouble( &xOk );
( void )match.captured( 1 ).toDouble( &xOk );
bool yOk = false;
( void )parts.at( 1 ).toDouble( &yOk );
( void )match.captured( 2 ).toDouble( &yOk );
return xOk && yOk;
}
else
Expand All @@ -1381,13 +1415,13 @@ QString QgsProcessingParameterPoint::valueAsPythonString( const QVariant &value,
if ( value.canConvert< QgsPointXY >() )
{
QgsPointXY r = value.value<QgsPointXY>();
return QStringLiteral( "QgsPointXY( %1, %2 )" ).arg( qgsDoubleToString( r.x() ),
qgsDoubleToString( r.y() ) );
return QStringLiteral( "'%1,%2'" ).arg( qgsDoubleToString( r.x() ),
qgsDoubleToString( r.y() ) );
}
if ( value.canConvert< QgsReferencedPointXY >() )
{
QgsReferencedPointXY r = value.value<QgsReferencedPointXY>();
return QStringLiteral( "QgsReferencedPointXY( QgsPointXY( %1, %2 ), QgsCoordinateReferenceSystem( '%3' ) )" ).arg( qgsDoubleToString( r.x() ),
return QStringLiteral( "'%1,%2 [%3]'" ).arg( qgsDoubleToString( r.x() ),
qgsDoubleToString( r.y() ),
r.crs().authid() );
}
Expand Down
24 changes: 22 additions & 2 deletions tests/src/core/testqgsprocessing.cpp
Expand Up @@ -2006,6 +2006,13 @@ void TestQgsProcessing::parameterPoint()
QVERIFY( !def->checkValueIsAcceptable( true ) );
QVERIFY( !def->checkValueIsAcceptable( 5 ) );
QVERIFY( def->checkValueIsAcceptable( "1.1,2" ) );
QVERIFY( def->checkValueIsAcceptable( " 1.1, 2 " ) );
QVERIFY( def->checkValueIsAcceptable( "-1.1,2" ) );
QVERIFY( def->checkValueIsAcceptable( "1.1,-2" ) );
QVERIFY( def->checkValueIsAcceptable( "-1.1,-2" ) );
QVERIFY( def->checkValueIsAcceptable( "1.1,2[EPSG:4326]" ) );
QVERIFY( def->checkValueIsAcceptable( "1.1,2 [EPSG:4326]" ) );
QVERIFY( def->checkValueIsAcceptable( " -1.1, -2 [EPSG:4326] " ) );
QVERIFY( !def->checkValueIsAcceptable( "1.1,a" ) );
QVERIFY( !def->checkValueIsAcceptable( "layer12312312" ) );
QVERIFY( !def->checkValueIsAcceptable( "" ) );
Expand All @@ -2026,6 +2033,18 @@ void TestQgsProcessing::parameterPoint()
QGSCOMPARENEAR( point.x(), 1.1, 0.001 );
QGSCOMPARENEAR( point.y(), 2.2, 0.001 );

// with CRS as string
params.insert( "non_optional", QString( "1.1,2.2[EPSG:4326]" ) );
QCOMPARE( QgsProcessingParameters::parameterAsPointCrs( def.get(), params, context ).authid(), QStringLiteral( "EPSG:4326" ) );
point = QgsProcessingParameters::parameterAsPoint( def.get(), params, context, QgsCoordinateReferenceSystem( "EPSG:3785" ) );
QGSCOMPARENEAR( point.x(), 122451, 100 );
QGSCOMPARENEAR( point.y(), 244963, 100 );
params.insert( "non_optional", QString( "1.1,2.2 [EPSG:4326]" ) );
QCOMPARE( QgsProcessingParameters::parameterAsPointCrs( def.get(), params, context ).authid(), QStringLiteral( "EPSG:4326" ) );
point = QgsProcessingParameters::parameterAsPoint( def.get(), params, context, QgsCoordinateReferenceSystem( "EPSG:3785" ) );
QGSCOMPARENEAR( point.x(), 122451, 100 );
QGSCOMPARENEAR( point.y(), 244963, 100 );

// nonsense string
params.insert( "non_optional", QString( "i'm not a crs, and nothing you can do will make me one" ) );
point = QgsProcessingParameters::parameterAsPoint( def.get(), params, context );
Expand Down Expand Up @@ -2056,8 +2075,9 @@ void TestQgsProcessing::parameterPoint()
QGSCOMPARENEAR( point.y(), 244963, 100 );

QCOMPARE( def->valueAsPythonString( "1,2", context ), QStringLiteral( "'1,2'" ) );
QCOMPARE( def->valueAsPythonString( QgsPointXY( 11, 12 ), context ), QStringLiteral( "QgsPointXY( 11, 12 )" ) );
QCOMPARE( def->valueAsPythonString( QgsReferencedPointXY( QgsPointXY( 11, 12 ), QgsCoordinateReferenceSystem( "epsg:4326" ) ), context ), QStringLiteral( "QgsReferencedPointXY( QgsPointXY( 11, 12 ), QgsCoordinateReferenceSystem( 'EPSG:4326' ) )" ) );
QCOMPARE( def->valueAsPythonString( "1,2 [EPSG:4326]", context ), QStringLiteral( "'1,2 [EPSG:4326]'" ) );
QCOMPARE( def->valueAsPythonString( QgsPointXY( 11, 12 ), context ), QStringLiteral( "'11,12'" ) );
QCOMPARE( def->valueAsPythonString( QgsReferencedPointXY( QgsPointXY( 11, 12 ), QgsCoordinateReferenceSystem( "epsg:4326" ) ), context ), QStringLiteral( "'11,12 [EPSG:4326]'" ) );

QString code = def->asScriptCode();
QCOMPARE( code, QStringLiteral( "##non_optional=point 1,2" ) );
Expand Down

0 comments on commit ec44e60

Please sign in to comment.