Skip to content

Commit 042bd1f

Browse files
committedApr 22, 2019
backport for default map scale / default map units per mm in project for the case that GetLegendGraphic request does not pass parameters to calculate map unit sized symbol size
(cherry-picks of 7ef426b 10b5f08 3d7cc16 1c3cfd1 679b100 96f054e 7f7d910 755c8ff 1d6a7dd 8e62a89 c22effb fa8e5fa fab5254 27fc381)
1 parent 1782384 commit 042bd1f

File tree

18 files changed

+1151
-514
lines changed

18 files changed

+1151
-514
lines changed
 

‎python/server/auto_generated/qgsserverprojectutils.sip.in

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,17 @@ Returns the maximum number of atlas features which can be printed in a request
161161
:param project: the QGIS project
162162

163163
:return: the number of atlas features
164+
%End
165+
166+
double wmsDefaultMapUnitsPerMm( const QgsProject &project );
167+
%Docstring
168+
Returns the default number of map units per millimeters in case of the scale is not given
169+
170+
:param project: the QGIS project
171+
172+
:return: the default number of map units per millimeter
173+
174+
.. versionadded:: 3.8
164175
%End
165176

166177
bool wmsUseLayerIds( const QgsProject &project );

‎src/app/qgsprojectproperties.cpp

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -642,6 +642,25 @@ QgsProjectProperties::QgsProjectProperties( QgsMapCanvas *mapCanvas, QWidget *pa
642642

643643
mWMSMaxAtlasFeaturesSpinBox->setValue( QgsProject::instance()->readNumEntry( QStringLiteral( "WMSMaxAtlasFeatures" ), QStringLiteral( "/" ), 1 ) );
644644

645+
QString defaultValueToolTip = tr( "In case of no other information to evaluate the map unit sized symbols, it uses default scale (on projected CRS) or default map units per mm (on geographic CRS)." );
646+
mWMSDefaultMapUnitsPerMm = new QDoubleSpinBox();
647+
mWMSDefaultMapUnitsPerMm->setDecimals( 4 );
648+
mWMSDefaultMapUnitsPerMm->setSingleStep( 0.001 );
649+
mWMSDefaultMapUnitsPerMm->setValue( QgsProject::instance()->readDoubleEntry( QStringLiteral( "WMSDefaultMapUnitsPerMm" ), QStringLiteral( "/" ), 1 ) );
650+
mWMSDefaultMapUnitsPerMm->setToolTip( defaultValueToolTip );
651+
mWMSDefaultMapUnitScale = new QgsScaleWidget();
652+
mWMSDefaultMapUnitScale->setScale( QgsProject::instance()->readDoubleEntry( QStringLiteral( "WMSDefaultMapUnitsPerMm" ), QStringLiteral( "/" ), 1 ) * QgsUnitTypes::fromUnitToUnitFactor( QgsProject::instance()->crs().mapUnits(), QgsUnitTypes::DistanceMillimeters ) );
653+
mWMSDefaultMapUnitScale->setToolTip( defaultValueToolTip );
654+
if ( QgsProject::instance()->crs().isGeographic() )
655+
{
656+
mWMSDefaultMapUnitsPerMmLayout->addWidget( mWMSDefaultMapUnitsPerMm );
657+
}
658+
else
659+
{
660+
mWMSDefaultMapUnitsPerMmLayout->addWidget( mWMSDefaultMapUnitScale );
661+
mWMSDefaultMapUnitsPerMmLabel->setText( tr( "Default scale for legend" ) );
662+
}
663+
645664
mWMTSUrlLineEdit->setText( QgsProject::instance()->readEntry( QStringLiteral( "WMTSUrl" ), QStringLiteral( "/" ), QString() ) );
646665
mWMTSMinScaleLineEdit->setValue( QgsProject::instance()->readNumEntry( QStringLiteral( "WMTSMinScale" ), QStringLiteral( "/" ), 5000 ) );
647666

@@ -1298,6 +1317,18 @@ void QgsProjectProperties::apply()
12981317
int maxAtlasFeatures = mWMSMaxAtlasFeaturesSpinBox->value();
12991318
QgsProject::instance()->writeEntry( QStringLiteral( "WMSMaxAtlasFeatures" ), QStringLiteral( "/" ), maxAtlasFeatures );
13001319

1320+
double defaultMapUnitsPerMm;
1321+
if ( QgsProject::instance()->crs().isGeographic() )
1322+
{
1323+
defaultMapUnitsPerMm = mWMSDefaultMapUnitsPerMm->value();
1324+
}
1325+
else
1326+
{
1327+
defaultMapUnitsPerMm = mWMSDefaultMapUnitScale->scale() / QgsUnitTypes::fromUnitToUnitFactor( QgsProject::instance()->crs().mapUnits(), QgsUnitTypes::DistanceMillimeters );
1328+
}
1329+
1330+
QgsProject::instance()->writeEntry( QStringLiteral( "WMSDefaultMapUnitsPerMm" ), QStringLiteral( "/" ), defaultMapUnitsPerMm );
1331+
13011332
QgsProject::instance()->writeEntry( QStringLiteral( "WMTSUrl" ), QStringLiteral( "/" ), mWMTSUrlLineEdit->text() );
13021333
QgsProject::instance()->writeEntry( QStringLiteral( "WMTSMinScale" ), QStringLiteral( "/" ), mWMTSMinScaleLineEdit->value() );
13031334
bool wmtsProject = false;

‎src/app/qgsprojectproperties.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
#include "qgis.h"
2323
#include "qgsunittypes.h"
2424
#include "qgsguiutils.h"
25+
#include "qgsscalewidget.h"
2526
#include "qgshelp.h"
2627
#include "qgis_app.h"
2728

@@ -204,6 +205,9 @@ class APP_EXPORT QgsProjectProperties : public QgsOptionsDialogBase, private Ui:
204205
QgsMetadataWidget *mMetadataWidget = nullptr;
205206
QgsLayerCapabilitiesModel *mLayerCapabilitiesModel = nullptr;
206207

208+
QDoubleSpinBox *mWMSDefaultMapUnitsPerMm = nullptr;
209+
QgsScaleWidget *mWMSDefaultMapUnitScale = nullptr;
210+
207211
QgsCoordinateReferenceSystem mCrs;
208212

209213
void checkPageWidgetNameMap();

‎src/server/qgsserverprojectutils.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,11 @@ int QgsServerProjectUtils::wmsMaxAtlasFeatures( const QgsProject &project )
116116
return project.readNumEntry( QStringLiteral( "WMSMaxAtlasFeatures" ), QStringLiteral( "/" ), 1 );
117117
}
118118

