Update code, formatting

This commit is contained in:
Nyall Dawson 2017-11-15 08:08:26 +10:00
parent 8fd8b6ebf1
commit 0d7b828bda
3 changed files with 131 additions and 125 deletions

View File

@ -22,9 +22,7 @@ class QgsCoordinateFormatter
ensuring that only geographic coordinates and not projected coordinates are formatted to degree ensuring that only geographic coordinates and not projected coordinates are formatted to degree
based formats. based formats.
.. note:: .. versionadded:: 3.0
Added in version 2.14
%End %End
%TypeHeaderCode %TypeHeaderCode
@ -34,51 +32,52 @@ class QgsCoordinateFormatter
enum Format enum Format
{ {
Pair, FormatPair,
DegreesMinutesSeconds, FormatDegreesMinutesSeconds,
DegreesMinutes, FormatDegreesMinutes,
DecimalDegrees, FormatDecimalDegrees,
}; };
enum FormatFlag enum FormatFlag
{ {
DegreesUseStringSuffix, FlagDegreesUseStringSuffix,
DegreesPadMinutesSeconds, FlagDegreesPadMinutesSeconds,
}; };
typedef QFlags<QgsCoordinateFormatter::FormatFlag> FormatFlags; typedef QFlags<QgsCoordinateFormatter::FormatFlag> FormatFlags;
static QString formatX( double x, Format format, int precision = 12, FormatFlags flags = DegreesUseStringSuffix ); static QString formatX( double x, Format format, int precision = 12, FormatFlags flags = FlagDegreesUseStringSuffix );
%Docstring %Docstring
Formats an X coordinate value according to the specified parameters. Formats an ``x`` coordinate value according to the specified parameters.
@param x x-coordinate
@param format string format to use for coordinate The ``format`` argument indicates the desired display format for the coordinate.
@param precision number of decimal places to include
@param flags flags controlling format options The ``precision`` argument gives the number of decimal places to include for coordinates.
@returns formatted X coordinate string
@see formatY() Optional ``flags`` can be specified to control the output format.
.. seealso:: formatY()
:rtype: str :rtype: str
%End %End
static QString formatY( double y, Format format, int precision = 12, FormatFlags flags = DegreesUseStringSuffix ); static QString formatY( double y, Format format, int precision = 12, FormatFlags flags = FlagDegreesUseStringSuffix );
%Docstring %Docstring
Formats an Y coordinate value according to the specified parameters. Formats a ``y`` coordinate value according to the specified parameters.
@param y y-coordinate
@param format string format to use for coordinate The ``format`` argument indicates the desired display format for the coordinate.
@param precision number of decimal places to include
@param flags flags controlling format options The ``precision`` argument gives the number of decimal places to include for coordinates.
@returns formatted Y coordinate string
@see formatX() Optional ``flags`` can be specified to control the output format.
.. seealso:: formatX()
:rtype: str :rtype: str
%End %End
static QString asPair( double x, double y, int precision = 12 ); static QString asPair( double x, double y, int precision = 12 );
%Docstring %Docstring
Formats coordinates as an "x,y" pair, with optional decimal precision. Formats coordinates as an "``x``,``y``" pair, with optional decimal ``precision`` (number
@param x x-coordinate of decimal places to include).
@param y y-coordinate
@param precision number of decimal places to include
@returns formatted coordinate string
:rtype: str :rtype: str
%End %End

View File

