diff --git a/src/providers/wms/qgswmsprovider.cpp b/src/providers/wms/qgswmsprovider.cpp index 38eda23412dc..af8e12d2d6ad 100644 --- a/src/providers/wms/qgswmsprovider.cpp +++ b/src/providers/wms/qgswmsprovider.cpp @@ -5236,6 +5236,8 @@ QVariantMap QgsWmsProviderMetadata::decodeUri( const QString &uri ) const if ( url.isLocalFile() ) { decoded[ QStringLiteral( "path" ) ] = url.toLocalFile(); + // Also add the url to insure WMS source widget works properly with XYZ file:// URLs + decoded[ item.first ] = item.second; } else if ( QFileInfo( item.second ).isFile() ) { @@ -5278,6 +5280,13 @@ QString QgsWmsProviderMetadata::encodeUri( const QVariantMap &parts ) const { items.push_back( { QStringLiteral( "url" ), QUrl::fromLocalFile( it.value().toString() ).toString() } ); } + else if ( it.key() == QLatin1String( "url" ) ) + { + if ( !parts.contains( QLatin1String( "path" ) ) ) + { + items.push_back( { it.key(), it.value().toString() } ); + } + } else { if ( it.value().type() == QVariant::StringList ) @@ -5376,6 +5385,20 @@ QList QgsWmsProviderMetadata::querySublayers( const } } } + else + { + const thread_local QRegularExpression re( QStringLiteral( "{-?[xyzq]}" ) ); + if ( fileName.contains( re ) ) + { + // local XYZ directory + QgsProviderSublayerDetails details; + details.setUri( uri ); + details.setProviderKey( key() ); + details.setType( Qgis::LayerType::Raster ); + return {details}; + } + } + return {}; } diff --git a/tests/src/providers/testqgswmsprovider.cpp b/tests/src/providers/testqgswmsprovider.cpp index 6592c32f0eca..eaf73d97b45e 100644 --- a/tests/src/providers/testqgswmsprovider.cpp +++ b/tests/src/providers/testqgswmsprovider.cpp @@ -376,11 +376,26 @@ class TestQgsWmsProvider: public QgsTest QString uriString = QStringLiteral( "url=file:///my/local/tiles.mbtiles&type=mbtiles" ); QVariantMap parts = QgsProviderRegistry::instance()->decodeUri( QStringLiteral( "wms" ), uriString ); QVariantMap expectedParts { { QString( "type" ), QVariant( "mbtiles" ) }, - { QString( "path" ), QVariant( "/my/local/tiles.mbtiles" ) } }; + { QString( "path" ), QVariant( "/my/local/tiles.mbtiles" ) }, + { QString( "url" ), QVariant( "file:///my/local/tiles.mbtiles" ) } }; QCOMPARE( parts, expectedParts ); QString encodedUri = QgsProviderRegistry::instance()->encodeUri( QStringLiteral( "wms" ), parts ); QCOMPARE( encodedUri, uriString ); + + QgsProviderMetadata *wmsMetadata = QgsProviderRegistry::instance()->providerMetadata( "wms" ); + QVERIFY( wmsMetadata ); + + // query sublayers + QList< QgsProviderSublayerDetails > sublayers; + sublayers = wmsMetadata->querySublayers( QStringLiteral( "type=xyz&url=file:///my/xyz/directory/%7Bz%7D/%7Bx%7D/%7By%7D.png&zmax=19&zmin=0" ) ); + QCOMPARE( sublayers.size(), 1 ); + QCOMPARE( sublayers.at( 0 ).providerKey(), QStringLiteral( "wms" ) ); + QCOMPARE( sublayers.at( 0 ).name(), QLatin1String( "" ) ); + QCOMPARE( sublayers.at( 0 ).uri(), QStringLiteral( "type=xyz&url=file:///my/xyz/directory/%7Bz%7D/%7Bx%7D/%7By%7D.png&zmax=19&zmin=0" ) ); + QCOMPARE( sublayers.at( 0 ).type(), Qgis::LayerType::Raster ); + QVERIFY( !sublayers.at( 0 ).skippedContainerScan() ); + QVERIFY( !QgsProviderUtils::sublayerDetailsAreIncomplete( sublayers ) ); } void absoluteRelativeUri()