Branch data Line data Source code
1 : : /*************************************************************************** 2 : : qgsvectortilelayer.h 3 : : -------------------------------------- 4 : : Date : March 2020 5 : : Copyright : (C) 2020 by Martin Dobias 6 : : Email : wonder dot sk at gmail dot com 7 : : *************************************************************************** 8 : : * * 9 : : * This program is free software; you can redistribute it and/or modify * 10 : : * it under the terms of the GNU General Public License as published by * 11 : : * the Free Software Foundation; either version 2 of the License, or * 12 : : * (at your option) any later version. * 13 : : * * 14 : : ***************************************************************************/ 15 : : 16 : : #ifndef QGSVECTORTILELAYER_H 17 : : #define QGSVECTORTILELAYER_H 18 : : 19 : : #include "qgis_core.h" 20 : : #include "qgis_sip.h" 21 : : 22 : : #include "qgsmaplayer.h" 23 : : 24 : : class QgsVectorTileLabeling; 25 : : class QgsVectorTileRenderer; 26 : : 27 : : class QgsTileXYZ; 28 : : 29 : : /** 30 : : * \ingroup core 31 : : * \brief Implements a map layer that is dedicated to rendering of vector tiles. 32 : : * Vector tiles compared to "ordinary" vector layers are pre-processed data 33 : : * optimized for fast rendering. A dataset is provided with a series of zoom levels 34 : : * for different map scales. Each zoom level has a matrix of tiles that contain 35 : : * actual data. A single vector tile may be a a file stored on a local drive, 36 : : * requested over HTTP request or retrieved from a database. 37 : : * 38 : : * Content of a vector tile is divided into one or more named sub-layers. Each such 39 : : * sub-layer may contain many features which consist of geometry and attributes. 40 : : * Contrary to traditional vector layers, these sub-layers do not need to have a rigid 41 : : * schema where geometry type and attributes are the same for all features. A single 42 : : * sub-layer may have multiple geometry types in a single tile or have some attributes 43 : : * defined only at particular zoom levels. 44 : : * 45 : : * Vector tile layer currently does not use the concept of data providers that other 46 : : * layer types use. The process of rendering of vector tiles looks like this: 47 : : * 48 : : * +--------+ +------+ +---------+ 49 : : * | DATA | | RAW | | DECODED | 50 : : * | | --> LOADER --> | | --> DECODER --> | | --> RENDERER 51 : : * | SOURCE | | TILE | | TILE | 52 : : * +--------+ +------+ +---------+ 53 : : * 54 : : * Data source is a place from where tiles are fetched from (URL for HTTP access, local 55 : : * files, MBTiles file, GeoPackage file or others. Loader (QgsVectorTileLoader) class 56 : : * takes care of loading data from the data source. The "raw tile" data is just a blob 57 : : * (QByteArray) that is encoded in some way. There are multiple ways how vector tiles 58 : : * are encoded just like there are different formats how to store images. For example, 59 : : * tiles can be encoded using Mapbox Vector Tiles (MVT) format or in GeoJSON. Decoder 60 : : * (QgsVectorTileDecoder) takes care of decoding raw tile data into QgsFeature objects. 61 : : * A decoded tile is essentially an array of vector features for each sub-layer found 62 : : * in the tile - this is what vector tile renderer (QgsVectorTileRenderer) expects 63 : : * and does the map rendering. 64 : : * 65 : : * To construct a vector tile layer, it is best to use QgsDataSourceUri class and set 66 : : * the following parameters to get a valid encoded URI: 67 : : * 68 : : * - "type" - what kind of data source will be used 69 : : * - "url" - URL or path of the data source (specific to each data source type, see below) 70 : : * 71 : : * Currently supported data source types: 72 : : * 73 : : * - "xyz" - the "url" should be a template like http://example.com/{z}/{x}/{y}.pbf where 74 : : * {x},{y},{z} will be replaced by tile coordinates 75 : : * - "mbtiles" - tiles read from a MBTiles file (a SQLite database) 76 : : * 77 : : * Currently supported decoders: 78 : : * 79 : : * - MVT - following Mapbox Vector Tiles specification 80 : : * 81 : : * \since QGIS 3.14 82 : : */ 83 : : class CORE_EXPORT QgsVectorTileLayer : public QgsMapLayer 84 : : { 85 : 0 : Q_OBJECT 86 : : 87 : : public: 88 : : //! Constructs a new vector tile layer 89 : : explicit QgsVectorTileLayer( const QString &path = QString(), const QString &baseName = QString() ); 90 : : ~QgsVectorTileLayer() override; 91 : : 92 : : #ifdef SIP_RUN 93 : : SIP_PYOBJECT __repr__(); 94 : : % MethodCode 95 : : QString str = QStringLiteral( "<QgsVectorTileLayer: '%1'>" ).arg( sipCpp->name() ); 96 : : sipRes = PyUnicode_FromString( str.toUtf8().constData() ); 97 : : % End 98 : : #endif 99 : : 100 : : // implementation of virtual functions from QgsMapLayer 101 : : 102 : : QgsVectorTileLayer *clone() const override SIP_FACTORY; 103 : : 104 : : QgsMapLayerRenderer *createMapRenderer( QgsRenderContext &rendererContext ) override SIP_FACTORY; 105 : : 106 : : bool readXml( const QDomNode &layerNode, QgsReadWriteContext &context ) override; 107 : : 108 : : bool writeXml( QDomNode &layerNode, QDomDocument &doc, const QgsReadWriteContext &context ) const override; 109 : : 110 : : bool readSymbology( const QDomNode &node, QString &errorMessage, 111 : : QgsReadWriteContext &context, StyleCategories categories = AllStyleCategories ) override; 112 : : 113 : : bool writeSymbology( QDomNode &node, QDomDocument &doc, QString &errorMessage, const QgsReadWriteContext &context, 114 : : StyleCategories categories = AllStyleCategories ) const override; 115 : : 116 : : void setTransformContext( const QgsCoordinateTransformContext &transformContext ) override; 117 : : QString loadDefaultStyle( bool &resultFlag SIP_OUT ) override; 118 : : 119 : : /** 120 : : * Loads the default style for the layer, and returns TRUE if the style was 121 : : * successfully loaded. 122 : : * 123 : : * The \a error string will be filled with a translated error message if an error 124 : : * occurs during the style load. The \a warnings list will be populated with any 125 : : * warning messages generated during the style load (e.g. default style properties 126 : : * which could not be converted). 127 : : * 128 : : * \since QGIS 3.16 129 : : */ 130 : : bool loadDefaultStyle( QString &error, QStringList &warnings ) SIP_SKIP; 131 : : 132 : : QString loadDefaultMetadata( bool &resultFlag SIP_OUT ) override; 133 : : 134 : : QString encodedSource( const QString &source, const QgsReadWriteContext &context ) const FINAL; 135 : : QString decodedSource( const QString &source, const QString &provider, const QgsReadWriteContext &context ) const FINAL; 136 : : QString htmlMetadata() const override; 137 : : 138 : : // new methods 139 : : 140 : : //! Returns type of the data source 141 : 0 : QString sourceType() const { return mSourceType; } 142 : : //! Returns URL/path of the data source (syntax different to each data source type) 143 : 0 : QString sourcePath() const { return mSourcePath; } 144 : : 145 : : //! Returns minimum zoom level at which source has any valid tiles (negative = unconstrained) 146 : 0 : int sourceMinZoom() const { return mSourceMinZoom; } 147 : : //! Returns maximum zoom level at which source has any valid tiles (negative = unconstrained) 148 : 0 : int sourceMaxZoom() const { return mSourceMaxZoom; } 149 : : 150 : : /** 151 : : * Fetches raw tile data for the give tile coordinates. If failed to fetch tile data, 152 : : * it will return an empty byte array. 153 : : * 154 : : * \note This call may issue a network request (depending on the source type) and will block 155 : : * the caller until the request is finished. 156 : : */ 157 : : QByteArray getRawTile( QgsTileXYZ tileID ) SIP_SKIP; 158 : : 159 : : /** 160 : : * Sets renderer for the map layer. 161 : : * \note Takes ownership of the passed renderer 162 : : */ 163 : : void setRenderer( QgsVectorTileRenderer *r SIP_TRANSFER ); 164 : : //! Returns currently assigned renderer 165 : : QgsVectorTileRenderer *renderer() const; 166 : : 167 : : /** 168 : : * Sets labeling for the map layer. 169 : : * \note Takes ownership of the passed labeling 170 : : */ 171 : : void setLabeling( QgsVectorTileLabeling *labeling SIP_TRANSFER ); 172 : : //! Returns currently assigned labeling 173 : : QgsVectorTileLabeling *labeling() const; 174 : : 175 : : //! Sets whether to render also borders of tiles (useful for debugging) 176 : : void setTileBorderRenderingEnabled( bool enabled ) { mTileBorderRendering = enabled; } 177 : : //! Returns whether to render also borders of tiles (useful for debugging) 178 : 0 : bool isTileBorderRenderingEnabled() const { return mTileBorderRendering; } 179 : : 180 : : private: 181 : : bool loadDataSource(); 182 : : 183 : : private: 184 : : //! Type of the data source 185 : : QString mSourceType; 186 : : //! URL/Path of the data source 187 : : QString mSourcePath; 188 : : //! Minimum zoom level at which source has any valid tiles (negative = unconstrained) 189 : : int mSourceMinZoom = -1; 190 : : //! Maximum zoom level at which source has any valid tiles (negative = unconstrained) 191 : : int mSourceMaxZoom = -1; 192 : : 193 : : //! Renderer assigned to the layer to draw map 194 : : std::unique_ptr<QgsVectorTileRenderer> mRenderer; 195 : : //! Labeling assigned to the layer to produce labels 196 : : std::unique_ptr<QgsVectorTileLabeling> mLabeling; 197 : : //! Whether we draw borders of tiles 198 : : bool mTileBorderRendering = false; 199 : : 200 : : QVariantMap mArcgisLayerConfiguration; 201 : : 202 : : bool setupArcgisVectorTileServiceConnection( const QString &uri, const QgsDataSourceUri &dataSourceUri ); 203 : : }; 204 : : 205 : : 206 : : #endif // QGSVECTORTILELAYER_H