QGIS API Documentation  3.26.3-Buenos Aires (65e4edfdad)
qgspointcloudextentrenderer.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgspointcloudextentrenderer.h
3  --------------------
4  begin : December 2020
5  copyright : (C) 2020 by Nyall Dawson
6  email : nyall dot dawson at gmail dot com
7  ***************************************************************************/
8 
9 /***************************************************************************
10  * *
11  * This program is free software; you can redistribute it and/or modify *
12  * it under the terms of the GNU General Public License as published by *
13  * the Free Software Foundation; either version 2 of the License, or *
14  * (at your option) any later version. *
15  * *
16  ***************************************************************************/
17 
19 #include "qgspointcloudblock.h"
20 #include "qgssymbollayerutils.h"
21 #include "qgssymbol.h"
22 #include "qgswkbtypes.h"
23 #include "qgspolygon.h"
24 #include "qgscurve.h"
25 #include "qgslinesymbollayer.h"
27 #include "qgsfillsymbol.h"
28 
30  : mFillSymbol( symbol ? symbol : defaultFillSymbol() )
31 {
32 
33 }
34 
36 
38 {
39  return QStringLiteral( "extent" );
40 }
41 
43 {
44  std::unique_ptr< QgsPointCloudExtentRenderer > res = std::make_unique< QgsPointCloudExtentRenderer >( mFillSymbol ? mFillSymbol->clone() : nullptr );
45  copyCommonProperties( res.get() );
46  return res.release();
47 }
48 
50 {
51 
52 }
53 
55 {
56  std::unique_ptr< QgsPointCloudExtentRenderer > r = std::make_unique< QgsPointCloudExtentRenderer >();
57 
58  const QDomElement symbolElem = element.firstChildElement( QStringLiteral( "symbol" ) );
59  if ( !symbolElem.isNull() )
60  {
61  r->mFillSymbol.reset( QgsSymbolLayerUtils::loadSymbol<QgsFillSymbol>( symbolElem, context ) );
62  }
63 
64  r->restoreCommonProperties( element, context );
65  return r.release();
66 }
67 
69 {
70  auto transformRing = [&context]( QPolygonF & pts )
71  {
72  //transform the QPolygonF to screen coordinates
73  if ( context.renderContext().coordinateTransform().isValid() )
74  {
75  try
76  {
78  }
79  catch ( QgsCsException & )
80  {
81  // we don't abort the rendering here, instead we remove any invalid points and just plot those which ARE valid
82  }
83  }
84 
85  // remove non-finite points, e.g. infinite or NaN points caused by reprojecting errors
86  pts.erase( std::remove_if( pts.begin(), pts.end(),
87  []( const QPointF point )
88  {
89  return !std::isfinite( point.x() ) || !std::isfinite( point.y() );
90  } ), pts.end() );
91 
92  QPointF *ptr = pts.data();
93  for ( int i = 0; i < pts.size(); ++i, ++ptr )
94  {
95  context.renderContext().mapToPixel().transformInPlace( ptr->rx(), ptr->ry() );
96  }
97  };
98 
99  for ( auto it = extent.const_parts_begin(); it != extent.const_parts_end(); ++it )
100  {
101  if ( const QgsPolygon *polygon = qgsgeometry_cast< const QgsPolygon * >( *it ) )
102  {
103  QPolygonF exterior = polygon->exteriorRing()->asQPolygonF();
104  transformRing( exterior );
105  QVector<QPolygonF> rings;
106  rings.reserve( polygon->numInteriorRings() );
107  for ( int i = 0; i < polygon->numInteriorRings(); ++i )
108  {
109  QPolygonF ring = polygon->interiorRing( i )->asQPolygonF();
110  transformRing( ring );
111  rings.append( ring );
112  }
113 
114  mFillSymbol->renderPolygon( exterior, rings.empty() ? nullptr : &rings, nullptr, context.renderContext() );
115  }
116  }
117 }
118 
120 {
121  std::unique_ptr< QgsSimpleLineSymbolLayer > layer = std::make_unique< QgsSimpleLineSymbolLayer >();
122  layer->setColor( QColor( 228, 26, 28 ) );
123  layer->setWidth( 0.960000 );
124  layer->setPenStyle( Qt::DotLine );
125  layer->setWidthUnit( QgsUnitTypes::RenderMillimeters );
126  return new QgsFillSymbol( QgsSymbolLayerList() << layer.release() );
127 }
128 
130 {
131  return mFillSymbol.get();
132 }
133 
135 {
136  mFillSymbol.reset( symbol );
137 }
138 
139 QDomElement QgsPointCloudExtentRenderer::save( QDomDocument &doc, const QgsReadWriteContext &context ) const
140 {
141  QDomElement rendererElem = doc.createElement( QStringLiteral( "renderer" ) );
142 
143  rendererElem.setAttribute( QStringLiteral( "type" ), type() );
144 
145  const QDomElement symbolElem = QgsSymbolLayerUtils::saveSymbol( QString(), mFillSymbol.get(), doc, context );
146  rendererElem.appendChild( symbolElem );
147 
148  saveCommonProperties( rendererElem, context );
149  return rendererElem;
150 }
151 
153 {
155  mFillSymbol->startRender( context.renderContext() );
156 }
157 
159 {
161  mFillSymbol->stopRender( context.renderContext() );
162 }
163 
164 QList<QgsLayerTreeModelLegendNode *> QgsPointCloudExtentRenderer::createLegendNodes( QgsLayerTreeLayer *nodeLayer )
165 {
166  QList<QgsLayerTreeModelLegendNode *> nodes;
167 
168  const QgsLegendSymbolItem extentItem( mFillSymbol.get(), QStringLiteral( "extent" ), QStringLiteral( "extent" ) );
169  QgsSymbolLegendNode *node = new QgsSymbolLegendNode( nodeLayer, extentItem );
170  node->setEmbeddedInParent( true );
171  nodes << node;
172 
173  return nodes;
174 }
qgspolygon.h
QgsPointCloudExtentRenderer::clone
QgsPointCloudRenderer * clone() const override
Create a deep copy of this renderer.
Definition: qgspointcloudextentrenderer.cpp:42
QgsPointCloudExtentRenderer::~QgsPointCloudExtentRenderer
~QgsPointCloudExtentRenderer() override
QgsRenderContext::mapToPixel
const QgsMapToPixel & mapToPixel() const
Returns the context's map to pixel transform, which transforms between map coordinates and device coo...
Definition: qgsrendercontext.h:258
QgsPointCloudExtentRenderer::QgsPointCloudExtentRenderer
QgsPointCloudExtentRenderer(QgsFillSymbol *symbol=nullptr)
Constructor for QgsPointCloudExtentRenderer.
Definition: qgspointcloudextentrenderer.cpp:29
qgslayertreemodellegendnode.h
QgsPointCloudExtentRenderer::type
QString type() const override
Returns the identifier of the renderer type.
Definition: qgspointcloudextentrenderer.cpp:37
QgsPolygon
Polygon geometry type.
Definition: qgspolygon.h:33
QgsReadWriteContext
The class is used as a container of context for various read/write operations on other objects.
Definition: qgsreadwritecontext.h:34
QgsGeometry::const_parts_end
QgsAbstractGeometry::const_part_iterator const_parts_end() const
Returns STL-style iterator pointing to the imaginary part after the last part of the geometry.
Definition: qgsgeometry.cpp:2026
QgsPointCloudExtentRenderer::save
QDomElement save(QDomDocument &doc, const QgsReadWriteContext &context) const override
Saves the renderer configuration to an XML element.
Definition: qgspointcloudextentrenderer.cpp:139
qgssymbollayerutils.h
QgsPointCloudExtentRenderer::renderExtent
void renderExtent(const QgsGeometry &extent, QgsPointCloudRenderContext &context)
Renders a polygon extent geometry to the specified render context.
Definition: qgspointcloudextentrenderer.cpp:68
QgsUnitTypes::RenderMillimeters
@ RenderMillimeters
Millimeters.
Definition: qgsunittypes.h:169
QgsGeometry::const_parts_begin
QgsAbstractGeometry::const_part_iterator const_parts_begin() const
Returns STL-style const iterator pointing to the first part of the geometry.
Definition: qgsgeometry.cpp:2019
QgsPointCloudRenderer::copyCommonProperties
void copyCommonProperties(QgsPointCloudRenderer *destination) const
Copies common point cloud properties (such as point size and screen error) to the destination rendere...
Definition: qgspointcloudrenderer.cpp:162
QgsPointCloudBlock
Base class for storing raw data from point cloud nodes.
Definition: qgspointcloudblock.h:38
QgsPointCloudExtentRenderer::stopRender
void stopRender(QgsPointCloudRenderContext &context) override
Must be called when a render cycle has finished, to allow the renderer to clean up.
Definition: qgspointcloudextentrenderer.cpp:158
QgsCoordinateTransform::isValid
bool isValid() const
Returns true if the coordinate transform is valid, ie both the source and destination CRS have been s...
Definition: qgscoordinatetransform.cpp:900
QgsPointCloudRenderer::startRender
virtual void startRender(QgsPointCloudRenderContext &context)
Must be called when a new render cycle is started.
Definition: qgspointcloudrenderer.cpp:88
QgsRenderContext::coordinateTransform
QgsCoordinateTransform coordinateTransform() const
Returns the current coordinate transform for the context.
Definition: qgsrendercontext.h:178
QgsLegendSymbolItem
The class stores information about one class/rule of a vector layer renderer in a unified way that ca...
Definition: qgslegendsymbolitem.h:36
QgsCsException
Custom exception class for Coordinate Reference System related exceptions.
Definition: qgsexception.h:65
QgsPointCloudExtentRenderer::createLegendNodes
QList< QgsLayerTreeModelLegendNode * > createLegendNodes(QgsLayerTreeLayer *nodeLayer) override
Creates a set of legend nodes representing the renderer.
Definition: qgspointcloudextentrenderer.cpp:164
QgsPointCloudRenderContext
Encapsulates the render context for a 2D point cloud rendering operation.
Definition: qgspointcloudrenderer.h:41
QgsLayerTreeLayer
Layer tree node points to a map layer.
Definition: qgslayertreelayer.h:43
QgsPointCloudExtentRenderer::startRender
void startRender(QgsPointCloudRenderContext &context) override
Must be called when a new render cycle is started.
Definition: qgspointcloudextentrenderer.cpp:152
qgspointcloudextentrenderer.h
QgsPointCloudRenderer::stopRender
virtual void stopRender(QgsPointCloudRenderContext &context)
Must be called when a render cycle has finished, to allow the renderer to clean up.
Definition: qgspointcloudrenderer.cpp:115
QgsPointCloudExtentRenderer::setFillSymbol
void setFillSymbol(QgsFillSymbol *symbol)
Sets the symbol used to render the cloud's extent.
Definition: qgspointcloudextentrenderer.cpp:134
QgsPointCloudExtentRenderer::renderBlock
void renderBlock(const QgsPointCloudBlock *block, QgsPointCloudRenderContext &context) override
Renders a block of point cloud data using the specified render context.
Definition: qgspointcloudextentrenderer.cpp:49
QgsPointCloudExtentRenderer::create
static QgsPointCloudRenderer * create(QDomElement &element, const QgsReadWriteContext &context)
Creates an extent renderer from an XML element.
Definition: qgspointcloudextentrenderer.cpp:54
QgsPointCloudExtentRenderer::defaultFillSymbol
static QgsFillSymbol * defaultFillSymbol()
Returns a new instance of the default fill symbol to use for showing point cloud extents.
Definition: qgspointcloudextentrenderer.cpp:119
QgsMapToPixel::transformInPlace
void transformInPlace(double &x, double &y) const
Transforms device coordinates to map coordinates.
Definition: qgsmaptopixel.h:128
QgsPointCloudExtentRenderer::fillSymbol
QgsFillSymbol * fillSymbol() const
Returns the symbol used to render the cloud's extent.
Definition: qgspointcloudextentrenderer.cpp:129
qgslinesymbollayer.h
qgscurve.h
QgsGeometry
A geometry is the spatial representation of a feature.
Definition: qgsgeometry.h:124
QgsSymbolLayerList
QList< QgsSymbolLayer * > QgsSymbolLayerList
Definition: qgssymbol.h:27
QgsFillSymbol
A fill symbol type, for rendering Polygon and MultiPolygon geometries.
Definition: qgsfillsymbol.h:29
QgsSymbolLegendNode::setEmbeddedInParent
void setEmbeddedInParent(bool embedded) override
Definition: qgslayertreemodellegendnode.cpp:815
QgsPointCloudRenderer
Abstract base class for 2d point cloud renderers.
Definition: qgspointcloudrenderer.h:296
qgspointcloudblock.h
QgsCoordinateTransform::transformPolygon
void transformPolygon(QPolygonF &polygon, Qgis::TransformDirection direction=Qgis::TransformDirection::Forward) const SIP_THROW(QgsCsException)
Transforms a polygon to the destination coordinate system.
Definition: qgscoordinatetransform.cpp:421
QgsPointCloudRenderer::saveCommonProperties
void saveCommonProperties(QDomElement &element, const QgsReadWriteContext &context) const
Saves common renderer properties (such as point size and screen error) to the specified DOM element.
Definition: qgspointcloudrenderer.cpp:185
QgsPointCloudRenderContext::renderContext
QgsRenderContext & renderContext()
Returns a reference to the context's render context.
Definition: qgspointcloudrenderer.h:69
QgsSymbolLegendNode
Implementation of legend node interface for displaying preview of vector symbols and their labels and...
Definition: qgslayertreemodellegendnode.h:358
qgswkbtypes.h
qgsfillsymbol.h
qgssymbol.h
QgsSymbolLayerUtils::saveSymbol
static QDomElement saveSymbol(const QString &symbolName, const QgsSymbol *symbol, QDomDocument &doc, const QgsReadWriteContext &context)
Writes a symbol definition to XML.
Definition: qgssymbollayerutils.cpp:1397