diff --git a/python/core/layertree/qgslayertreegroup.sip b/python/core/layertree/qgslayertreegroup.sip index 9279e1efbc2..a8411098285 100644 --- a/python/core/layertree/qgslayertreegroup.sip +++ b/python/core/layertree/qgslayertreegroup.sip @@ -41,6 +41,8 @@ class QgsLayerTreeGroup : QgsLayerTreeNode void removeLayer( QgsMapLayer* layer ); //! Remove child nodes from index "from". The nodes will be deleted. void removeChildren( int from, int count ); + //! Remove all child group nodes without layers. The groupnodes will be deleted. + void removeChildrenGroupWithoutLayers(); //! Remove all child nodes. The nodes will be deleted. void removeAllChildren(); diff --git a/src/core/composer/qgscomposerlabel.cpp b/src/core/composer/qgscomposerlabel.cpp index 3e4e26b2896..cdc1f959562 100644 --- a/src/core/composer/qgscomposerlabel.cpp +++ b/src/core/composer/qgscomposerlabel.cpp @@ -98,7 +98,6 @@ void QgsComposerLabel::paint( QPainter* painter, const QStyleOptionGraphicsItem* if ( mHtmlState ) { painter->scale( 1.0 / mHtmlUnitsToMM / 10.0, 1.0 / mHtmlUnitsToMM / 10.0 ); - QWebPage *webPage = new QWebPage(); webPage->setNetworkAccessManager( QgsNetworkAccessManager::instance() ); @@ -149,7 +148,6 @@ void QgsComposerLabel::paint( QPainter* painter, const QStyleOptionGraphicsItem* // Pause until html is loaded loop.exec(); } - webPage->mainFrame()->render( painter );//DELETE WEBPAGE ? } else diff --git a/src/core/layertree/qgslayertreegroup.cpp b/src/core/layertree/qgslayertreegroup.cpp index ab1ef976d4b..0da464b7939 100644 --- a/src/core/layertree/qgslayertreegroup.cpp +++ b/src/core/layertree/qgslayertreegroup.cpp @@ -119,6 +119,22 @@ void QgsLayerTreeGroup::removeChildren( int from, int count ) updateVisibilityFromChildren(); } +void QgsLayerTreeGroup::removeChildrenGroupWithoutLayers() +{ + // clean the layer tree by removing empty group + foreach ( QgsLayerTreeNode* treeNode, children() ) + { + if ( treeNode->nodeType() == QgsLayerTreeNode::NodeGroup ) + { + QgsLayerTreeGroup* treeGroup = qobject_cast( treeNode ); + if ( treeGroup->findLayerIds().count() == 0 ) + removeChildNode( treeNode ); + else + treeGroup->removeChildrenGroupWithoutLayers(); + } + } +} + void QgsLayerTreeGroup::removeAllChildren() { removeChildren( 0, mChildren.count() ); diff --git a/src/core/layertree/qgslayertreegroup.h b/src/core/layertree/qgslayertreegroup.h index 058145e1042..1b2e277e3b6 100644 --- a/src/core/layertree/qgslayertreegroup.h +++ b/src/core/layertree/qgslayertreegroup.h @@ -62,6 +62,8 @@ class CORE_EXPORT QgsLayerTreeGroup : public QgsLayerTreeNode void removeLayer( QgsMapLayer* layer ); //! Remove child nodes from index "from". The nodes will be deleted. void removeChildren( int from, int count ); + //! Remove all child group nodes without layers. The groupnodes will be deleted. + void removeChildrenGroupWithoutLayers(); //! Remove all child nodes. The nodes will be deleted. void removeAllChildren(); diff --git a/src/mapserver/qgssldconfigparser.cpp b/src/mapserver/qgssldconfigparser.cpp index 263ed55843f..e71b2b3fbc0 100644 --- a/src/mapserver/qgssldconfigparser.cpp +++ b/src/mapserver/qgssldconfigparser.cpp @@ -696,11 +696,11 @@ QgsComposition* QgsSLDConfigParser::createPrintComposition( const QString& compo return 0; } -QgsComposition* QgsSLDConfigParser::initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const +QgsComposition* QgsSLDConfigParser::initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLegend* >& legendList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const { if ( mFallbackParser ) { - return mFallbackParser->initComposition( composerTemplate, mapRenderer, mapList, labelList, htmlFrameList ); + return mFallbackParser->initComposition( composerTemplate, mapRenderer, mapList, legendList, labelList, htmlFrameList ); } return 0; } diff --git a/src/mapserver/qgssldconfigparser.h b/src/mapserver/qgssldconfigparser.h index 89b5c30185f..47a9b9762dc 100644 --- a/src/mapserver/qgssldconfigparser.h +++ b/src/mapserver/qgssldconfigparser.h @@ -107,7 +107,7 @@ class QgsSLDConfigParser : public QgsWMSConfigParser QgsComposition* createPrintComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, const QMap< QString, QString >& parameterMap ) const; /**Creates a composition from the project file (probably delegated to the fallback parser)*/ - QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const; + QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLegend* >& legendList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const; /**Adds print capabilities to xml document. ParentElem usually is the element*/ void printCapabilities( QDomElement& parentElement, QDomDocument& doc ) const; diff --git a/src/mapserver/qgswmsconfigparser.cpp b/src/mapserver/qgswmsconfigparser.cpp index cfaed150ac0..2266d567425 100644 --- a/src/mapserver/qgswmsconfigparser.cpp +++ b/src/mapserver/qgswmsconfigparser.cpp @@ -17,13 +17,18 @@ #include "qgswmsconfigparser.h" #include "qgsmaplayer.h" +#include "qgsmapserviceexception.h" #include "qgscomposerlabel.h" +#include "qgscomposerlegend.h" #include "qgscomposermap.h" #include "qgscomposerhtml.h" #include "qgscomposerframe.h" #include "qgscomposition.h" +#include "qgslayertreegroup.h" +#include "qgslayertreelayer.h" + QgsWMSConfigParser::QgsWMSConfigParser() { @@ -37,10 +42,11 @@ QgsWMSConfigParser::~QgsWMSConfigParser() QgsComposition* QgsWMSConfigParser::createPrintComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, const QMap< QString, QString >& parameterMap ) const { QList composerMaps; + QList composerLegends; QList composerLabels; QList composerHtmls; - QgsComposition* c = initComposition( composerTemplate, mapRenderer, composerMaps, composerLabels, composerHtmls ); + QgsComposition* c = initComposition( composerTemplate, mapRenderer, composerMaps, composerLegends, composerLabels, composerHtmls ); if ( !c ) { return 0; @@ -158,6 +164,66 @@ QgsComposition* QgsWMSConfigParser::createPrintComposition( const QString& compo currentMap->setGridIntervalX( parameterMap.value( mapId + ":GRID_INTERVAL_X" ).toDouble() ); currentMap->setGridIntervalY( parameterMap.value( mapId + ":GRID_INTERVAL_Y" ).toDouble() ); } + //update legend + // if it has an auto-update model + foreach ( QgsComposerLegend* currentLegend, composerLegends ) + { + if ( !currentLegend ) + { + continue; + } + + if ( currentLegend->autoUpdateModel() || currentLegend->legendFilterByMapEnabled() ) + { + // the legend has an auto-update model or + // has to be filter by map + // we will update it with map's layers + const QgsComposerMap* map = currentLegend->composerMap(); + if ( !map ) + { + continue; + } + + // get model and layer tree root of the legend + QgsLegendModelV2* model = currentLegend->modelV2(); + QgsLayerTreeGroup* root = model->rootGroup(); + + + // get layerIds find in the layer tree root + QStringList layerIds = root->findLayerIds(); + // get map layerIds + QStringList layerSet = map->layerSet(); + + // get map scale + double scale = map->scale(); + + // foreach layer find in the layer tree + // remove it if the layer id is not in map layerIds + foreach ( QString layerId, layerIds ) + { + QgsLayerTreeLayer* nodeLayer = root->findLayer( layerId ); + if ( !nodeLayer ) { + continue; + } + if ( !layerSet.contains( layerId ) ) + { + qobject_cast( nodeLayer->parent() )->removeChildNode( nodeLayer ); + } + else + { + QgsMapLayer* layer = nodeLayer->layer(); + if ( layer->hasScaleBasedVisibility() ) + { + if ( layer->minimumScale() > scale ) + qobject_cast( nodeLayer->parent() )->removeChildNode( nodeLayer ); + else if ( layer->maximumScale() < scale ) + qobject_cast( nodeLayer->parent() )->removeChildNode( nodeLayer ); + } + } + } + root->removeChildrenGroupWithoutLayers(); + } + } //replace label text foreach ( QgsComposerLabel *currentLabel, composerLabels ) diff --git a/src/mapserver/qgswmsconfigparser.h b/src/mapserver/qgswmsconfigparser.h index ed1bd47aba4..73053f95f15 100644 --- a/src/mapserver/qgswmsconfigparser.h +++ b/src/mapserver/qgswmsconfigparser.h @@ -22,6 +22,7 @@ class QgsComposerHtml; class QgsComposerLabel; +class QgsComposerLegend; class QgsComposerMap; class QgsComposition; class QgsMapLayer; @@ -107,7 +108,7 @@ class QgsWMSConfigParser QgsComposition* createPrintComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, const QMap< QString, QString >& parameterMap ) const; /**Creates a composition from the project file (probably delegated to the fallback parser)*/ - virtual QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const = 0; + virtual QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLegend* >& legendList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const = 0; /**Adds print capabilities to xml document. ParentElem usually is the element*/ virtual void printCapabilities( QDomElement& parentElement, QDomDocument& doc ) const = 0; diff --git a/src/mapserver/qgswmsprojectparser.cpp b/src/mapserver/qgswmsprojectparser.cpp index 16c583e0c60..27d0f5bf226 100644 --- a/src/mapserver/qgswmsprojectparser.cpp +++ b/src/mapserver/qgswmsprojectparser.cpp @@ -34,6 +34,7 @@ #include "qgscomposerpicture.h" #include "qgscomposerscalebar.h" #include "qgscomposershape.h" +#include "qgslayertreegroup.h" #include #include @@ -368,7 +369,7 @@ int QgsWMSProjectParser::WMSPrecision() const return WMSPrecision; } -QgsComposition* QgsWMSProjectParser::initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLabel* >& labelList, QList& htmlList ) const +QgsComposition* QgsWMSProjectParser::initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap* >& mapList, QList< QgsComposerLegend* >& legendList, QList< QgsComposerLabel* >& labelList, QList& htmlList ) const { //Create composition from xml QDomElement composerElem = composerByName( composerTemplate ); @@ -394,6 +395,7 @@ QgsComposition* QgsWMSProjectParser::initComposition( const QString& composerTem labelList.clear(); mapList.clear(); + legendList.clear(); htmlList.clear(); QList itemList; @@ -413,6 +415,23 @@ QgsComposition* QgsWMSProjectParser::initComposition( const QString& composerTem mapList.push_back( map ); continue; } + QgsComposerLegend* legend = dynamic_cast< QgsComposerLegend *>( *itemIt ); + if ( legend ) + { + /* + QgsLegendModelV2* model = legend->modelV2(); + QgsLayerTreeGroup* root = model->rootGroup(); + QStringList layerIds = root->findLayerIds(); + throw QgsMapServiceException( "Error", "Composer legend layerIds "+layerIds.join(" ,") ); + */ + if ( legend->autoUpdateModel() ) + { + QgsLegendModelV2* model = legend->modelV2(); + model->setRootGroup( projectLayerTreeGroup() ); + } + legendList.push_back( legend ); + continue; + } QgsComposerPicture* pic = dynamic_cast< QgsComposerPicture *>( *itemIt ); if ( pic ) { @@ -1913,6 +1932,27 @@ QDomElement QgsWMSProjectParser::composerByName( const QString& composerName ) c return composerElem; } +QgsLayerTreeGroup* QgsWMSProjectParser::projectLayerTreeGroup() const +{ + const QDomDocument* projectDoc = mProjectParser.xmlDocument(); + if ( !projectDoc ) + { + return 0; + } + + QDomElement qgisElem = projectDoc->documentElement(); + if ( qgisElem.isNull() ) + { + return 0; + } + QDomElement layerTreeElem = qgisElem.firstChildElement( "layer-tree-group" ); + if ( layerTreeElem.isNull() ) + { + return 0; + } + return QgsLayerTreeGroup::readXML( layerTreeElem ); +} + bool QgsWMSProjectParser::annotationPosition( const QDomElement& elem, double scaleFactor, double& xPos, double& yPos ) { Q_UNUSED( scaleFactor ); diff --git a/src/mapserver/qgswmsprojectparser.h b/src/mapserver/qgswmsprojectparser.h index 8fec7db975a..85b1d060944 100644 --- a/src/mapserver/qgswmsprojectparser.h +++ b/src/mapserver/qgswmsprojectparser.h @@ -20,6 +20,7 @@ #include "qgswmsconfigparser.h" #include "qgsserverprojectparser.h" +#include "qgslayertreegroup.h" class QTextDocument; class QSvgRenderer; @@ -59,7 +60,7 @@ class QgsWMSProjectParser : public QgsWMSConfigParser int WMSPrecision() const; //printing - QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap*>& mapList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const; + QgsComposition* initComposition( const QString& composerTemplate, QgsMapRenderer* mapRenderer, QList< QgsComposerMap* >& mapList, QList< QgsComposerLegend* >& legendList, QList< QgsComposerLabel* >& labelList, QList& htmlFrameList ) const; void printCapabilities( QDomElement& parentElement, QDomDocument& doc ) const; @@ -147,6 +148,7 @@ class QgsWMSProjectParser : public QgsWMSConfigParser void addLayersFromGroup( const QDomElement& legendGroupElem, QMap< int, QgsMapLayer*>& layers, bool useCache = true ) const; QDomElement composerByName( const QString& composerName ) const; + QgsLayerTreeGroup* projectLayerTreeGroup() const; static bool annotationPosition( const QDomElement& elem, double scaleFactor, double& xPos, double& yPos ); static void drawAnnotationRectangle( QPainter* p, const QDomElement& elem, double scaleFactor, double xPos, double yPos, int itemWidth, int itemHeight );