Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Fixes #45872 : resolveReference after we load/create embedded group
  • Loading branch information
troopa81 authored and github-actions[bot] committed Jan 4, 2022
1 parent 45aa0b7 commit c6a5baf
Show file tree
Hide file tree
Showing 7 changed files with 910 additions and 36 deletions.
73 changes: 41 additions & 32 deletions src/app/qgisapp.cpp
Expand Up @@ -13588,52 +13588,61 @@ void QgisApp::addMapLayer( QgsMapLayer *mapLayer )
}
}


void QgisApp::embedLayers()
{
//dialog to select groups/layers from other project files
QgsProjectLayerGroupDialog d( this );
if ( d.exec() == QDialog::Accepted && d.isValid() )
{
QgsCanvasRefreshBlocker refreshBlocker;
addEmbeddedItems( d.selectedProjectFile(), d.selectedGroups(), d.selectedLayerIds() );
}
}

QString projectFile = d.selectedProjectFile();
void QgisApp::addEmbeddedItems( const QString &projectFile, const QStringList &groups, const QStringList &layerIds )
{
QgsCanvasRefreshBlocker refreshBlocker;

//groups
QStringList groups = d.selectedGroups();
QStringList::const_iterator groupIt = groups.constBegin();
for ( ; groupIt != groups.constEnd(); ++groupIt )
{
QgsLayerTreeGroup *newGroup = QgsProject::instance()->createEmbeddedGroup( *groupIt, projectFile, QStringList() );
//groups
QStringList::const_iterator groupIt = groups.constBegin();
for ( ; groupIt != groups.constEnd(); ++groupIt )
{
QgsLayerTreeGroup *newGroup = QgsProject::instance()->createEmbeddedGroup( *groupIt, projectFile, QStringList() );

if ( newGroup )
QgsProject::instance()->layerTreeRoot()->addChildNode( newGroup );
}
if ( newGroup )
QgsProject::instance()->layerTreeRoot()->addChildNode( newGroup );
}

//layer ids
QList<QDomNode> brokenNodes;
//layer ids
QList<QDomNode> brokenNodes;

// resolve dependencies
QgsLayerDefinition::DependencySorter depSorter( projectFile );
QStringList sortedIds = depSorter.sortedLayerIds();
QStringList layerIds = d.selectedLayerIds();
const auto constSortedIds = sortedIds;
for ( const QString &id : constSortedIds )
// resolve dependencies
QgsLayerDefinition::DependencySorter depSorter( projectFile );
QStringList sortedIds = depSorter.sortedLayerIds();
const auto constSortedIds = sortedIds;
for ( const QString &id : constSortedIds )
{
const auto constLayerIds = layerIds;
for ( const QString &selId : constLayerIds )
{
const auto constLayerIds = layerIds;
for ( const QString &selId : constLayerIds )
{
if ( selId == id )
QgsProject::instance()->createEmbeddedLayer( selId, projectFile, brokenNodes );
}
if ( selId == id )
QgsProject::instance()->createEmbeddedLayer( selId, projectFile, brokenNodes );
}
}

// fix broken relations and dependencies
for ( const QString &id : constSortedIds )
{
QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( QgsProject::instance()->mapLayer( id ) );
if ( vlayer )
vectorLayerStyleLoaded( vlayer, QgsMapLayer::AllStyleCategories );
}
// fix broken relations and dependencies
for ( const QString &id : constSortedIds )
{
QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( QgsProject::instance()->mapLayer( id ) );
if ( vlayer )
vectorLayerStyleLoaded( vlayer, QgsMapLayer::AllStyleCategories );
}

// Resolve references to other layers
QMap<QString, QgsMapLayer *> layers = QgsProject::instance()->mapLayers();
for ( QMap<QString, QgsMapLayer *>::iterator it = layers.begin(); it != layers.end(); ++it )
{
it.value()->resolveReferences( QgsProject::instance() );
}
}

Expand Down
10 changes: 10 additions & 0 deletions src/app/qgisapp.h
Expand Up @@ -1558,8 +1558,17 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
void showMeshCalculator();
//! Open dialog to align raster layers
void showAlignRasterTool();

/**
* Called whenever user wants to embed layers
*/
void embedLayers();

/**
* Embed \a groups and \a layerIds items from \a projectFile
*/
void addEmbeddedItems( const QString &projectFile, const QStringList &groups, const QStringList &layerIds );

