Branch data Line data Source code
1 : : /*************************************************************************** 2 : : qgsmapsettingsutils.cpp 3 : : ------------------- 4 : : begin : May 2017 5 : : copyright : (C) 2017 by Mathieu Pellerin 6 : : email : nirvn dot asia at gmail dot com 7 : : ***************************************************************************/ 8 : : 9 : : /*************************************************************************** 10 : : * * 11 : : * This program is free software; you can redistribute it and/or modify * 12 : : * it under the terms of the GNU General Public License as published by * 13 : : * the Free Software Foundation; either version 2 of the License, or * 14 : : * (at your option) any later version. * 15 : : * * 16 : : ***************************************************************************/ 17 : : 18 : : #include "qgsmapsettings.h" 19 : : #include "qgsmapsettingsutils.h" 20 : : #include "qgspallabeling.h" 21 : : #include "qgstextformat.h" 22 : : #include "qgsvectorlayer.h" 23 : : #include "qgsabstractgeopdfexporter.h" 24 : : 25 : : #include <QString> 26 : : 27 : 0 : QStringList QgsMapSettingsUtils::containsAdvancedEffects( const QgsMapSettings &mapSettings, EffectsCheckFlags flags ) 28 : : { 29 : 0 : QSet< QString > layers; 30 : : 31 : 0 : QgsTextFormat layerFormat; 32 : 0 : const auto constLayers = mapSettings.layers(); 33 : 0 : for ( QgsMapLayer *layer : constLayers ) 34 : : { 35 : 0 : if ( layer && layer->isInScaleRange( mapSettings.scale() ) ) 36 : : { 37 : 0 : bool layerHasAdvancedBlendMode = false; 38 : 0 : if ( layer->blendMode() != QPainter::CompositionMode_SourceOver ) 39 : : { 40 : 0 : if ( flags & EffectsCheckFlag::IgnoreGeoPdfSupportedEffects ) 41 : : { 42 : 0 : layerHasAdvancedBlendMode = !QgsAbstractGeoPdfExporter::compositionModeSupported( layer->blendMode() ); 43 : 0 : } 44 : : else 45 : : { 46 : 0 : layerHasAdvancedBlendMode = true; 47 : : } 48 : 0 : } 49 : : 50 : 0 : if ( layerHasAdvancedBlendMode ) 51 : : { 52 : 0 : layers << layer->name(); 53 : 0 : } 54 : : // if vector layer, check labels and feature blend mode 55 : 0 : if ( QgsVectorLayer *currentVectorLayer = qobject_cast<QgsVectorLayer *>( layer ) ) 56 : : { 57 : 0 : if ( currentVectorLayer->featureBlendMode() != QPainter::CompositionMode_SourceOver ) 58 : : { 59 : 0 : layers << layer->name(); 60 : 0 : } 61 : : // check label blend modes 62 : 0 : if ( QgsPalLabeling::staticWillUseLayer( currentVectorLayer ) ) 63 : : { 64 : : // Check all label blending properties 65 : 0 : layerFormat.readFromLayer( currentVectorLayer ); 66 : 0 : if ( layerFormat.containsAdvancedEffects() ) 67 : : { 68 : 0 : layers << layer->name(); 69 : 0 : } 70 : 0 : } 71 : 0 : } 72 : 0 : } 73 : : } 74 : : 75 : 0 : return qgis::setToList( layers ); 76 : 0 : } 77 : : 78 : 0 : void QgsMapSettingsUtils::worldFileParameters( const QgsMapSettings &mapSettings, double &a, double &b, double &c, double &d, double &e, double &f ) 79 : : { 80 : 0 : QgsMapSettings ms = mapSettings; 81 : : 82 : 0 : double rotation = ms.rotation(); 83 : 0 : double alpha = rotation / 180 * M_PI; 84 : : 85 : : // reset rotation to 0 to calculate world file parameters 86 : 0 : ms.setRotation( 0 ); 87 : : 88 : 0 : double xOrigin = ms.visibleExtent().xMinimum() + ( ms.mapUnitsPerPixel() / 2 ); 89 : 0 : double yOrigin = ms.visibleExtent().yMaximum() - ( ms.mapUnitsPerPixel() / 2 ); 90 : : 91 : 0 : double xCenter = ms.visibleExtent().center().x(); 92 : 0 : double yCenter = ms.visibleExtent().center().y(); 93 : : 94 : : // scaling matrix 95 : : double s[6]; 96 : 0 : s[0] = ms.mapUnitsPerPixel(); 97 : 0 : s[1] = 0; 98 : 0 : s[2] = xOrigin; 99 : 0 : s[3] = 0; 100 : 0 : s[4] = -ms.mapUnitsPerPixel(); 101 : 0 : s[5] = yOrigin; 102 : : 103 : : // rotation matrix 104 : : double r[6]; 105 : 0 : r[0] = std::cos( alpha ); 106 : 0 : r[1] = -std::sin( alpha ); 107 : 0 : r[2] = xCenter * ( 1 - std::cos( alpha ) ) + yCenter * std::sin( alpha ); 108 : 0 : r[3] = std::sin( alpha ); 109 : 0 : r[4] = std::cos( alpha ); 110 : 0 : r[5] = - xCenter * std::sin( alpha ) + yCenter * ( 1 - std::cos( alpha ) ); 111 : : 112 : : // result = rotation x scaling = rotation(scaling(X)) 113 : 0 : a = r[0] * s[0] + r[1] * s[3]; 114 : 0 : b = r[0] * s[1] + r[1] * s[4]; 115 : 0 : c = r[0] * s[2] + r[1] * s[5] + r[2]; 116 : 0 : d = r[3] * s[0] + r[4] * s[3]; 117 : : // Pixel YDim - almost always negative 118 : : // See https://en.wikipedia.org/wiki/World_file#cite_ref-3, https://github.com/qgis/QGIS/issues/26379 119 : 0 : e = r[3] * s[1] + r[4] * s[4]; 120 : 0 : f = r[3] * s[2] + r[4] * s[5] + r[5]; 121 : 0 : } 122 : : 123 : 0 : QString QgsMapSettingsUtils::worldFileContent( const QgsMapSettings &mapSettings ) 124 : : { 125 : : double a, b, c, d, e, f; 126 : 0 : worldFileParameters( mapSettings, a, b, c, d, e, f ); 127 : : 128 : 0 : QString content; 129 : : // Pixel XDim 130 : 0 : content += qgsDoubleToString( a ) + "\r\n"; 131 : : // Rotation on y axis 132 : 0 : content += qgsDoubleToString( d ) + "\r\n"; 133 : : // Rotation on x axis 134 : 0 : content += qgsDoubleToString( b ) + "\r\n"; 135 : : // Pixel YDim 136 : 0 : content += qgsDoubleToString( e ) + "\r\n"; 137 : : // Origin X (top left cell) 138 : 0 : content += qgsDoubleToString( c ) + "\r\n"; 139 : : // Origin Y (top left cell) 140 : 0 : content += qgsDoubleToString( f ) + "\r\n"; 141 : : 142 : 0 : return content; 143 : 0 : }