QGIS API Documentation 4.0.0-Norrköping (1ddcee3d0e4)
Loading...
Searching...
No Matches
qgsmapsettings.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgsmapsettings.cpp
3 --------------------------------------
4 Date : December 2013
5 Copyright : (C) 2013 by Martin Dobias
6 Email : wonder dot sk at gmail dot com
7 ***************************************************************************
8 * *
9 * This program is free software; you can redistribute it and/or modify *
10 * it under the terms of the GNU General Public License as published by *
11 * the Free Software Foundation; either version 2 of the License, or *
12 * (at your option) any later version. *
13 * *
14 ***************************************************************************/
15
16#include "qgsmapsettings.h"
17
19#include "qgsellipsoidutils.h"
20#include "qgsexception.h"
21#include "qgsgeometry.h"
22#include "qgsgrouplayer.h"
23#include "qgslogger.h"
24#include "qgsmaplayer.h"
26#include "qgsmaptopixel.h"
27#include "qgsmessagelog.h"
28#include "qgspainting.h"
29#include "qgsscalecalculator.h"
30#include "qgsunittypes.h"
31#include "qgsxmlutils.h"
32
33#include <QString>
34
35using namespace Qt::StringLiterals;
36
38 : mDpi( QgsPainting::qtDefaultDpiX() ) // DPI that will be used by default for QImage instances
39 , mSize( QSize( 0, 0 ) )
40 , mBackgroundColor( Qt::white )
41 , mSelectionColor( Qt::yellow )
42 , mFlags( Qgis::MapSettingsFlag::Antialiasing | Qgis::MapSettingsFlag::UseAdvancedEffects | Qgis::MapSettingsFlag::DrawLabeling | Qgis::MapSettingsFlag::DrawSelection )
43 , mSegmentationTolerance( M_PI_2 / 90 )
44{
47
49}
50
51void QgsMapSettings::setMagnificationFactor( double factor, const QgsPointXY *center )
52{
53 const double ratio = mMagnificationFactor / factor;
54
55 mMagnificationFactor = factor;
56
57 const double rot = rotation();
58 setRotation( 0.0 );
59
61 ext.scale( ratio, center );
62
63 mRotation = rot;
64 mExtent = ext;
65 mDpi = mDpi / ratio;
66
67 QgsDebugMsgLevel( u"Magnification factor: %1 dpi: %2 ratio: %3"_s.arg( factor ).arg( mDpi ).arg( ratio ), 3 );
68
70}
71
76
78{
79 return mExtent;
80}
81
82void QgsMapSettings::setExtent( const QgsRectangle &extent, bool magnified )
83{
84 QgsRectangle magnifiedExtent = extent;
85
86 if ( !magnified )
87 magnifiedExtent.scale( 1 / mMagnificationFactor );
88
89 mExtent = magnifiedExtent;
90
92}
93
95{
96 return mExtentBuffer;
97}
98
99void QgsMapSettings::setExtentBuffer( const double buffer )
100{
101 mExtentBuffer = buffer;
102}
103
105{
106 return mRotation;
107}
108
109void QgsMapSettings::setRotation( double degrees )
110{
111 if ( qgsDoubleNear( mRotation, degrees ) )
112 return;
113
114 mRotation = degrees;
115
116 // TODO: update extent while keeping scale ?
118}
119
120
122{
124
125 if ( extent.isEmpty() || !extent.isFinite() )
126 {
127 mValid = false;
128 return;
129 }
130
131 // Don't allow zooms where the current extent is so small that it
132 // can't be accurately represented using a double (which is what
133 // currentExtent uses). Excluding 0 avoids a divide by zero and an
134 // infinite loop when rendering to a new canvas. Excluding extents
135 // greater than 1 avoids doing unnecessary calculations.
136
137 // The scheme is to compare the width against the mean x coordinate
138 // (and height against mean y coordinate) and only allow zooms where
139 // the ratio indicates that there is more than about 12 significant
140 // figures (there are about 16 significant figures in a double).
141
142 if ( extent.width() > 0 && extent.height() > 0 && extent.width() < 1 && extent.height() < 1 )
143 {
144 // Use abs() on the extent to avoid the case where the extent is
145 // symmetrical about 0.
146 const double xMean = ( std::fabs( extent.xMinimum() ) + std::fabs( extent.xMaximum() ) ) * 0.5;
147 const double yMean = ( std::fabs( extent.yMinimum() ) + std::fabs( extent.yMaximum() ) ) * 0.5;
148
149 const double xRange = extent.width() / xMean;
150 const double yRange = extent.height() / yMean;
151
152 static const double MIN_PROPORTION = 1e-12;
153 if ( xRange < MIN_PROPORTION || yRange < MIN_PROPORTION )
154 {
155 mValid = false;
156 return;
157 }
158 }
159
160 const double myHeight = mSize.height();
161 const double myWidth = mSize.width();
162
163 if ( !myWidth || !myHeight )
164 {
165 mValid = false;
166 return;
167 }
168
169 // calculate the translation and scaling parameters
170 const double mapUnitsPerPixelY = mExtent.height() / myHeight;
171 const double mapUnitsPerPixelX = mExtent.width() / myWidth;
172 mMapUnitsPerPixel = mapUnitsPerPixelY > mapUnitsPerPixelX ? mapUnitsPerPixelY : mapUnitsPerPixelX;
173
174 // calculate the actual extent of the mapCanvas
175 double dxmin = mExtent.xMinimum(), dxmax = mExtent.xMaximum(), dymin = mExtent.yMinimum(), dymax = mExtent.yMaximum(), whitespace;
176
177 if ( mapUnitsPerPixelY > mapUnitsPerPixelX )
178 {
179 whitespace = ( ( myWidth * mMapUnitsPerPixel ) - mExtent.width() ) * 0.5;
180 dxmin -= whitespace;
181 dxmax += whitespace;
182 }
183 else
184 {
185 whitespace = ( ( myHeight * mMapUnitsPerPixel ) - mExtent.height() ) * 0.5;
186 dymin -= whitespace;
187 dymax += whitespace;
188 }
189
190 mVisibleExtent.set( dxmin, dymin, dxmax, dymax );
191
192 // update the scale
193 mScaleCalculator.setDpi( mDpi );
194 mScale = mScaleCalculator.calculate( mVisibleExtent, mSize.width() );
195
196 bool ok = true;
197 mMapToPixel.setParameters( mapUnitsPerPixel(), visibleExtent().center().x(), visibleExtent().center().y(), outputSize().width(), outputSize().height(), mRotation, &ok );
198
199 mValid = ok;
200
201#if 1 // set visible extent taking rotation in consideration
202 if ( mRotation )
203 {
204 const QgsPointXY p1 = mMapToPixel.toMapCoordinates( QPoint( 0, 0 ) );
205 const QgsPointXY p2 = mMapToPixel.toMapCoordinates( QPoint( 0, myHeight ) );
206 const QgsPointXY p3 = mMapToPixel.toMapCoordinates( QPoint( myWidth, 0 ) );
207 const QgsPointXY p4 = mMapToPixel.toMapCoordinates( QPoint( myWidth, myHeight ) );
208 dxmin = std::min( p1.x(), std::min( p2.x(), std::min( p3.x(), p4.x() ) ) );
209 dymin = std::min( p1.y(), std::min( p2.y(), std::min( p3.y(), p4.y() ) ) );
210 dxmax = std::max( p1.x(), std::max( p2.x(), std::max( p3.x(), p4.x() ) ) );
211 dymax = std::max( p1.y(), std::max( p2.y(), std::max( p3.y(), p4.y() ) ) );
212 mVisibleExtent.set( dxmin, dymin, dxmax, dymax );
213 }
214#endif
215
216 QgsDebugMsgLevel( u"Map units per pixel (x,y) : %1, %2"_s.arg( qgsDoubleToString( mapUnitsPerPixelX ), qgsDoubleToString( mapUnitsPerPixelY ) ), 5 );
217 QgsDebugMsgLevel( u"Pixmap dimensions (x,y) : %1, %2"_s.arg( qgsDoubleToString( mSize.width() ), qgsDoubleToString( mSize.height() ) ), 5 );
218 QgsDebugMsgLevel( u"Extent dimensions (x,y) : %1, %2"_s.arg( qgsDoubleToString( mExtent.width() ), qgsDoubleToString( mExtent.height() ) ), 5 );
219 QgsDebugMsgLevel( mExtent.toString(), 5 );
220 QgsDebugMsgLevel( u"Adjusted map units per pixel (x,y) : %1, %2"_s.arg( qgsDoubleToString( mVisibleExtent.width() / myWidth ), qgsDoubleToString( mVisibleExtent.height() / myHeight ) ), 5 );
221 QgsDebugMsgLevel( u"Recalced pixmap dimensions (x,y) : %1, %2"_s.arg( qgsDoubleToString( mVisibleExtent.width() / mMapUnitsPerPixel ), qgsDoubleToString( mVisibleExtent.height() / mMapUnitsPerPixel ) ), 5 );
222 QgsDebugMsgLevel( u"Scale (assuming meters as map units) = 1:%1"_s.arg( qgsDoubleToString( mScale ) ), 5 );
223 QgsDebugMsgLevel( u"Rotation: %1 degrees"_s.arg( mRotation ), 5 );
224 QgsDebugMsgLevel( u"Extent: %1"_s.arg( mExtent.asWktCoordinates() ), 5 );
225 QgsDebugMsgLevel( u"Visible Extent: %1"_s.arg( mVisibleExtent.asWktCoordinates() ), 5 );
226 QgsDebugMsgLevel( u"Magnification factor: %1"_s.arg( mMagnificationFactor ), 5 );
227}
228
229void QgsMapSettings::matchRasterizedRenderingPolicyToFlags()
230{
237}
238
240{
241 return mSize;
242}
243
245{
246 mSize = size;
247
249}
250
252{
253 return mDevicePixelRatio;
254}
255
257{
258 mDevicePixelRatio = dpr;
260}
261
263{
264 return outputSize() * mDevicePixelRatio;
265}
266
268{
269 return mDpi;
270}
271
273{
274 mDpi = dpi;
275
277}
278
280{
281 return mDpiTarget;
282}
283
285{
286 mDpiTarget = dpi;
287}
288
289QStringList QgsMapSettings::layerIds( bool expandGroupLayers ) const
290{
291 if ( !expandGroupLayers || !mHasGroupLayers )
292 {
293 return mLayerIds;
294 }
295 else
296 {
297 const QList<QgsMapLayer * > mapLayers = layers( expandGroupLayers );
298 QStringList res;
299 res.reserve( mapLayers.size() );
300 for ( const QgsMapLayer *layer : mapLayers )
301 res << layer->id();
302 return res;
303 }
304}
305
306QList<QgsMapLayer *> QgsMapSettings::layers( bool expandGroupLayers ) const
307{
308 const QList<QgsMapLayer *> actualLayers = _qgis_listQPointerToRaw( mLayers );
309 if ( !expandGroupLayers )
310 return actualLayers;
311
312 QList< QgsMapLayer * > result;
313
314 std::function< void( const QList< QgsMapLayer * > &layers ) > expandLayers;
315 expandLayers = [&result, &expandLayers]( const QList< QgsMapLayer * > &layers ) {
316 for ( QgsMapLayer *layer : layers )
317 {
318 if ( QgsGroupLayer *groupLayer = qobject_cast< QgsGroupLayer * >( layer ) )
319 {
320 expandLayers( groupLayer->childLayers() );
321 }
322 else
323 {
324 result << layer;
325 }
326 }
327 };
328
329 expandLayers( actualLayers );
330 return result;
331}
332
333template<typename T> QVector<T> QgsMapSettings::layers() const
334{
335 const QList<QgsMapLayer *> actualLayers = _qgis_listQPointerToRaw( mLayers );
336
337 QVector<T> layers;
338 for ( QgsMapLayer *layer : actualLayers )
339 {
340 T tLayer = qobject_cast<T>( layer );
341 if ( tLayer )
342 {
343 layers << tLayer;
344 }
345 }
346 return layers;
347}
348
349void QgsMapSettings::setLayers( const QList<QgsMapLayer *> &layers )
350{
351 // filter list, removing null layers and non-spatial layers
352 auto filteredList = layers;
353 filteredList.erase( std::remove_if( filteredList.begin(), filteredList.end(), []( QgsMapLayer *layer ) { return !layer || !layer->isSpatial(); } ), filteredList.end() );
354
355 mLayers = _qgis_listRawToQPointer( filteredList );
356
357 // pre-generate and store layer IDs, so that we can safely access them from other threads
358 // without needing to touch the actual map layer object
359 mLayerIds.clear();
360 mHasGroupLayers = false;
361 mLayerIds.reserve( mLayers.size() );
362 for ( const QgsMapLayer *layer : std::as_const( mLayers ) )
363 {
364 mLayerIds << layer->id();
365 if ( layer->type() == Qgis::LayerType::Group )
366 mHasGroupLayers = true;
367 }
368}
369
370QMap<QString, QString> QgsMapSettings::layerStyleOverrides() const
371{
373}
374
375void QgsMapSettings::setLayerStyleOverrides( const QMap<QString, QString> &overrides )
376{
377 mLayerStyleOverrides = overrides;
378}
379
381{
382 mDestCRS = crs;
383 mScaleCalculator.setMapUnits( crs.mapUnits() );
384 // Since the map units have changed, force a recalculation of the scale.
386}
387
392
394{
396 if ( !params.valid )
397 {
398 return false;
399 }
400 else
401 {
403 return true;
404 }
405}
406
408{
409 mFlags = flags;
410 matchRasterizedRenderingPolicyToFlags();
411}
412
414{
415 if ( on )
416 mFlags |= flag;
417 else
418 mFlags &= ~( static_cast< int >( flag ) );
419 matchRasterizedRenderingPolicyToFlags();
420}
421
426
428{
429 return mFlags.testFlag( flag );
430}
431
433{
434 return mScaleCalculator.mapUnits();
435}
436
441
443{
444 mScaleCalculator.setMethod( method );
446}
447
449{
450 return mValid;
451}
452
457
459{
460 QPolygonF poly;
461
462 const QSize &sz = outputSize();
463 const QgsMapToPixel &m2p = mapToPixel();
464
465 poly << m2p.toMapCoordinates( 0.0, 0.0 ).toQPointF();
466 poly << m2p.toMapCoordinates( static_cast<double>( sz.width() ), 0.0 ).toQPointF();
467 poly << m2p.toMapCoordinates( static_cast<double>( sz.width() ), static_cast<double>( sz.height() ) ).toQPointF();
468 poly << m2p.toMapCoordinates( 0.0, static_cast<double>( sz.height() ) ).toQPointF();
469
470 return poly;
471}
472
474{
475 QPolygonF poly;
476
477 const QSize &sz = outputSize();
478 const QgsMapToPixel &m2p = mapToPixel();
479
480 // Transform tilebuffer in pixel.
481 // Original tilebuffer is in pixel and transformed only according
482 // extent width (see QgsWmsRenderContext::mapTileBuffer)
483
484 const double mapUnitsPerPixel = mExtent.width() / sz.width();
485 const double buffer = mExtentBuffer / mapUnitsPerPixel;
486
487 poly << m2p.toMapCoordinates( -buffer, -buffer ).toQPointF();
488 poly << m2p.toMapCoordinates( static_cast<double>( sz.width() + buffer ), -buffer ).toQPointF();
489 poly << m2p.toMapCoordinates( static_cast<double>( sz.width() + buffer ), static_cast<double>( sz.height() + buffer ) ).toQPointF();
490 poly << m2p.toMapCoordinates( -buffer, static_cast<double>( sz.height() + buffer ) ).toQPointF();
491
492 return poly;
493}
494
496{
497 return mMapUnitsPerPixel;
498}
499
501{
502 return mScale;
503}
504
506{
507#ifdef QGISDEBUG
508 if ( !mHasTransformContext )
509 QgsDebugMsgLevel( u"No QgsCoordinateTransformContext context set for transform"_s, 4 );
510#endif
511
512 return mTransformContext;
513}
514
516{
517 mTransformContext = context;
518#ifdef QGISDEBUG
519 mHasTransformContext = true;
520#endif
521}
522
524{
525 if ( !layer )
526 return QgsCoordinateTransform();
527
529}
530
532{
533 // Output width in inches
534 const double outputWidthInInches = outputSize().width() / outputDpi();
535
536 // Desired visible width (honouring scale)
537 const double scaledWidthInInches = outputWidthInInches * scale;
538
540 {
541 // Start with some fraction of the current extent around the center
542 const double delta = mExtent.width() / 100.;
543 QgsRectangle ext( center.x() - delta, center.y() - delta, center.x() + delta, center.y() + delta );
544 // Get scale at extent, and then scale extent to the desired scale
545 const double testScale = mScaleCalculator.calculate( ext, outputSize().width() );
546 ext.scale( scale / testScale );
547 return ext;
548 }
549 else
550 {
551 // Conversion from inches to mapUnits - this is safe to use, because we know here that the map units AREN'T in degrees
552 const double conversionFactor = QgsUnitTypes::fromUnitToUnitFactor( Qgis::DistanceUnit::Feet, mapUnits() ) / 12;
553
554 const double delta = 0.5 * scaledWidthInInches * conversionFactor;
555 return QgsRectangle( center.x() - delta, center.y() - delta, center.x() + delta, center.y() + delta );
556 }
557}
558
560{
561 return mScaleCalculator.calculate( extent, outputSize().width() );
562}
563
564double QgsMapSettings::layerToMapUnits( const QgsMapLayer *layer, const QgsRectangle &referenceExtent ) const
565{
566 return layerTransform( layer ).scaleFactor( referenceExtent );
567}
568
569
571{
572 try
573 {
575 if ( ct.isValid() )
576 {
577 QgsDebugMsgLevel( u"sourceCrs = %1"_s.arg( ct.sourceCrs().authid() ), 3 );
578 QgsDebugMsgLevel( u"destCRS = %1"_s.arg( ct.destinationCrs().authid() ), 3 );
579 QgsDebugMsgLevel( u"extent %1"_s.arg( extent.toString() ), 3 );
582 }
583 }
584 catch ( QgsCsException &cse )
585 {
586 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
587 }
588
589 QgsDebugMsgLevel( u"proj extent = %1 "_s.arg( extent.toString() ), 3 );
590
591 return extent;
592}
593
594
596{
597 try
598 {
601 if ( ct.isValid() )
602 {
603 QgsDebugMsgLevel( u"sourceCrs = %1"_s.arg( ct.sourceCrs().authid() ), 3 );
604 QgsDebugMsgLevel( u"destCRS = %1"_s.arg( ct.destinationCrs().authid() ), 3 );
605 QgsDebugMsgLevel( u"extent = %1"_s.arg( extent.toString() ), 3 );
607 }
608 }
609 catch ( QgsCsException &cse )
610 {
611 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
612 }
613
614 QgsDebugMsgLevel( u"proj extent = %1"_s.arg( extent.toString() ), 3 );
615
616 return extent;
617}
618
619
621{
622 try
623 {
624 const QgsCoordinateTransform ct = layerTransform( layer );
625 if ( ct.isValid() )
626 point = ct.transform( point, Qgis::TransformDirection::Forward );
627 }
628 catch ( QgsCsException &cse )
629 {
630 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
631 }
632
633 return point;
634}
635
637{
638 double x = point.x();
639 double y = point.y();
640 double z = point.z();
641 const double m = point.m();
642
643 try
644 {
645 const QgsCoordinateTransform ct = layerTransform( layer );
646 if ( ct.isValid() )
648 }
649 catch ( QgsCsException &cse )
650 {
651 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
652 }
653
654 return QgsPoint( x, y, z, m );
655}
656
657
659{
660 try
661 {
662 const QgsCoordinateTransform ct = layerTransform( layer );
663 if ( ct.isValid() )
665 }
666 catch ( QgsCsException &cse )
667 {
668 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
669 }
670
671 return rect;
672}
673
674
676{
677 try
678 {
679 const QgsCoordinateTransform ct = layerTransform( layer );
680 if ( ct.isValid() )
681 point = ct.transform( point, Qgis::TransformDirection::Reverse );
682 }
683 catch ( QgsCsException &cse )
684 {
685 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
686 }
687
688 return point;
689}
690
692{
693 double x = point.x();
694 double y = point.y();
695 double z = point.z();
696 const double m = point.m();
697
698 try
699 {
700 const QgsCoordinateTransform ct = layerTransform( layer );
701 if ( ct.isValid() )
703 }
704 catch ( QgsCsException &cse )
705 {
706 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
707 }
708
709 return QgsPoint( x, y, z, m );
710}
711
712
714{
715 try
716 {
717 const QgsCoordinateTransform ct = layerTransform( layer );
718 if ( ct.isValid() )
720 }
721 catch ( QgsCsException &cse )
722 {
723 QgsMessageLog::logMessage( QObject::tr( "Transform error caught: %1" ).arg( cse.what() ), QObject::tr( "CRS" ) );
724 }
725
726 return rect;
727}
728
729
731{
732 // reset the map canvas extent since the extent may now be smaller
733 // We can't use a constructor since QgsRectangle normalizes the rectangle upon construction
735 fullExtent.setNull();
736
737 // iterate through the map layers and test each layers extent
738 // against the current min and max values
739 QgsDebugMsgLevel( u"Layer count: %1"_s.arg( mLayers.count() ), 5 );
740 const auto constMLayers = mLayers;
741 for ( const QgsWeakMapLayerPointer &layerPtr : constMLayers )
742 {
743 if ( QgsMapLayer *lyr = layerPtr.data() )
744 {
745 QgsDebugMsgLevel( "Updating extent using " + lyr->name(), 5 );
746 QgsDebugMsgLevel( "Input extent: " + lyr->extent().toString(), 5 );
747
748 if ( lyr->extent().isNull() )
749 continue;
750
751 // Layer extents are stored in the coordinate system (CS) of the
752 // layer. The extent must be projected to the canvas CS
753 const QgsRectangle extent = layerExtentToOutputExtent( lyr, lyr->extent() );
754
755 QgsDebugMsgLevel( "Output extent: " + extent.toString(), 5 );
756 fullExtent.combineExtentWith( extent );
757 }
758 }
759
760 if ( fullExtent.width() == 0.0 || fullExtent.height() == 0.0 )
761 {
762 // If all of the features are at the one point, buffer the
763 // rectangle a bit. If they are all at zero, do something a bit
764 // more crude.
765
766 if ( fullExtent.xMinimum() == 0.0 && fullExtent.xMaximum() == 0.0 && fullExtent.yMinimum() == 0.0 && fullExtent.yMaximum() == 0.0 )
767 {
768 fullExtent.set( -1.0, -1.0, 1.0, 1.0 );
769 }
770 else
771 {
772 const double padFactor = 1e-8;
773 const double widthPad = fullExtent.xMinimum() * padFactor;
774 const double heightPad = fullExtent.yMinimum() * padFactor;
775 const double xmin = fullExtent.xMinimum() - widthPad;
776 const double xmax = fullExtent.xMaximum() + widthPad;
777 const double ymin = fullExtent.yMinimum() - heightPad;
778 const double ymax = fullExtent.yMaximum() + heightPad;
779 fullExtent.set( xmin, ymin, xmax, ymax );
780 }
781 }
782
783 QgsDebugMsgLevel( "Full extent: " + fullExtent.toString(), 5 );
784 return fullExtent;
785}
786
787
788void QgsMapSettings::readXml( QDomNode &node )
789{
790 // set destination CRS
792 const QDomNode srsNode = node.namedItem( u"destinationsrs"_s );
793 if ( !srsNode.isNull() )
794 {
795 srs.readXml( srsNode );
796 }
797 setDestinationCrs( srs );
798
799 // set extent
800 const QDomNode extentNode = node.namedItem( u"extent"_s );
801 const QgsRectangle aoi = QgsXmlUtils::readRectangle( extentNode.toElement() );
802 setExtent( aoi );
803
804 // set rotation
805 const QDomNode rotationNode = node.namedItem( u"rotation"_s );
806 const QString rotationVal = rotationNode.toElement().text();
807 if ( !rotationVal.isEmpty() )
808 {
809 const double rot = rotationVal.toDouble();
810 setRotation( rot );
811 }
812
813 //render map tile
814 const QDomElement renderMapTileElem = node.firstChildElement( u"rendermaptile"_s );
815 if ( !renderMapTileElem.isNull() )
816 {
817 setFlag( Qgis::MapSettingsFlag::RenderMapTile, renderMapTileElem.text() == "1"_L1 );
818 }
819}
820
821
822void QgsMapSettings::writeXml( QDomNode &node, QDomDocument &doc )
823{
824 // units
825 node.appendChild( QgsXmlUtils::writeMapUnits( mapUnits(), doc ) );
826
827 // Write current view extents
828 node.appendChild( QgsXmlUtils::writeRectangle( extent(), doc ) );
829
830 // Write current view rotation
831 QDomElement rotNode = doc.createElement( u"rotation"_s );
832 rotNode.appendChild( doc.createTextNode( qgsDoubleToString( rotation() ) ) );
833 node.appendChild( rotNode );
834
835 // destination CRS
836 if ( mDestCRS.isValid() )
837 {
838 QDomElement srsNode = doc.createElement( u"destinationsrs"_s );
839 node.appendChild( srsNode );
840 mDestCRS.writeXml( srsNode, doc );
841 }
842
843 //render map tile
844 QDomElement renderMapTileElem = doc.createElement( u"rendermaptile"_s );
845 const QDomText renderMapTileText = doc.createTextNode( testFlag( Qgis::MapSettingsFlag::RenderMapTile ) ? "1" : "0" );
846 renderMapTileElem.appendChild( renderMapTileText );
847 node.appendChild( renderMapTileElem );
848}
849
854
856{
857 mLabelBoundaryGeometry = boundary;
858}
859
861{
862 mClippingRegions.append( region );
863}
864
865void QgsMapSettings::setClippingRegions( const QList<QgsMapClippingRegion> &regions )
866{
867 mClippingRegions = regions;
868}
869
870QList<QgsMapClippingRegion> QgsMapSettings::clippingRegions() const
871{
872 return mClippingRegions;
873}
874
876{
877 mMaskRenderSettings = settings;
878}
879
881{
882 mRenderedFeatureHandlers.append( handler );
883}
884
885QList<QgsRenderedFeatureHandlerInterface *> QgsMapSettings::renderedFeatureHandlers() const
886{
887 return mRenderedFeatureHandlers;
888}
889
891{
892 return mZRange;
893}
894
896{
897 mZRange = zRange;
898}
899
904
909
911{
912 return mFrameRate;
913}
914
916{
917 mFrameRate = rate;
918}
919
921{
922 return mCurrentFrame;
923}
924
925void QgsMapSettings::setCurrentFrame( long long frame )
926{
927 mCurrentFrame = frame;
928}
929
934
939
944
964
965QHash<QString, QgsSelectiveMaskingSourceSet> QgsMapSettings::selectiveMaskingSourceSets() const
966{
968}
969
970void QgsMapSettings::setSelectiveMaskingSourceSets( const QVector<QgsSelectiveMaskingSourceSet> &sets )
971{
973 mSelectiveMaskingSourceSets.reserve( sets.size() );
974 for ( const QgsSelectiveMaskingSourceSet &set : sets )
975 {
976 mSelectiveMaskingSourceSets.insert( set.id(), set );
977 }
978}
Provides global constants and enumerations for use throughout the application.
Definition qgis.h:62
RasterizedRenderingPolicy
Policies controlling when rasterisation of content during renders is permitted.
Definition qgis.h:2798
@ Default
Allow raster-based rendering in situations where it is required for correct rendering or where it wil...
Definition qgis.h:2799
@ PreferVector
Prefer vector-based rendering, when the result will still be visually near-identical to a raster-base...
Definition qgis.h:2800
@ ForceVector
Always force vector-based rendering, even when the result will be visually different to a raster-base...
Definition qgis.h:2801
QFlags< MapSettingsFlag > MapSettingsFlags
Map settings flags.
Definition qgis.h:2835
@ NoSimplification
No simplification can be applied.
Definition qgis.h:3131
DistanceUnit
Units of distance.
Definition qgis.h:5170
@ Feet
Imperial feet.
Definition qgis.h:5173
@ Unknown
Unknown distance unit.
Definition qgis.h:5220
@ Degrees
Degrees, for planar geographic CRS distance measurements.
Definition qgis.h:5177
@ Group
Composite group layer. Added in QGIS 3.24.
Definition qgis.h:214
ScaleCalculationMethod
Scale calculation logic.
Definition qgis.h:5447
RendererUsage
Usage of the renderer.
Definition qgis.h:3559
@ Forward
Forward transform (from source to destination).
Definition qgis.h:2765
@ Reverse
Reverse/inverse transform (from destination to source).
Definition qgis.h:2766
MapSettingsFlag
Flags which adjust the way maps are rendered.
Definition qgis.h:2811
@ RenderMapTile
Draw map such that there are no problems between adjacent tiles.
Definition qgis.h:2820
@ ForceVectorOutput
Vector graphics should not be cached and drawn as raster images.
Definition qgis.h:2814
@ UseAdvancedEffects
Enable layer opacity and blending effects.
Definition qgis.h:2815
Represents a coordinate reference system (CRS).
bool readXml(const QDomNode &node)
Restores state from the given DOM node.
Contains information about the context in which a coordinate transform is executed.
Handles coordinate transforms between two coordinate systems.
QgsCoordinateReferenceSystem sourceCrs() const
Returns the source coordinate reference system, which the transform will transform coordinates from.
void setBallparkTransformsAreAppropriate(bool appropriate)
Sets whether approximate "ballpark" results are appropriate for this coordinate transform.
double scaleFactor(const QgsRectangle &referenceExtent) const
Computes an estimated conversion factor between source and destination units:
QgsPointXY transform(const QgsPointXY &point, Qgis::TransformDirection direction=Qgis::TransformDirection::Forward) const
Transform the point from the source CRS to the destination CRS.
void transformInPlace(double &x, double &y, double &z, Qgis::TransformDirection direction=Qgis::TransformDirection::Forward) const
Transforms an array of x, y and z double coordinates in place, from the source CRS to the destination...
QgsRectangle transformBoundingBox(const QgsRectangle &rectangle, Qgis::TransformDirection direction=Qgis::TransformDirection::Forward, bool handle180Crossover=false) const
Transforms a rectangle from the source CRS to the destination CRS.
bool isValid() const
Returns true if the coordinate transform is valid, ie both the source and destination CRS have been s...
QgsCoordinateReferenceSystem destinationCrs() const
Returns the destination coordinate reference system, which the transform will transform coordinates t...
Custom exception class for Coordinate Reference System related exceptions.
QgsRange which stores a range of double values.
Definition qgsrange.h:217
Renders elevation shading on an image with different methods (eye dome lighting, hillshading,...
static EllipsoidParameters ellipsoidParameters(const QString &ellipsoid)
Returns the parameters for the specified ellipsoid.
QString what() const
A geometry is the spatial representation of a feature.
A map layer which consists of a set of child layers, where all component layers are rendered as a sin...
A map clipping region (in map coordinates and CRS).
Base class for all map layer types.
Definition qgsmaplayer.h:83
QgsCoordinateReferenceSystem crs
Definition qgsmaplayer.h:90
QString id
Definition qgsmaplayer.h:86
Qgis::LayerType type
Definition qgsmaplayer.h:93
void setElevationShadingRenderer(const QgsElevationShadingRenderer &renderer)
Sets the shading renderer used to render shading on the entire map.
QSize deviceOutputSize() const
Returns the device output size of the map render.
Qgis::DistanceUnit mapUnits() const
Returns the units of the map's geographical coordinates - used for scale calculation.
Qgis::RendererUsage rendererUsage() const
Returns the rendering usage.
QgsVectorSimplifyMethod mSimplifyMethod
void addClippingRegion(const QgsMapClippingRegion &region)
Adds a new clipping region to the map settings.
void writeXml(QDomNode &node, QDomDocument &doc)
Writes the map settings to an XML node.
QgsPointXY layerToMapCoordinates(const QgsMapLayer *layer, QgsPointXY point) const
transform point coordinates from layer's CRS to output CRS
QgsMaskRenderSettings mMaskRenderSettings
QList< QgsMapLayer * > layers(bool expandGroupLayers=false) const
Returns the list of layers which will be rendered in the map.
Qgis::RendererUsage mRendererUsage
QgsRectangle mVisibleExtent
Extent with some additional white space that matches the output aspect ratio.
QPolygonF visiblePolygon() const
Returns the visible area as a polygon (may be rotated).
void addRenderedFeatureHandler(QgsRenderedFeatureHandlerInterface *handler)
Adds a rendered feature handler to use while rendering the map settings.
void setLayers(const QList< QgsMapLayer * > &layers)
Sets the list of layers to render in the map.
double scale() const
Returns the calculated map scale.
void setFrameRate(double rate)
Sets the frame rate of the map (in frames per second), for maps which are part of an animation.
void setFlags(Qgis::MapSettingsFlags flags)
Sets combination of flags that will be used for rendering.
Qgis::MapSettingsFlags mFlags
QgsCoordinateTransform layerTransform(const QgsMapLayer *layer) const
Returns the coordinate transform from layer's CRS to destination CRS.
QgsRectangle layerExtentToOutputExtent(const QgsMapLayer *layer, QgsRectangle extent) const
transform bounding box from layer's CRS to output CRS
QgsDoubleRange zRange() const
Returns the range of z-values which will be visible in the map.
bool setEllipsoid(const QString &ellipsoid)
Sets the ellipsoid by its acronym.
void setScaleMethod(Qgis::ScaleCalculationMethod method)
Sets the method to use for scale calculations for the map.
void setDpiTarget(double dpi)
Sets the target dpi (dots per inch) to be taken into consideration when rendering.
double magnificationFactor() const
Returns the magnification factor.
QHash< QString, QgsSelectiveMaskingSourceSet > mSelectiveMaskingSourceSets
QStringList mLayerIds
QgsGeometry labelBoundaryGeometry() const
Returns the label boundary geometry, which restricts where in the rendered map labels are permitted t...
QList< QgsRenderedFeatureHandlerInterface * > renderedFeatureHandlers() const
Returns the list of rendered feature handlers to use while rendering the map settings.
QStringList layerIds(bool expandGroupLayers=false) const
Returns the list of layer IDs which will be rendered in the map.
void setDevicePixelRatio(float dpr)
Sets the device pixel ratio.
QString mEllipsoid
ellipsoid acronym (from table tbl_ellipsoids)
void setZRange(const QgsDoubleRange &range)
Sets the range of z-values which will be visible in the map.
double dpiTarget() const
Returns the target DPI (dots per inch) to be taken into consideration when rendering.
long long currentFrame() const
Returns the current frame number of the map, for maps which are part of an animation.
bool mValid
Whether the actual settings are valid (set in updateDerived()).
void setOutputDpi(double dpi)
Sets the dpi (dots per inch) used for conversion between real world units (e.g.
const QgsMapToPixel & mapToPixel() const
double mapUnitsPerPixel() const
Returns the distance in geographical coordinates that equals to one pixel in the map.
void setRendererUsage(Qgis::RendererUsage rendererUsage)
Sets the rendering usage.
float devicePixelRatio() const
Returns the device pixel ratio.
void setRasterizedRenderingPolicy(Qgis::RasterizedRenderingPolicy policy)
Sets the policy controlling when rasterisation of content during renders is permitted.
QgsRectangle mExtent
QSize outputSize() const
Returns the size of the resulting map image, in pixels.
QgsRectangle extent() const
Returns geographical coordinates of the rectangle that should be rendered.
void setMaskSettings(const QgsMaskRenderSettings &settings)
Sets the mask render settings, which control how masks are drawn and behave during the map render.
QMap< QString, QString > mLayerStyleOverrides
QgsGeometry mLabelBoundaryGeometry
void setLayerStyleOverrides(const QMap< QString, QString > &overrides)
Sets the map of map layer style overrides (key: layer ID, value: style name) where a different style ...
QgsElevationShadingRenderer mShadingRenderer
QgsCoordinateTransformContext mTransformContext
void setExtent(const QgsRectangle &rect, bool magnified=true)
Sets the coordinates of the rectangle which should be rendered.
void setClippingRegions(const QList< QgsMapClippingRegion > &regions)
Sets the list of clipping regions to apply to the map.
double layerToMapUnits(const QgsMapLayer *layer, const QgsRectangle &referenceExtent=QgsRectangle()) const
Computes an estimated conversion factor between layer and map units, where layerUnits × layerToMapUni...
double extentBuffer() const
Returns the buffer in map units to use around the visible extent for rendering symbols whose correspo...
QVector< T > layers() const
Returns a list of registered map layers with a specified layer type.
void setSelectiveMaskingSourceSets(const QVector< QgsSelectiveMaskingSourceSet > &sets)
Sets a list of all selective masking source sets defined for the map.
QgsScaleCalculator mScaleCalculator
Qgis::MapSettingsFlags flags() const
Returns combination of flags used for rendering.
Qgis::ScaleCalculationMethod scaleMethod() const
Returns the method to use for scale calculations for the map.
double frameRate() const
Returns the frame rate of the map (in frames per second), for maps which are part of an animation.
void setExtentBuffer(double buffer)
Sets the buffer in map units to use around the visible extent for rendering symbols whose correspondi...
QgsRectangle visibleExtent() const
Returns the actual extent derived from requested extent that takes output image size into account.
QgsRectangle outputExtentToLayerExtent(const QgsMapLayer *layer, QgsRectangle extent) const
transform bounding box from output CRS to layer's CRS
QgsRectangle fullExtent() const
returns current extent of layer set
void setTransformContext(const QgsCoordinateTransformContext &context)
Sets the coordinate transform context, which stores various information regarding which datum transfo...
void setRotation(double rotation)
Sets the rotation of the resulting map image, in degrees clockwise.
double computeScaleForExtent(const QgsRectangle &extent) const
Compute the scale that corresponds to the specified extent.
QString ellipsoid() const
Returns ellipsoid's acronym.
double mMagnificationFactor
void setCurrentFrame(long long frame)
Sets the current frame of the map, for maps which are part of an animation.
const QgsElevationShadingRenderer & elevationShadingRenderer() const
Returns the shading renderer used to render shading on the entire map.
QHash< QString, QgsSelectiveMaskingSourceSet > selectiveMaskingSourceSets() const
Returns a hash of all selective masking source sets defined for the map.
QgsCoordinateReferenceSystem mDestCRS
double outputDpi() const
Returns the DPI (dots per inch) used for conversion between real world units (e.g.
void setLabelBoundaryGeometry(const QgsGeometry &boundary)
Sets the label boundary geometry, which restricts where in the rendered map labels are permitted to b...
Qgis::RasterizedRenderingPolicy mRasterizedRenderingPolicy
QgsMapToPixel mMapToPixel
bool testFlag(Qgis::MapSettingsFlag flag) const
Check whether a particular flag is enabled.
QMap< QString, QString > layerStyleOverrides() const
Returns the map of map layer style overrides (key: layer ID, value: style name) where a different sty...
double rotation() const
Returns the rotation of the resulting map image, in degrees clockwise.
QList< QgsMapClippingRegion > clippingRegions() const
Returns the list of clipping regions to apply to the map.
bool hasValidSettings() const
Check whether the map settings are valid and can be used for rendering.
QgsWeakMapLayerPointerList mLayers
list of layers to be rendered (stored as weak pointers)
void setOutputSize(QSize size)
Sets the size of the resulting map image, in pixels.
Qgis::RasterizedRenderingPolicy rasterizedRenderingPolicy() const
Returns the policy controlling when rasterisation of content during renders is permitted.
QgsPointXY mapToLayerCoordinates(const QgsMapLayer *layer, QgsPointXY point) const
transform point coordinates from output CRS to layer's CRS
long long mCurrentFrame
QgsCoordinateReferenceSystem destinationCrs() const
Returns the destination coordinate reference system for the map render.
QPolygonF visiblePolygonWithBuffer() const
Returns the visible area as a polygon (may be rotated) with extent buffer included.
void setFlag(Qgis::MapSettingsFlag flag, bool on=true)
Enable or disable a particular flag (other flags are not affected).
void setDestinationCrs(const QgsCoordinateReferenceSystem &crs)
Sets the destination crs (coordinate reference system) for the map render.
void readXml(QDomNode &node)
Restore the map settings from a XML node.
double mSegmentationTolerance
QgsRectangle computeExtentForScale(const QgsPointXY &center, double scale) const
Compute the extent such that its center is at the specified position (mapped to the destinatonCrs) an...
void setMagnificationFactor(double factor, const QgsPointXY *center=nullptr)
Set the magnification factor.
QgsCoordinateTransformContext transformContext() const
Returns the coordinate transform context, which stores various information regarding which datum tran...
Perform transforms between map coordinates and device coordinates.
QgsPointXY toMapCoordinates(int x, int y) const
Transforms device coordinates to map (world) coordinates.
Contains settings regarding how masks are calculated and handled during a map render.
static void logMessage(const QString &message, const QString &tag=QString(), Qgis::MessageLevel level=Qgis::MessageLevel::Warning, bool notifyUser=true, const char *file=__builtin_FILE(), const char *function=__builtin_FUNCTION(), int line=__builtin_LINE(), Qgis::StringFormat format=Qgis::StringFormat::PlainText)
Adds a message to the log instance (and creates it if necessary).
Contains miscellaneous painting utility functions.
Definition qgspainting.h:32
Represents a 2D point.
Definition qgspointxy.h:62
double y
Definition qgspointxy.h:66
double x
Definition qgspointxy.h:65
QPointF toQPointF() const
Converts a point to a QPointF.
Definition qgspointxy.h:168
Point geometry type, with support for z-dimension and m-values.
Definition qgspoint.h:53
double z
Definition qgspoint.h:58
double x
Definition qgspoint.h:56
double m
Definition qgspoint.h:59
double y
Definition qgspoint.h:57
A rectangle specified with double values.
void scale(double scaleFactor, const QgsPointXY *c=nullptr)
Scale the rectangle around its center point.
An interface for classes which provide custom handlers for features rendered as part of a map render ...
Represents a named set of selective masking sources (QgsSelectiveMaskSource).
static Q_INVOKABLE double fromUnitToUnitFactor(Qgis::DistanceUnit fromUnit, Qgis::DistanceUnit toUnit)
Returns the conversion factor between the specified distance units.
static QDomElement writeRectangle(const QgsRectangle &rect, QDomDocument &doc, const QString &elementName=u"extent"_s)
Encodes a rectangle to a DOM element.
static QgsRectangle readRectangle(const QDomElement &element)
static QDomElement writeMapUnits(Qgis::DistanceUnit units, QDomDocument &doc)
Encodes a distance unit to a DOM element.
QString qgsDoubleToString(double a, int precision=17)
Returns a string representation of a double.
Definition qgis.h:6893
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference).
Definition qgis.h:6975
#define QgsDebugMsgLevel(str, level)
Definition qgslogger.h:63
QPointer< QgsMapLayer > QgsWeakMapLayerPointer
Weak pointer for QgsMapLayer.
Contains parameters for an ellipsoid.
bool valid
Whether ellipsoid parameters are valid.