QGIS API Documentation  3.16.0-Hannover (43b64b13f3)
qgsvectorlayerchunkloader_p.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsvectorlayerchunkloader_p.cpp
3  --------------------------------------
4  Date : July 2019
5  Copyright : (C) 2019 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 
17 
18 #include "qgs3dutils.h"
20 #include "qgschunknode_p.h"
21 #include "qgspolygon3dsymbol_p.h"
22 #include "qgseventtracing.h"
23 #include "qgslogger.h"
24 #include "qgsvectorlayer.h"
26 
27 #include "qgsline3dsymbol.h"
28 #include "qgspoint3dsymbol.h"
29 #include "qgspolygon3dsymbol.h"
30 
31 #include "qgsapplication.h"
32 #include "qgs3dsymbolregistry.h"
33 
34 #include <QtConcurrent>
35 
37 
38 
39 QgsVectorLayerChunkLoader::QgsVectorLayerChunkLoader( const QgsVectorLayerChunkLoaderFactory *factory, QgsChunkNode *node )
40  : QgsChunkLoader( node )
41  , mFactory( factory )
42  , mContext( factory->mMap )
43  , mSource( new QgsVectorLayerFeatureSource( factory->mLayer ) )
44 {
45  if ( node->level() < mFactory->mLeafLevel )
46  {
47  QTimer::singleShot( 0, this, &QgsVectorLayerChunkLoader::finished );
48  return;
49  }
50 
51  QgsVectorLayer *layer = mFactory->mLayer;
52  const Qgs3DMapSettings &map = mFactory->mMap;
53 
54  QgsFeature3DHandler *handler = QgsApplication::symbol3DRegistry()->createHandlerForSymbol( layer, mFactory->mSymbol.get() );
55  if ( !handler )
56  {
57  QgsDebugMsg( QStringLiteral( "Unknown 3D symbol type for vector layer: " ) + mFactory->mSymbol->type() );
58  return;
59  }
60  mHandler.reset( handler );
61 
63  exprContext.setFields( layer->fields() );
64  mContext.setExpressionContext( exprContext );
65 
66  QSet<QString> attributeNames;
67  if ( !mHandler->prepare( mContext, attributeNames ) )
68  {
69  QgsDebugMsg( QStringLiteral( "Failed to prepare 3D feature handler!" ) );
70  return;
71  }
72 
73  // build the feature request
75  req.setDestinationCrs( map.crs(), map.transformContext() );
76  req.setSubsetOfAttributes( attributeNames, layer->fields() );
77 
78  // only a subset of data to be queried
79  QgsRectangle rect = Qgs3DUtils::worldToMapExtent( node->bbox(), map.origin() );
80  req.setFilterRect( rect );
81 
82  //
83  // this will be run in a background thread
84  //
85 
86  QFuture<void> future = QtConcurrent::run( [req, this]
87  {
88  QgsEventTracing::ScopedEvent e( QStringLiteral( "3D" ), QStringLiteral( "VL chunk load" ) );
89 
90  QgsFeature f;
91  QgsFeatureIterator fi = mSource->getFeatures( req );
92  while ( fi.nextFeature( f ) )
93  {
94  if ( mCanceled )
95  break;
96  mContext.expressionContext().setFeature( f );
97  mHandler->processFeature( f, mContext );
98  }
99  } );
100 
101  // emit finished() as soon as the handler is populated with features
102  mFutureWatcher = new QFutureWatcher<void>( this );
103  mFutureWatcher->setFuture( future );
104  connect( mFutureWatcher, &QFutureWatcher<void>::finished, this, &QgsChunkQueueJob::finished );
105 }
106 
107 QgsVectorLayerChunkLoader::~QgsVectorLayerChunkLoader()
108 {
109  if ( mFutureWatcher && !mFutureWatcher->isFinished() )
110  {
111  disconnect( mFutureWatcher, &QFutureWatcher<void>::finished, this, &QgsChunkQueueJob::finished );
112  mFutureWatcher->waitForFinished();
113  }
114 }
115 
116 void QgsVectorLayerChunkLoader::cancel()
117 {
118  mCanceled = true;
119 }
120 
121 Qt3DCore::QEntity *QgsVectorLayerChunkLoader::createEntity( Qt3DCore::QEntity *parent )
122 {
123  if ( mNode->level() < mFactory->mLeafLevel )
124  {
125  return new Qt3DCore::QEntity( parent ); // dummy entity
126  }
127 
128  Qt3DCore::QEntity *entity = new Qt3DCore::QEntity( parent );
129  mHandler->finalize( entity, mContext );
130  return entity;
131 }
132 
133 
135 
136 
137 QgsVectorLayerChunkLoaderFactory::QgsVectorLayerChunkLoaderFactory( const Qgs3DMapSettings &map, QgsVectorLayer *vl, QgsAbstract3DSymbol *symbol, int leafLevel )
138  : mMap( map )
139  , mLayer( vl )
140  , mSymbol( symbol->clone() )
141  , mLeafLevel( leafLevel )
142 {
143 }
144 
145 QgsChunkLoader *QgsVectorLayerChunkLoaderFactory::createChunkLoader( QgsChunkNode *node ) const
146 {
147  return new QgsVectorLayerChunkLoader( this, node );
148 }
149 
150 
152 
153 
154 QgsVectorLayerChunkedEntity::QgsVectorLayerChunkedEntity( QgsVectorLayer *vl, double zMin, double zMax, const QgsVectorLayer3DTilingSettings &tilingSettings, QgsAbstract3DSymbol *symbol, const Qgs3DMapSettings &map )
155  : QgsChunkedEntity( Qgs3DUtils::layerToWorldExtent( vl->extent(), zMin, zMax, vl->crs(), map.origin(), map.crs(), map.transformContext() ),
156  -1, // rootError (negative error means that the node does not contain anything)
157  -1, // max. allowed screen error (negative tau means that we need to go until leaves are reached)
158  tilingSettings.zoomLevelsCount() - 1,
159  new QgsVectorLayerChunkLoaderFactory( map, vl, symbol, tilingSettings.zoomLevelsCount() - 1 ), true )
160 {
161  setShowBoundingBoxes( tilingSettings.showBoundingBoxes() );
162 }
163 
164 QgsVectorLayerChunkedEntity::~QgsVectorLayerChunkedEntity()
165 {
166  // cancel / wait for jobs
167  cancelActiveJobs();
168 }
169 
QgsExpressionContext
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...
Definition: qgsexpressioncontext.h:370
Qgs3DMapSettings::crs
QgsCoordinateReferenceSystem crs() const
Returns coordinate reference system used in the 3D scene.
Definition: qgs3dmapsettings.h:96
qgsline3dsymbol.h
crs
const QgsCoordinateReferenceSystem & crs
Definition: qgswfsgetfeature.cpp:51
QgsVectorLayer3DTilingSettings::showBoundingBoxes
bool showBoundingBoxes() const
Returns whether to display bounding boxes of entity's tiles (for debugging)
Definition: qgsabstractvectorlayer3drenderer.h:58
QgsApplication::symbol3DRegistry
static Qgs3DSymbolRegistry * symbol3DRegistry()
Returns registry of available 3D symbols.
Definition: qgsapplication.cpp:2288
qgschunknode_p.h
qgsvectorlayerchunkloader_p.h
Qgs3DUtils::worldToMapExtent
static QgsRectangle worldToMapExtent(const QgsAABB &bbox, const QgsVector3D &mapOrigin)
Converts axis aligned bounding box in 3D world coordinates to extent in map coordinates.
Definition: qgs3dutils.cpp:488
QgsFeatureRequest::setSubsetOfAttributes
QgsFeatureRequest & setSubsetOfAttributes(const QgsAttributeList &attrs)
Set a subset of attributes that will be fetched.
Definition: qgsfeaturerequest.cpp:185
QgsDebugMsg
#define QgsDebugMsg(str)
Definition: qgslogger.h:38
Qgs3DMapSettings::transformContext
QgsCoordinateTransformContext transformContext() const
Returns the coordinate transform context, which stores various information regarding which datum tran...
Definition: qgs3dmapsettings.cpp:392
qgs3dsymbolregistry.h
QgsRectangle
A rectangle specified with double values.
Definition: qgsrectangle.h:42
qgsapplication.h
QgsFeatureRequest::setFilterRect
QgsFeatureRequest & setFilterRect(const QgsRectangle &rectangle)
Sets the rectangle from which features will be taken.
Definition: qgsfeaturerequest.cpp:92
Qgs3DUtils::globalProjectLayerExpressionContext
static QgsExpressionContext globalProjectLayerExpressionContext(QgsVectorLayer *layer)
Returns expression context for use in preparation of 3D data of a layer.
Definition: qgs3dutils.cpp:551
qgseventtracing.h
QgsVectorLayer::fields
QgsFields fields() const FINAL
Returns the list of fields of this layer.
Definition: qgsvectorlayer.cpp:3283
QgsFeatureRequest
This class wraps a request for features to a vector layer (or directly its vector data provider).
Definition: qgsfeaturerequest.h:76
QgsAbstract3DSymbol
3 Abstract base class for 3D symbols that are used by VectorLayer3DRenderer objects.
Definition: qgsabstract3dsymbol.h:46
QgsAbstractVectorLayer3DRenderer::tilingSettings
QgsVectorLayer3DTilingSettings tilingSettings() const
Returns tiling settings of the renderer.
Definition: qgsabstractvectorlayer3drenderer.h:90
qgs3dutils.h
QgsAbstractVectorLayer3DRenderer::layer
QgsVectorLayer * layer() const
Returns vector layer associated with the renderer.
Definition: qgsabstractvectorlayer3drenderer.cpp:53
qgsabstractvectorlayer3drenderer.h
Qgs3DMapSettings
3 Definition of the world
Definition: qgs3dmapsettings.h:54
qgsvectorlayerfeatureiterator.h
Qgs3DMapSettings::origin
QgsVector3D origin() const
Returns coordinates in map CRS at which 3D scene has origin (0,0,0)
Definition: qgs3dmapsettings.h:86
qgsvectorlayer.h
qgspolygon3dsymbol_p.h
qgspolygon3dsymbol.h
QgsFeatureIterator::nextFeature
bool nextFeature(QgsFeature &f)
Definition: qgsfeatureiterator.h:374
QgsVectorLayer
Represents a vector layer which manages a vector based data sets.
Definition: qgsvectorlayer.h:387
qgspoint3dsymbol.h
QgsVectorLayerFeatureSource
Partial snapshot of vector layer's state (only the members necessary for access to features)
Definition: qgsvectorlayerfeatureiterator.h:52
Qgs3DUtils
3 Miscellaneous utility functions used from 3D code.
Definition: qgs3dutils.h:50
QgsFeature
The feature class encapsulates a single feature including its id, geometry and a list of field/values...
Definition: qgsfeature.h:56
QgsFeatureRequest::setDestinationCrs
QgsFeatureRequest & setDestinationCrs(const QgsCoordinateReferenceSystem &crs, const QgsCoordinateTransformContext &context)
Sets the destination crs for feature's geometries.
Definition: qgsfeaturerequest.cpp:258
qgslogger.h
Qgs3DSymbolRegistry::createHandlerForSymbol
QgsFeature3DHandler * createHandlerForSymbol(QgsVectorLayer *layer, const QgsAbstract3DSymbol *symbol)
Creates a feature handler for a symbol, for the specified vector layer.
Definition: qgs3dsymbolregistry.cpp:60
QgsFeatureIterator
Wrapper for iterator of features from vector data provider or vector layer.
Definition: qgsfeatureiterator.h:265
QgsVectorLayer3DTilingSettings
3 This class defines configuration of how a vector layer gets tiled for 3D rendering.
Definition: qgsabstractvectorlayer3drenderer.h:38