diff --git a/src/gui/layout/qgslayoutelevationprofilewidget.cpp b/src/gui/layout/qgslayoutelevationprofilewidget.cpp index 0f187bbeb96..dfc6dde9f62 100644 --- a/src/gui/layout/qgslayoutelevationprofilewidget.cpp +++ b/src/gui/layout/qgslayoutelevationprofilewidget.cpp @@ -657,15 +657,16 @@ void QgsLayoutElevationProfileWidget::copySettingsFromProfileCanvas( QgsElevatio } QList canvasLayers = canvas->layers(); - // canvas layers are in opposite direction to what the layout item requires - std::reverse( canvasLayers.begin(), canvasLayers.end() ); mProfile->setLayers( canvasLayers ); const QList layers = mLayerTree->findLayers(); for ( QgsLayerTreeLayer *layer : layers ) { layer->setItemVisibilityChecked( mProfile->layers().contains( layer->layer() ) ); } - mLayerTree->reorderGroupLayers( mProfile->layers() ); + + // canvas layers are in opposite direction to what the layer tree requires + std::reverse( canvasLayers.begin(), canvasLayers.end() ); + mLayerTree->reorderGroupLayers( canvasLayers ); mProfile->invalidateCache(); mProfile->update(); @@ -755,12 +756,15 @@ void QgsLayoutElevationProfileWidget::setGuiElementValues() mSpinTopMargin->setValue( mProfile->plot()->margins().top() ); mSpinBottomMargin->setValue( mProfile->plot()->margins().bottom() ); + QList profileLayers = mProfile->layers(); const QList layers = mLayerTree->findLayers(); for ( QgsLayerTreeLayer *layer : layers ) { - layer->setItemVisibilityChecked( mProfile->layers().contains( layer->layer() ) ); + layer->setItemVisibilityChecked( profileLayers.contains( layer->layer() ) ); } - mLayerTree->reorderGroupLayers( mProfile->layers() ); + // elevation profile layers are in opposite direction to what the layer tree requires + std::reverse( profileLayers.begin(), profileLayers.end() ); + mLayerTree->reorderGroupLayers( profileLayers ); updateDataDefinedButton( mDDBtnTolerance ); updateDataDefinedButton( mDDBtnMinDistance ); @@ -795,6 +799,8 @@ void QgsLayoutElevationProfileWidget::updateItemLayers() layers << layer; } + std::reverse( layers.begin(), layers.end() ); + mProfile->setLayers( layers ); mProfile->update(); } diff --git a/src/gui/layout/qgslayoutelevationprofilewidget.h b/src/gui/layout/qgslayoutelevationprofilewidget.h index 20281992efd..e5151634012 100644 --- a/src/gui/layout/qgslayoutelevationprofilewidget.h +++ b/src/gui/layout/qgslayoutelevationprofilewidget.h @@ -80,6 +80,8 @@ class GUI_EXPORT QgsLayoutElevationProfileWidget : public QgsLayoutItemBaseWidge QgsLayerTreeRegistryBridge *mLayerTreeBridge = nullptr; QgsElevationProfileLayerTreeView *mLayerTreeView = nullptr; QMenu *mCopyFromDockMenu = nullptr; + + friend class TestQgsLayoutGui; }; #endif //QGSLAYOUTELEVATIONPROFILEWIDGET_H diff --git a/tests/src/gui/testqgslayoutgui.cpp b/tests/src/gui/testqgslayoutgui.cpp index fcc1e753691..27e8693d40e 100644 --- a/tests/src/gui/testqgslayoutgui.cpp +++ b/tests/src/gui/testqgslayoutgui.cpp @@ -22,6 +22,11 @@ #include "qgslayoutitemmap.h" #include "qgslayoutmodel.h" #include "qgslayoutitemcombobox.h" +#include "qgslayoutelevationprofilewidget.h" +#include "qgsvectorlayer.h" +#include "qgsvectorlayerelevationproperties.h" +#include "qgselevationprofilecanvas.h" +#include "qgslayertree.h" #include #include @@ -39,6 +44,7 @@ class TestQgsLayoutGui : public QObject void itemTypeComboBox(); void testProxyCrash(); + void testElevationProfileWidget(); private: }; @@ -235,6 +241,58 @@ void TestQgsLayoutGui::testProxyCrash() delete layout; } +void TestQgsLayoutGui::testElevationProfileWidget() +{ + QgsProject project; + QgsLayout layout( &project ); + QgsVectorLayer *vl1 = new QgsVectorLayer( QStringLiteral( "Point?field=intarray:int[]&field=strarray:string[]&field=intf:int" ), QStringLiteral( "vl1" ), QStringLiteral( "memory" ) ); + qobject_cast< QgsVectorLayerElevationProperties * >( vl1->elevationProperties() )->setZOffset( 5 ); + QgsVectorLayer *vl2 = new QgsVectorLayer( QStringLiteral( "Point?field=intarray:int[]&field=strarray:string[]&field=intf:int" ), QStringLiteral( "vl2" ), QStringLiteral( "memory" ) ); + qobject_cast< QgsVectorLayerElevationProperties * >( vl2->elevationProperties() )->setZOffset( 5 ); + QgsVectorLayer *vl3 = new QgsVectorLayer( QStringLiteral( "Point?field=intarray:int[]&field=strarray:string[]&field=intf:int" ), QStringLiteral( "vl3" ), QStringLiteral( "memory" ) ); + qobject_cast< QgsVectorLayerElevationProperties * >( vl3->elevationProperties() )->setZOffset( 5 ); + project.addMapLayers( { vl1, vl2, vl3 } ); + + QgsLayoutItemElevationProfile profile( &layout ); + // layers will be rendered from v1->vl3 from bottom to top + profile.setLayers( { vl1, vl2, vl3 } ); + QgsLayoutElevationProfileWidget widget( &profile ); + + QCOMPARE( widget.mLayerTree->children().size(), 3 ); + // in widget's layer tree the layers should be in order v1->vl3 from bottom to top + QCOMPARE( qobject_cast< QgsLayerTreeLayer * >( widget.mLayerTree->children().at( 0 ) )->layer()->name(), QStringLiteral( "vl3" ) ); + QVERIFY( widget.mLayerTree->children().at( 0 )->isItemVisibilityCheckedRecursive() ); + QCOMPARE( qobject_cast< QgsLayerTreeLayer * >( widget.mLayerTree->children().at( 1 ) )->layer()->name(), QStringLiteral( "vl2" ) ); + QVERIFY( widget.mLayerTree->children().at( 1 )->isItemVisibilityCheckedRecursive() ); + QCOMPARE( qobject_cast< QgsLayerTreeLayer * >( widget.mLayerTree->children().at( 2 ) )->layer()->name(), QStringLiteral( "vl1" ) ); + QVERIFY( widget.mLayerTree->children().at( 2 )->isItemVisibilityCheckedRecursive() ); + + // uncheck a layer + widget.mLayerTree->children().at( 1 )->setItemVisibilityChecked( false ); + QCOMPARE( profile.layers().size(), 2 ); + // layers should be in order of rendering, ie vl1 before vl3 as vl3 is rendered on top + QCOMPARE( profile.layers().at( 0 )->name(), QStringLiteral( "vl1" ) ); + QCOMPARE( profile.layers().at( 1 )->name(), QStringLiteral( "vl3" ) ); + + QgsElevationProfileCanvas canvas; + // layers will be rendered from v1->vl3 from bottom to top + canvas.setLayers( { vl1, vl2, vl3 } ); + + widget.copySettingsFromProfileCanvas( &canvas ); + QCOMPARE( profile.layers().size(), 3 ); + // layers should be in order of rendering, ie vl1 before vl3 as vl3 is rendered on top + QCOMPARE( profile.layers().at( 0 )->name(), QStringLiteral( "vl1" ) ); + QCOMPARE( profile.layers().at( 1 )->name(), QStringLiteral( "vl2" ) ); + QCOMPARE( profile.layers().at( 2 )->name(), QStringLiteral( "vl3" ) ); + + canvas.setLayers( { vl3, vl2, vl1 } ); + widget.copySettingsFromProfileCanvas( &canvas ); + QCOMPARE( profile.layers().size(), 3 ); + QCOMPARE( profile.layers().at( 0 )->name(), QStringLiteral( "vl3" ) ); + QCOMPARE( profile.layers().at( 1 )->name(), QStringLiteral( "vl2" ) ); + QCOMPARE( profile.layers().at( 2 )->name(), QStringLiteral( "vl1" ) ); +} + QTEST_MAIN( TestQgsLayoutGui ) #include "testqgslayoutgui.moc"