Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Fix composer scale bar when crs units are non-meters and OTF is off (fix
  • Loading branch information
nyalldawson committed Oct 23, 2015
1 parent 68f11d4 commit d56dcdb
Show file tree
Hide file tree
Showing 4 changed files with 66 additions and 8 deletions.
24 changes: 17 additions & 7 deletions src/core/composer/qgscomposerscalebar.cpp
Expand Up @@ -305,14 +305,24 @@ double QgsComposerScaleBar::mapWidth() const
da.setSourceCrs( mComposition->mapSettings().destinationCrs().srsid() );
da.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", "WGS84" ) );

double measure = da.measureLine( QgsPoint( composerMapRect.xMinimum(), composerMapRect.yMinimum() ), QgsPoint( composerMapRect.xMaximum(), composerMapRect.yMinimum() ) );
if ( mUnits == QgsComposerScaleBar::Feet )
{
measure /= QGis::fromUnitToUnitFactor( QGis::Feet, QGis::Meters );
}
else if ( mUnits == QgsComposerScaleBar::NauticalMiles )
QGis::UnitType units = QGis::Meters;
double measure = da.measureLine( QgsPoint( composerMapRect.xMinimum(), composerMapRect.yMinimum() ),
QgsPoint( composerMapRect.xMaximum(), composerMapRect.yMinimum() ),
units );
switch ( mUnits )
{
measure /= QGis::fromUnitToUnitFactor( QGis::NauticalMiles, QGis::Meters );
case QgsComposerScaleBar::Feet:
measure /= QGis::fromUnitToUnitFactor( QGis::Feet, units );
break;
case QgsComposerScaleBar::NauticalMiles:
measure /= QGis::fromUnitToUnitFactor( QGis::NauticalMiles, units );
break;
case QgsComposerScaleBar::Meters:
measure /= QGis::fromUnitToUnitFactor( QGis::Meters, units );
break;
case QgsComposerScaleBar::MapUnits:
//avoid warning
break;
}
return measure;
}
Expand Down
8 changes: 8 additions & 0 deletions src/core/qgsdistancearea.cpp
Expand Up @@ -486,8 +486,15 @@ double QgsDistanceArea::measureLine( const QList<QgsPoint> &points ) const
}

double QgsDistanceArea::measureLine( const QgsPoint &p1, const QgsPoint &p2 ) const
{
QGis::UnitType units;
return measureLine( p1, p2, units );
}

double QgsDistanceArea::measureLine( const QgsPoint& p1, const QgsPoint& p2, QGis::UnitType& units ) const
{
double result;
units = mCoordTransform->sourceCrs().mapUnits();

try
{
Expand All @@ -496,6 +503,7 @@ double QgsDistanceArea::measureLine( const QgsPoint &p1, const QgsPoint &p2 ) co
QgsDebugMsgLevel( QString( "Measuring from %1 to %2" ).arg( p1.toString( 4 ), p2.toString( 4 ) ), 3 );
if ( mEllipsoidalMode && ( mEllipsoid != GEO_NONE ) )
{
units = QGis::Meters;
QgsDebugMsgLevel( QString( "Ellipsoidal calculations is enabled, using ellipsoid %1" ).arg( mEllipsoid ), 4 );
QgsDebugMsgLevel( QString( "From proj4 : %1" ).arg( mCoordTransform->sourceCrs().toProj4() ), 4 );
QgsDebugMsgLevel( QString( "To proj4 : %1" ).arg( mCoordTransform->destCRS().toProj4() ), 4 );
Expand Down
15 changes: 14 additions & 1 deletion src/core/qgsdistancearea.h
Expand Up @@ -118,9 +118,22 @@ class CORE_EXPORT QgsDistanceArea
//! measures line
double measureLine( const QList<QgsPoint>& points ) const;

//! measures line with one segment
/** Measures length of line with one segment
* @param p1 start of line
* @param p2 end of line
* @returns distance in meters, or map units if cartesian calculation was performed
*/
double measureLine( const QgsPoint& p1, const QgsPoint& p2 ) const;

/** Measures length of line with one segment and returns units of distance.
* @param p1 start of line
* @param p2 end of line
* @param units will be set to units of measure
* @returns calculated distance between points. Distance units are stored in units parameter.
* @note added in QGIS 2.12
*/
double measureLine( const QgsPoint& p1, const QgsPoint& p2, QGis::UnitType& units ) const;

//! measures polygon area
double measurePolygon( const QList<QgsPoint>& points ) const;

Expand Down
27 changes: 27 additions & 0 deletions tests/src/core/testqgsdistancearea.cpp
Expand Up @@ -25,6 +25,8 @@
#include "qgslogger.h"
#include "qgsgeometryfactory.h"
#include "qgsgeometry.h"
#include "qgis.h"


class TestQgsDistanceArea: public QObject
{
Expand All @@ -38,6 +40,7 @@ class TestQgsDistanceArea: public QObject
void unit_conversions();
void regression13601();
void collections();
void measureUnits();
};

void TestQgsDistanceArea::initTestCase()
Expand Down Expand Up @@ -221,6 +224,30 @@ void TestQgsDistanceArea::collections()
Q_NOWARN_DEPRECATED_POP
}

void TestQgsDistanceArea::measureUnits()
{
//test regression #13610
QgsDistanceArea calc;
calc.setEllipsoidalMode( false );
calc.setEllipsoid( "NONE" );
calc.setSourceCrs( 254L );
QGis::UnitType units;
QgsPoint p1( 1341683.9854275715, 408256.9562717728 );
QgsPoint p2( 1349321.7807031618, 408256.9562717728 );

double result = calc.measureLine( p1, p2, units );
//no OTF, result will be in CRS unit (feet)
QCOMPARE( units, QGis::Feet );
QVERIFY( qgsDoubleNear( result, 7637.7952755903825, 0.001 ) );

calc.setEllipsoidalMode( true );
calc.setEllipsoid( "WGS84" );
result = calc.measureLine( p1, p2, units );
//OTF, result will be in meters
QCOMPARE( units, QGis::Meters );
QVERIFY( qgsDoubleNear( result, 2328.0988253106957, 0.001 ) );
}

QTEST_MAIN( TestQgsDistanceArea )
#include "testqgsdistancearea.moc"

Expand Down

0 comments on commit d56dcdb

Please sign in to comment.