@ -1,10 +1,10 @@
/*************************************************************************** /***************************************************************************
qgscoordinateformatter.cpp qgscoordinateformatter.cpp
-------------------------- --------------------------
begin : Decemeber 2015 begin : Decemeber 2015
copyright : (C) 2015 by Nyall Dawson copyright : (C) 2015 by Nyall Dawson
email : nyall dot dawson at gmail dot com email : nyall dot dawson at gmail dot com
***************************************************************************/ ***************************************************************************/
/*************************************************************************** /***************************************************************************
* * * *
@ -24,16 +24,16 @@ QString QgsCoordinateFormatter::formatX( double x, QgsCoordinateFormatter::Forma
{ {
switch ( format ) switch ( format )
{ {
case Pair: case FormatPair:
return formatAsPair( x, precision ); return formatAsPair( x, precision );
case DegreesMinutesSeconds: case FormatDegreesMinutesSeconds:
return formatXAsDegreesMinutesSeconds( x, precision, flags ); return formatXAsDegreesMinutesSeconds( x, precision, flags );
case DegreesMinutes: case FormatDegreesMinutes:
return formatXAsDegreesMinutes( x, precision, flags ); return formatXAsDegreesMinutes( x, precision, flags );
case DecimalDegrees: case FormatDecimalDegrees:
return formatXAsDegrees( x, precision, flags ); return formatXAsDegrees( x, precision, flags );
} }
return QString(); //avoid warnings return QString(); //avoid warnings
@ -43,16 +43,16 @@ QString QgsCoordinateFormatter::formatY( double y, QgsCoordinateFormatter::Forma
{ {
switch ( format ) switch ( format )
{ {
case Pair: case FormatPair:
return formatAsPair( y, precision ); return formatAsPair( y, precision );
case DegreesMinutesSeconds: case FormatDegreesMinutesSeconds:
return formatYAsDegreesMinutesSeconds( y, precision, flags ); return formatYAsDegreesMinutesSeconds( y, precision, flags );
case DegreesMinutes: case FormatDegreesMinutes:
return formatYAsDegreesMinutes( y, precision, flags ); return formatYAsDegreesMinutes( y, precision, flags );
case DecimalDegrees: case FormatDecimalDegrees:
return formatYAsDegrees( y, precision, flags ); return formatYAsDegrees( y, precision, flags );
} }
return QString(); //avoid warnings return QString(); //avoid warnings
@ -68,13 +68,13 @@ QString QgsCoordinateFormatter::asPair( double x, double y, int precision )
QString QgsCoordinateFormatter::formatAsPair( double val, int precision ) QString QgsCoordinateFormatter::formatAsPair( double val, int precision )
{ {
return qIsFinite( val ) ? QString::number( val, 'f', precision ) : QObject::tr( "infinite" ); return std::isfinite( val ) ? QString::number( val, 'f', precision ) : QObject::tr( "infinite" );
} }
QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int precision, FormatFlags flags )
{ {
//first, limit longitude to -360 to 360 degree range //first, limit longitude to -360 to 360 degree range
double wrappedX = fmod( val, 360.0 ); double wrappedX = std::fmod( val, 360.0 );
//next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W" //next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W"
if ( wrappedX > 180.0 ) if ( wrappedX > 180.0 )
{ {
@ -85,17 +85,17 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int
wrappedX = wrappedX + 360.0; wrappedX = wrappedX + 360.0;
} }
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
int degreesX = int( qAbs( wrappedX ) ); int degreesX = int( std::fabs( wrappedX ) );
double floatMinutesX = ( qAbs( wrappedX ) - degreesX ) * 60.0; double floatMinutesX = ( std::fabs( wrappedX ) - degreesX ) * 60.0;
int intMinutesX = int( floatMinutesX ); int intMinutesX = int( floatMinutesX );
double secondsX = ( floatMinutesX - intMinutesX ) * 60.0; double secondsX = ( floatMinutesX - intMinutesX ) * 60.0;
//make sure rounding to specified precision doesn't create seconds >= 60 //make sure rounding to specified precision doesn't create seconds >= 60
if ( qRound( secondsX * precisionMultiplier ) >= 60 * precisionMultiplier ) if ( std::round( secondsX * precisionMultiplier ) >= 60 * precisionMultiplier )
{ {
secondsX = qMax( secondsX - 60, 0.0 ); secondsX = std::max( secondsX - 60, 0.0 );
intMinutesX++; intMinutesX++;
if ( intMinutesX >= 60 ) if ( intMinutesX >= 60 )
{ {
@ -106,7 +106,7 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" ); hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" );
} }
@ -119,14 +119,14 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( degreesX == 0 && intMinutesX == 0 && qRound( secondsX * precisionMultiplier ) == 0 ) if ( degreesX == 0 && intMinutesX == 0 && std::round( secondsX * precisionMultiplier ) == 0 )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();
} }
//also remove directional prefix from 180 degree longitudes //also remove directional prefix from 180 degree longitudes
if ( degreesX == 180 && intMinutesX == 0 && qRound( secondsX * precisionMultiplier ) == 0 ) if ( degreesX == 180 && intMinutesX == 0 && std::round( secondsX * precisionMultiplier ) == 0 )
{ {
hemisphere.clear(); hemisphere.clear();
} }
@ -135,7 +135,7 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int
QString strSecondsX; QString strSecondsX;
//pad with leading digits if required //pad with leading digits if required
if ( flags.testFlag( DegreesPadMinutesSeconds ) ) if ( flags.testFlag( FlagDegreesPadMinutesSeconds ) )
{ {
minutesX = QString( "%1" ).arg( intMinutesX, 2, 10, QChar( '0' ) ); minutesX = QString( "%1" ).arg( intMinutesX, 2, 10, QChar( '0' ) );
int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required
@ -156,7 +156,7 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutesSeconds( double val, int
QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int precision, FormatFlags flags )
{ {
//first, limit latitude to -180 to 180 degree range //first, limit latitude to -180 to 180 degree range
double wrappedY = fmod( val, 180.0 ); double wrappedY = std::fmod( val, 180.0 );
//next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N" //next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N"
if ( wrappedY > 90.0 ) if ( wrappedY > 90.0 )
{ {
@ -167,17 +167,17 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int
wrappedY = wrappedY + 180.0; wrappedY = wrappedY + 180.0;
} }
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
int degreesY = int( qAbs( wrappedY ) ); int degreesY = int( std::fabs( wrappedY ) );
double floatMinutesY = ( qAbs( wrappedY ) - degreesY ) * 60.0; double floatMinutesY = ( std::fabs( wrappedY ) - degreesY ) * 60.0;
int intMinutesY = int( floatMinutesY ); int intMinutesY = int( floatMinutesY );
double secondsY = ( floatMinutesY - intMinutesY ) * 60.0; double secondsY = ( floatMinutesY - intMinutesY ) * 60.0;
//make sure rounding to specified precision doesn't create seconds >= 60 //make sure rounding to specified precision doesn't create seconds >= 60
if ( qRound( secondsY * precisionMultiplier ) >= 60 * precisionMultiplier ) if ( std::round( secondsY * precisionMultiplier ) >= 60 * precisionMultiplier )
{ {
secondsY = qMax( secondsY - 60, 0.0 ); secondsY = std::max( secondsY - 60, 0.0 );
intMinutesY++; intMinutesY++;
if ( intMinutesY >= 60 ) if ( intMinutesY >= 60 )
{ {
@ -188,7 +188,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" ); hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" );
} }
@ -201,7 +201,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( degreesY == 0 && intMinutesY == 0 && qRound( secondsY * precisionMultiplier ) == 0 ) if ( degreesY == 0 && intMinutesY == 0 && std::round( secondsY * precisionMultiplier ) == 0 )
{ {
sign = QString(); sign = QString();
hemisphere.clear(); hemisphere.clear();
@ -211,7 +211,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int
QString strSecondsY; QString strSecondsY;
//pad with leading digits if required //pad with leading digits if required
if ( flags.testFlag( DegreesPadMinutesSeconds ) ) if ( flags.testFlag( FlagDegreesPadMinutesSeconds ) )
{ {
strMinutesY = QString( "%1" ).arg( intMinutesY, 2, 10, QChar( '0' ) ); strMinutesY = QString( "%1" ).arg( intMinutesY, 2, 10, QChar( '0' ) );
int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required
@ -232,7 +232,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutesSeconds( double val, int
QString QgsCoordinateFormatter::formatXAsDegreesMinutes( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatXAsDegreesMinutes( double val, int precision, FormatFlags flags )
{ {
//first, limit longitude to -360 to 360 degree range //first, limit longitude to -360 to 360 degree range
double wrappedX = fmod( val, 360.0 ); double wrappedX = std::fmod( val, 360.0 );
//next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W" //next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W"
if ( wrappedX > 180.0 ) if ( wrappedX > 180.0 )
{ {
@ -243,21 +243,21 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutes( double val, int precisi
wrappedX = wrappedX + 360.0; wrappedX = wrappedX + 360.0;
} }
int degreesX = int( qAbs( wrappedX ) ); int degreesX = int( std::fabs( wrappedX ) );
double floatMinutesX = ( qAbs( wrappedX ) - degreesX ) * 60.0; double floatMinutesX = ( std::fabs( wrappedX ) - degreesX ) * 60.0;
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
//make sure rounding to specified precision doesn't create minutes >= 60 //make sure rounding to specified precision doesn't create minutes >= 60
if ( qRound( floatMinutesX * precisionMultiplier ) >= 60 * precisionMultiplier ) if ( std::round( floatMinutesX * precisionMultiplier ) >= 60 * precisionMultiplier )
{ {
floatMinutesX = qMax( floatMinutesX - 60, 0.0 ); floatMinutesX = std::max( floatMinutesX - 60, 0.0 );
degreesX++; degreesX++;
} }
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" ); hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" );
} }
@ -270,21 +270,21 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutes( double val, int precisi
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( degreesX == 0 && qRound( floatMinutesX * precisionMultiplier ) == 0 ) if ( degreesX == 0 && std::round( floatMinutesX * precisionMultiplier ) == 0 )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();
} }
//also remove directional prefix from 180 degree longitudes //also remove directional prefix from 180 degree longitudes
if ( degreesX == 180 && qRound( floatMinutesX * precisionMultiplier ) == 0 ) if ( degreesX == 180 && std::round( floatMinutesX * precisionMultiplier ) == 0 )
{ {
hemisphere.clear(); hemisphere.clear();
} }
//pad minutes with leading digits if required //pad minutes with leading digits if required
int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required
QString strMinutesX = flags.testFlag( DegreesPadMinutesSeconds ) ? QString( "%1" ).arg( floatMinutesX, digits, 'f', precision, QChar( '0' ) ) QString strMinutesX = flags.testFlag( FlagDegreesPadMinutesSeconds ) ? QString( "%1" ).arg( floatMinutesX, digits, 'f', precision, QChar( '0' ) )
: QString::number( floatMinutesX, 'f', precision ); : QString::number( floatMinutesX, 'f', precision );
return sign + QString::number( degreesX ) + QChar( 176 ) + return sign + QString::number( degreesX ) + QChar( 176 ) +
@ -295,7 +295,7 @@ QString QgsCoordinateFormatter::formatXAsDegreesMinutes( double val, int precisi
QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precision, FormatFlags flags )
{ {
//first, limit latitude to -180 to 180 degree range //first, limit latitude to -180 to 180 degree range
double wrappedY = fmod( val, 180.0 ); double wrappedY = std::fmod( val, 180.0 );
//next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N" //next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N"
if ( wrappedY > 90.0 ) if ( wrappedY > 90.0 )
{ {
@ -306,21 +306,21 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precisi
wrappedY = wrappedY + 180.0; wrappedY = wrappedY + 180.0;
} }
int degreesY = int( qAbs( wrappedY ) ); int degreesY = int( std::fabs( wrappedY ) );
double floatMinutesY = ( qAbs( wrappedY ) - degreesY ) * 60.0; double floatMinutesY = ( std::fabs( wrappedY ) - degreesY ) * 60.0;
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
//make sure rounding to specified precision doesn't create minutes >= 60 //make sure rounding to specified precision doesn't create minutes >= 60
if ( qRound( floatMinutesY * precisionMultiplier ) >= 60 * precisionMultiplier ) if ( std::round( floatMinutesY * precisionMultiplier ) >= 60 * precisionMultiplier )
{ {
floatMinutesY = qMax( floatMinutesY - 60, 0.0 ); floatMinutesY = std::max( floatMinutesY - 60, 0.0 );
degreesY++; degreesY++;
} }
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" ); hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" );
} }
@ -333,7 +333,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precisi
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( degreesY == 0 && qRound( floatMinutesY * precisionMultiplier ) == 0 ) if ( degreesY == 0 && std::round( floatMinutesY * precisionMultiplier ) == 0 )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();
@ -342,7 +342,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precisi
//pad minutes with leading digits if required //pad minutes with leading digits if required
int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required int digits = 2 + ( precision == 0 ? 0 : 1 + precision ); //1 for decimal place if required
QString strMinutesY = flags.testFlag( DegreesPadMinutesSeconds ) ? QString( "%1" ).arg( floatMinutesY, digits, 'f', precision, QChar( '0' ) ) QString strMinutesY = flags.testFlag( FlagDegreesPadMinutesSeconds ) ? QString( "%1" ).arg( floatMinutesY, digits, 'f', precision, QChar( '0' ) )
: QString::number( floatMinutesY, 'f', precision ); : QString::number( floatMinutesY, 'f', precision );
return sign + QString::number( degreesY ) + QChar( 176 ) + return sign + QString::number( degreesY ) + QChar( 176 ) +
@ -353,7 +353,7 @@ QString QgsCoordinateFormatter::formatYAsDegreesMinutes( double val, int precisi
QString QgsCoordinateFormatter::formatXAsDegrees( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatXAsDegrees( double val, int precision, FormatFlags flags )
{ {
//first, limit longitude to -360 to 360 degree range //first, limit longitude to -360 to 360 degree range
double wrappedX = fmod( val, 360.0 ); double wrappedX = std::fmod( val, 360.0 );
//next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W" //next, wrap around longitudes > 180 or < -180 degrees, so that eg "190E" -> "170W"
if ( wrappedX > 180.0 ) if ( wrappedX > 180.0 )
{ {
@ -364,13 +364,13 @@ QString QgsCoordinateFormatter::formatXAsDegrees( double val, int precision, For
wrappedX = wrappedX + 360.0; wrappedX = wrappedX + 360.0;
} }
double absX = qAbs( wrappedX ); double absX = std::fabs( wrappedX );
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" ); hemisphere = wrappedX < 0 ? QObject::tr( "W" ) : QObject::tr( "E" );
} }
@ -383,14 +383,14 @@ QString QgsCoordinateFormatter::formatXAsDegrees( double val, int precision, For
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( qRound( absX * precisionMultiplier ) == 0 ) if ( std::round( absX * precisionMultiplier ) == 0 )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();
} }
//also remove directional prefix from 180 degree longitudes //also remove directional prefix from 180 degree longitudes
if ( qRound( absX * precisionMultiplier ) == 180 * precisionMultiplier ) if ( std::round( absX * precisionMultiplier ) == 180 * precisionMultiplier )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();
@ -402,7 +402,7 @@ QString QgsCoordinateFormatter::formatXAsDegrees( double val, int precision, For
QString QgsCoordinateFormatter::formatYAsDegrees( double val, int precision, FormatFlags flags ) QString QgsCoordinateFormatter::formatYAsDegrees( double val, int precision, FormatFlags flags )
{ {
//first, limit latitude to -180 to 180 degree range //first, limit latitude to -180 to 180 degree range
double wrappedY = fmod( val, 180.0 ); double wrappedY = std::fmod( val, 180.0 );
//next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N" //next, wrap around latitudes > 90 or < -90 degrees, so that eg "110S" -> "70N"
if ( wrappedY > 90.0 ) if ( wrappedY > 90.0 )
{ {
@ -413,13 +413,13 @@ QString QgsCoordinateFormatter::formatYAsDegrees( double val, int precision, For
wrappedY = wrappedY + 180.0; wrappedY = wrappedY + 180.0;
} }
double absY = qAbs( wrappedY ); double absY = std::fabs( wrappedY );
int precisionMultiplier = pow( 10.0, precision ); int precisionMultiplier = std::pow( 10.0, precision );
QString hemisphere; QString hemisphere;
QString sign; QString sign;
if ( flags.testFlag( DegreesUseStringSuffix ) ) if ( flags.testFlag( FlagDegreesUseStringSuffix ) )
{ {
hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" ); hemisphere = wrappedY < 0 ? QObject::tr( "S" ) : QObject::tr( "N" );
} }
@ -432,7 +432,7 @@ QString QgsCoordinateFormatter::formatYAsDegrees( double val, int precision, For
} }
//check if coordinate is all zeros for the specified precision, and if so, //check if coordinate is all zeros for the specified precision, and if so,
//remove the sign and hemisphere strings //remove the sign and hemisphere strings
if ( qRound( absY * precisionMultiplier ) == 0 ) if ( std::round( absY * precisionMultiplier ) == 0 )
{ {
sign.clear(); sign.clear();
hemisphere.clear(); hemisphere.clear();

View File

@ -20,7 +20,8 @@
#include <QString> #include <QString>
/** \ingroup core /**
* \ingroup core
* \class QgsCoordinateFormatter * \class QgsCoordinateFormatter
* \brief Contains methods for converting coordinates for display in various formats. * \brief Contains methods for converting coordinates for display in various formats.
* *
@ -31,57 +32,63 @@
* ensuring that only geographic coordinates and not projected coordinates are formatted to degree * ensuring that only geographic coordinates and not projected coordinates are formatted to degree
* based formats. * based formats.
* *
* \note Added in version 2.14 * \since QGIS 3.0
*/ */
class CORE_EXPORT QgsCoordinateFormatter class CORE_EXPORT QgsCoordinateFormatter
{ {
public: public:
/** Available formats for displaying coordinates. /**
* Available formats for displaying coordinates.
*/ */
enum Format enum Format
{ {
Pair, /*!< Formats coordinates as an "x,y" pair */ FormatPair, //!< Formats coordinates as an "x,y" pair
DegreesMinutesSeconds, /*!< Degrees, minutes and seconds, eg 30 degrees 45'30" */ FormatDegreesMinutesSeconds, //!< Degrees, minutes and seconds, eg 30 degrees 45'30"
DegreesMinutes, /*!< Degrees and decimal minutes, eg 30degrees 45.55' */ FormatDegreesMinutes, //!< Degrees and decimal minutes, eg 30degrees 45.55'
DecimalDegrees, /*!< Decimal degrees, eg 30.7555 degrees */ FormatDecimalDegrees, //!< Decimal degrees, eg 30.7555 degrees
}; };
/** Flags for controlling formatting of coordinates. /**
* Flags for controlling formatting of coordinates.
*/ */
enum FormatFlag enum FormatFlag
{ {
DegreesUseStringSuffix = 0x01, /*!< include a direction suffix (eg 'N', 'E', 'S' or 'W'), otherwise a "-" prefix is used for west and south coordinates */ FlagDegreesUseStringSuffix = 1 << 1, //!< Include a direction suffix (eg 'N', 'E', 'S' or 'W'), otherwise a "-" prefix is used for west and south coordinates
DegreesPadMinutesSeconds = 0x02, /*!< pad minute and second values with leading zeros, eg '05' instead of '5' */ FlagDegreesPadMinutesSeconds = 1 << 2, //!< Pad minute and second values with leading zeros, eg '05' instead of '5'
}; };
Q_DECLARE_FLAGS( FormatFlags, FormatFlag ) Q_DECLARE_FLAGS( FormatFlags, FormatFlag )
/** Formats an X coordinate value according to the specified parameters. /**
* @param x x-coordinate * Formats an \a x coordinate value according to the specified parameters.
* @param format string format to use for coordinate *
* @param precision number of decimal places to include * The \a format argument indicates the desired display format for the coordinate.
* @param flags flags controlling format options *
* @returns formatted X coordinate string * The \a precision argument gives the number of decimal places to include for coordinates.
* @see formatY() *
* Optional \a flags can be specified to control the output format.
*
* \see formatY()
*/ */
static QString formatX( double x, Format format, int precision = 12, FormatFlags flags = DegreesUseStringSuffix ); static QString formatX( double x, Format format, int precision = 12, FormatFlags flags = FlagDegreesUseStringSuffix );
/** Formats an Y coordinate value according to the specified parameters. /**
* @param y y-coordinate * Formats a \a y coordinate value according to the specified parameters.
* @param format string format to use for coordinate *
* @param precision number of decimal places to include * The \a format argument indicates the desired display format for the coordinate.
* @param flags flags controlling format options *
* @returns formatted Y coordinate string * The \a precision argument gives the number of decimal places to include for coordinates.
* @see formatX() *
* Optional \a flags can be specified to control the output format.
*
* \see formatX()
*/ */
static QString formatY( double y, Format format, int precision = 12, FormatFlags flags = DegreesUseStringSuffix ); static QString formatY( double y, Format format, int precision = 12, FormatFlags flags = FlagDegreesUseStringSuffix );
/** Formats coordinates as an "x,y" pair, with optional decimal precision. /**
* @param x x-coordinate * Formats coordinates as an "\a x,\a y" pair, with optional decimal \a precision (number
* @param y y-coordinate * of decimal places to include).
* @param precision number of decimal places to include
* @returns formatted coordinate string
*/ */
static QString asPair( double x, double y, int precision = 12 ); static QString asPair( double x, double y, int precision = 12 );