//! Creates a new map canvas view
void newMapCanvas();
//! Creates a new 3D map canvas view
Expand Down Expand Up @@ -2733,6 +2742,7 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
friend class QgsCanvasRefreshBlocker;

friend class TestQgisAppPython;
friend class TestQgisApp;
friend class QgisAppInterface;
friend class QgsAppScreenShots;
};
Expand Down
8 changes: 4 additions & 4 deletions src/core/project/qgsproject.cpp
Expand Up @@ -1632,6 +1632,10 @@ bool QgsProject::readProjectFile( const QString &filename, QgsProject::ReadFlags
mMainAnnotationLayer->readLayerXml( doc->documentElement().firstChildElement( QStringLiteral( "main-annotation-layer" ) ), context );
mMainAnnotationLayer->setTransformContext( mTransformContext );

// load embedded groups and layers
profile.switchTask( tr( "Loading embedded layers" ) );
loadEmbeddedNodes( mRootGroup, flags );

// Resolve references to other layers
// Needs to be done here once all dependent layers are loaded
profile.switchTask( tr( "Resolving layer references" ) );
Expand All @@ -1643,10 +1647,6 @@ bool QgsProject::readProjectFile( const QString &filename, QgsProject::ReadFlags

mLayerTreeRegistryBridge->setEnabled( true );

// load embedded groups and layers
profile.switchTask( tr( "Loading embedded layers" ) );
loadEmbeddedNodes( mRootGroup, flags );

// now that layers are loaded, we can resolve layer tree's references to the layers
profile.switchTask( tr( "Resolving references" ) );
mRootGroup->resolveReferences( this );
Expand Down
18 changes: 18 additions & 0 deletions tests/src/app/testqgisapp.cpp
Expand Up @@ -42,6 +42,7 @@ class TestQgisApp : public QObject
void addVectorLayerGeopackageSingleLayer();
void addVectorLayerGeopackageSingleLayerAlreadyLayername();
void addVectorLayerInvalid();
void addEmbeddedGroup();

private:
QgisApp *mQgisApp = nullptr;
Expand Down Expand Up @@ -137,5 +138,22 @@ void TestQgisApp::addVectorLayerInvalid()
QVERIFY( !layer );
}

void TestQgisApp::addEmbeddedGroup()
{
const QString projectPath = QString( TEST_DATA_DIR ) + QStringLiteral( "/embedded_groups/joins1.qgs" );

QCOMPARE( QgsProject::instance()->layers<QgsVectorLayer *>().count(), 0 );

mQgisApp->addEmbeddedItems( projectPath, QStringList() << QStringLiteral( "GROUP" ), QStringList() );

QgsVectorLayer *vl = QgsProject::instance()->mapLayer<QgsVectorLayer *>( QStringLiteral( "polys_with_id_32002f94_eebe_40a5_a182_44198ba1bc5a" ) );
QCOMPARE( vl->fields().count(), 5 );

// cleanup
QgsProject::instance()->clear();
}



QGSTEST_MAIN( TestQgisApp )
#include "testqgisapp.moc"
14 changes: 14 additions & 0 deletions tests/src/core/testqgsproject.cpp
Expand Up @@ -59,6 +59,7 @@ class TestQgsProject : public QObject
void testAttachmentsQgs();
void testAttachmentsQgz();
void testAttachmentIdentifier();
void testEmbeddedGroupWithJoins();
};

void TestQgsProject::init()
Expand Down Expand Up @@ -906,5 +907,18 @@ void TestQgsProject::testAttachmentIdentifier()
}


void TestQgsProject::testEmbeddedGroupWithJoins()
{
const QString projectPath = QString( TEST_DATA_DIR ) + QStringLiteral( "/embedded_groups/joins2.qgz" );
QgsProject p;
p.read( projectPath );

QCOMPARE( p.layers<QgsVectorLayer *>().count(), 2 );

QgsVectorLayer *vl = p.mapLayer<QgsVectorLayer *>( QStringLiteral( "polys_with_id_32002f94_eebe_40a5_a182_44198ba1bc5a" ) );
QCOMPARE( vl->fields().count(), 5 );
}


QGSTEST_MAIN( TestQgsProject )
#include "testqgsproject.moc"

0 comments on commit c6a5baf

Please sign in to comment.