119+
double QgsServerProjectUtils::wmsDefaultMapUnitsPerMm( const QgsProject &project )
120+
{
121+
return project.readDoubleEntry( QStringLiteral( "WMSDefaultMapUnitsPerMm" ), QStringLiteral( "/" ), 1 );
122+
}
123+
119124
bool QgsServerProjectUtils::wmsInfoFormatSia2045( const QgsProject &project )
120125
{
121126
QString sia2045 = project.readEntry( QStringLiteral( "WMSInfoFormatSIA2045" ), QStringLiteral( "/" ), "" );

‎src/server/qgsserverprojectutils.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -154,6 +154,14 @@ namespace QgsServerProjectUtils
154154
*/
155155
SERVER_EXPORT int wmsMaxAtlasFeatures( const QgsProject &project );
156156

157+
/**
158+
* Returns the default number of map units per millimeters in case of the scale is not given
159+
* \param project the QGIS project
160+
* \returns the default number of map units per millimeter
161+
* \since QGIS 3.8
162+
*/
163+
SERVER_EXPORT double wmsDefaultMapUnitsPerMm( const QgsProject &project );
164+
157165
/**
158166
* Returns if layer ids are used as name in WMS.
159167
* \param project the QGIS project

‎src/server/services/wms/qgswmsrenderer.cpp

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -183,15 +183,20 @@ namespace QgsWms
183183
std::unique_ptr<QImage> image;
184184
std::unique_ptr<QPainter> painter;
185185

186-
// getting scale from bbox
186+
// getting scale from bbox or default size
187187
if ( !mWmsParameters.bbox().isEmpty() )
188188
{
189189
QgsMapSettings mapSettings;
190-
image.reset( createImage( width(), height(), false ) );
191-
configureMapSettings( image.get(), mapSettings );
190+
std::unique_ptr<QImage> tmp( createImage( width(), height(), false ) );
191+
configureMapSettings( tmp.get(), mapSettings );
192192
legendSettings.setMapScale( mapSettings.scale() );
193193
legendSettings.setMapUnitsPerPixel( mapSettings.mapUnitsPerPixel() );
194194
}
195+
else
196+
{
197+
double defaultMapUnitsPerPixel = QgsServerProjectUtils::wmsDefaultMapUnitsPerMm( *mContext.project() ) / mContext.dotsPerMm();
198+
legendSettings.setMapUnitsPerPixel( defaultMapUnitsPerPixel );
199+
}
195200

196201
if ( !mWmsParameters.rule().isEmpty() )
197202
{
@@ -231,6 +236,11 @@ namespace QgsWms
231236
legendRendererNew.drawLegend( painter.get() );
232237
painter->end();
233238
}
239+
else
240+
{
241+
double defaultMapUnitsPerPixel = QgsServerProjectUtils::wmsDefaultMapUnitsPerMm( *mContext.project() ) / mContext.dotsPerMm();
242+
settings.setMapUnitsPerPixel( defaultMapUnitsPerPixel );
243+
}
234244

235245
rootGroup.clear();
236246
return image.release();

‎src/ui/qgsprojectpropertiesbase.ui

Lines changed: 316 additions & 305 deletions
Large diffs are not rendered by default.

‎tests/src/python/test_qgsserver_wms_getlegendgraphic.py

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -691,6 +691,51 @@ def test_wms_GetLegendGraphic_ScaleSymbol_Max(self):
691691
r, h = self._result(self._execute_request(qs))
692692
self._img_diff_error(r, h, "WMS_GetLegendGraphic_ScaleSymbol_Max", max_size_diff=QSize(15, 15))
693693

694+
def test_wms_GetLegendGraphic_ScaleSymbol_DefaultMapUnitsPerMillimeter(self):
695+
# map units per mm on 1:20000000 with SRCHEIGHT=598&SRCWIDTH=1640&BBOX=16.5,-69.7,73.3,86.1 would be around what is set as default: 0.359 map units per mm
696+
qs = "?" + "&".join(["%s=%s" % i for i in list({
697+
"MAP": self.testdata_path + 'test_project_scaledsymbols.qgs',
698+
"SERVICE": "WMS",
699+
"REQUEST": "GetLegendGraphic",
700+
"LAYER": "testlayer",
701+
"FORMAT": "image/png",
702+
"CRS": "EPSG:4326"
703+
}.items())])
704+
705+
r, h = self._result(self._execute_request(qs))
706+
self._img_diff_error(r, h, "WMS_GetLegendGraphic_ScaleSymbol_DefaultMapUnitsPerMillimeter", max_size_diff=QSize(15, 15))
707+
708+
def test_wms_GetLegendGraphic_ScaleSymbol_Scaled_2056(self):
709+
# 1:1000 scale on an EPSG:2056 calculating DPI that is around 96
710+
qs = "?" + "&".join(["%s=%s" % i for i in list({
711+
"MAP": self.testdata_path + 'test_project_scaledsymbols_2056.qgs',
712+
"SERVICE": "WMS",
713+
"REQUEST": "GetLegendGraphic",
714+
"LAYER": "testlayer_2056",
715+
"FORMAT": "image/png",
716+
"SRCHEIGHT": "600",
717+
"SRCWIDTH": "1500",
718+
"BBOX": "2662610.7,1268841.8,2663010.5,1269000.05",
719+
"CRS": "EPSG:2056"
720+
}.items())])
721+
722+
r, h = self._result(self._execute_request(qs))
723+
self._img_diff_error(r, h, "WMS_GetLegendGraphic_ScaleSymbol_Scaled_2056", max_size_diff=QSize(15, 15))
724+
725+
def test_wms_GetLegendGraphic_ScaleSymbol_DefaultScale_2056(self):
726+
# 1:1000 as default value - it's not exactly the same result than passing the bbox and size because of exact DPI 96 (default)
727+
qs = "?" + "&".join(["%s=%s" % i for i in list({
728+
"MAP": self.testdata_path + 'test_project_scaledsymbols_2056.qgs',
729+
"SERVICE": "WMS",
730+
"REQUEST": "GetLegendGraphic",
731+
"LAYER": "testlayer_2056",
732+
"FORMAT": "image/png",
733+
"CRS": "EPSG:2056"
734+
}.items())])
735+
736+
r, h = self._result(self._execute_request(qs))
737+
self._img_diff_error(r, h, "WMS_GetLegendGraphic_ScaleSymbol_DefaultScale_2056", max_size_diff=QSize(15, 15))
738+
694739
def test_wms_GetLegendGraphic_LAYERFONTCOLOR(self):
695740
qs = "?" + "&".join(["%s=%s" % i for i in list({
696741
"MAP": urllib.parse.quote(self.projectPath),

‎tests/testdata/qgis_server/test_project_scaledsymbols.qgs

Lines changed: 211 additions & 206 deletions
Large diffs are not rendered by default.

‎tests/testdata/qgis_server/test_project_scaledsymbols_2056.qgs

Lines changed: 505 additions & 0 deletions
Large diffs are not rendered by default.
189 Bytes
Binary file not shown.
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
PROJCS["CH1903+_LV95",GEOGCS["GCS_CH1903+",DATUM["D_CH1903+",SPHEROID["Bessel_1841",6377397.155,299.1528128]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]],PROJECTION["Hotine_Oblique_Mercator_Azimuth_Center"],PARAMETER["latitude_of_center",46.95240555555556],PARAMETER["longitude_of_center",7.439583333333333],PARAMETER["azimuth",90],PARAMETER["scale_factor",1],PARAMETER["false_easting",2600000],PARAMETER["false_northing",1200000],UNIT["Meter",1]]
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
PROJCS["CH1903+ / LV95",GEOGCS["CH1903+",DATUM["CH1903+",SPHEROID["Bessel 1841",6377397.155,299.1528128,AUTHORITY["EPSG","7004"]],TOWGS84[674.374,15.056,405.346,0,0,0,0],AUTHORITY["EPSG","6150"]],PRIMEM["Greenwich",0,AUTHORITY["EPSG","8901"]],UNIT["degree",0.0174532925199433,AUTHORITY["EPSG","9122"]],AUTHORITY["EPSG","4150"]],PROJECTION["Hotine_Oblique_Mercator_Azimuth_Center"],PARAMETER["latitude_of_center",46.95240555555556],PARAMETER["longitude_of_center",7.439583333333333],PARAMETER["azimuth",90],PARAMETER["rectified_grid_angle",90],PARAMETER["scale_factor",1],PARAMETER["false_easting",2600000],PARAMETER["false_northing",1200000],UNIT["metre",1,AUTHORITY["EPSG","9001"]],AXIS["Easting",EAST],AXIS["Northing",NORTH],AUTHORITY["EPSG","2056"]]
128 Bytes
Binary file not shown.
108 Bytes
Binary file not shown.

0 commit comments

Comments
 (0)
Please sign in to comment.