QGIS API Documentation 3.28.0-Firenze (ed3ad0430f)
qgsmaptooldigitizefeature.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgsmaptooldigitizefeature.cpp
3
4 ---------------------
5 begin : 7.12.2017
6 copyright : (C) 2017 by David Signer
8 ***************************************************************************
9 * *
10 * This program is free software; you can redistribute it and/or modify *
11 * it under the terms of the GNU General Public License as published by *
12 * the Free Software Foundation; either version 2 of the License, or *
13 * (at your option) any later version. *
14 * *
15 ***************************************************************************/
16
18
20#include "qgsapplication.h"
21#include "qgsattributedialog.h"
22#include "qgscurvepolygon.h"
23#include "qgsexception.h"
24#include "qgsfields.h"
25#include "qgsgeometry.h"
26#include "qgslinestring.h"
27#include "qgslogger.h"
28#include "qgsmapcanvas.h"
29#include "qgsmapmouseevent.h"
30#include "qgsmultipoint.h"
31#include "qgspolygon.h"
32#include "qgsproject.h"
35#include "qgsvectorlayer.h"
36
37#include <QSettings>
38
40 : QgsMapToolCaptureLayerGeometry( canvas, cadDockWidget, mode )
41 , mCheckGeometryType( true )
42{
43 mToolName = tr( "Digitize feature" );
46}
47
48QgsMapToolCapture::Capabilities QgsMapToolDigitizeFeature::capabilities() const
49{
51}
52
54{
55 switch ( technique )
56 {
58 return true;
63 }
64 return false;
65}
66
67void QgsMapToolDigitizeFeature::layerGeometryCaptured( const QgsGeometry &geometry )
68{
69 QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( mLayer );
70 if ( !vlayer )
71 vlayer = currentVectorLayer();
72
73 if ( !vlayer )
74 return;
75
76 QgsFeature f( vlayer->fields(), 0 );
77
78 if ( vlayer->isSpatial() )
79 {
80 const QgsWkbTypes::Type layerWKBType = vlayer->wkbType();
81
82 QgsGeometry layerGeometry;
83
84 if ( mCheckGeometryType )
85 {
88 QVector<QgsGeometry> layerGeometries = geometry.coerceToType( layerWKBType, defaultZ, defaultM );
89 if ( layerGeometries.count() > 0 )
90 layerGeometry = layerGeometries.at( 0 );
91
92 if ( layerGeometry.wkbType() != layerWKBType && layerGeometry.wkbType() != QgsWkbTypes::linearType( layerWKBType ) )
93 {
94 emit messageEmitted( tr( "The digitized geometry type (%1) does not correspond to the layer geometry type (%2)." ).arg( QgsWkbTypes::displayString( layerGeometry.wkbType() ), QgsWkbTypes::displayString( layerWKBType ) ), Qgis::MessageLevel::Warning );
95 return;
96 }
97 }
98 else
99 {
100 layerGeometry = geometry;
101 }
102 f.setGeometry( layerGeometry );
103 }
104 f.setValid( true );
105 emit digitizingCompleted( f );
106 featureDigitized( f );
107}
108
110{
111 QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( mLayer );
112 if ( !vlayer )
113 vlayer = currentVectorLayer();
114
115 if ( vlayer && vlayer->geometryType() == QgsWkbTypes::NullGeometry )
116 {
117 layerGeometryCaptured( QgsGeometry() );
118 return;
119 }
120
121 if ( mLayer )
122 {
123 //remember current layer
124 mCurrentLayer = mCanvas->currentLayer();
125 //set the layer with the given
126 mCanvas->setCurrentLayer( mLayer );
127 }
128
130}
131
133{
135
136 if ( mCurrentLayer )
137 //set the layer back to the one remembered
138 mCanvas->setCurrentLayer( mCurrentLayer );
139 emit digitizingFinished();
140}
141
143{
144 if ( e->key() == Qt::Key_Escape )
145 {
146 emit digitizingCanceled();
147 }
149}
150
152{
153 return mCheckGeometryType;
154}
155
157{
158 mCheckGeometryType = checkGeometryType;
159}
160
162{
163 QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( mLayer );
164
165 if ( !vlayer )
166 //if no given layer take the current from canvas
167 vlayer = currentVectorLayer();
168
169 if ( !vlayer )
170 {
172 return;
173 }
174
175 QgsVectorDataProvider *provider = vlayer->dataProvider();
176
177 if ( !( provider->capabilities() & QgsVectorDataProvider::AddFeatures ) )
178 {
179 emit messageEmitted( tr( "The data provider for this layer does not support the addition of features." ), Qgis::MessageLevel::Warning );
180 return;
181 }
182
183 if ( !vlayer->isEditable() )
184 {
186 return;
187 }
188
189 //check we only use this tool for point/multipoint layers
190 if ( mode() == CapturePoint && vlayer->geometryType() != QgsWkbTypes::PointGeometry && mCheckGeometryType )
191 {
192 emit messageEmitted( tr( "Wrong editing tool, cannot apply the 'capture point' tool on this vector layer" ), Qgis::MessageLevel::Warning );
193 return;
194 }
195
196 //check we only use the line tool for line/multiline layers
197 if ( mode() == CaptureLine && vlayer->geometryType() != QgsWkbTypes::LineGeometry && mCheckGeometryType )
198 {
199 emit messageEmitted( tr( "Wrong editing tool, cannot apply the 'capture line' tool on this vector layer" ), Qgis::MessageLevel::Warning );
200 return;
201 }
202
203 //check we only use the polygon tool for polygon/multipolygon layers
204 if ( mode() == CapturePolygon && vlayer->geometryType() != QgsWkbTypes::PolygonGeometry && mCheckGeometryType )
205 {
206 emit messageEmitted( tr( "Wrong editing tool, cannot apply the 'capture polygon' tool on this vector layer" ), Qgis::MessageLevel::Warning );
207 return;
208 }
209
211}
212
214{
215 mLayer = vl;
216}
217
CaptureTechnique
Capture technique.
Definition: qgis.h:153
@ Shape
Digitize shapes.
@ StraightSegments
Default capture mode - capture occurs with straight line segments.
@ CircularString
Capture in circular strings.
@ Streaming
Streaming points digitizing mode (points are automatically added as the mouse cursor moves).
The QgsAdvancedDigitizingDockWidget class is a dockable widget used to handle the CAD tools on top of...
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Definition: qgsfeature.h:56
A geometry is the spatial representation of a feature.
Definition: qgsgeometry.h:164
QVector< QgsGeometry > coerceToType(QgsWkbTypes::Type type, double defaultZ=0, double defaultM=0) const
Attempts to coerce this geometry into the specified destination type.
QgsWkbTypes::Type wkbType() const SIP_HOLDGIL
Returns type of the geometry as a WKB type (point / linestring / polygon etc.)
Map canvas is a class for displaying all GIS data types on a canvas.
Definition: qgsmapcanvas.h:90
Base class for all map layer types.
Definition: qgsmaplayer.h:73
A QgsMapMouseEvent is the result of a user interaction with the mouse on a QgsMapCanvas.
QgsMapToolCaptureLayerGeometry is a base class for map tools digitizing layer geometries This map too...
void deactivate() override
Unregisters this maptool from the cad dock widget.
void stopCapturing()
Stop capturing.
CaptureMode mode() const
The capture mode.
void keyPressEvent(QKeyEvent *e) override
Intercept key events like Esc or Del to delete the last point.
void activate() override
Registers this maptool with the cad dock widget.
CaptureMode
Different capture modes.
@ CapturePolygon
Capture polygons.
@ CapturePoint
Capture points.
@ CaptureLine
Capture lines.
@ ValidateGeometries
Tool supports geometry validation (since QGIS 3.22)
@ SupportsCurves
Supports curved geometries input.
void cadCanvasReleaseEvent(QgsMapMouseEvent *e) override
Override this method when subclassing this class.
void cadCanvasReleaseEvent(QgsMapMouseEvent *e) override
Override this method when subclassing this class.
void setCheckGeometryType(bool checkGeometryType)
Check if CaptureMode matches layer type.
void digitizingCanceled()
Emitted when the digitizing process was interrupted by the user.
void digitizingCompleted(const QgsFeature &feature)
Emitted whenever the digitizing has been successfully completed.
bool checkGeometryType() const
Check if CaptureMode matches layer type.
void digitizingFinished()
Emitted whenever the digitizing has been ended without digitizing any feature.
void keyPressEvent(QKeyEvent *e) override
Intercept key events like Esc or Del to delete the last point.
void activate() override
Registers this maptool with the cad dock widget.
void setLayer(QgsMapLayer *vl)
Change the layer edited by the map tool.
bool supportsTechnique(Qgis::CaptureTechnique technique) const override
Returns true if the tool supports the specified capture technique.
void deactivate() override
Unregisters this maptool from the cad dock widget.
QgsMapToolDigitizeFeature(QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget, CaptureMode mode=QgsMapToolCapture::CaptureNone)
QgsMapToolDigitizeFeature is a map tool to digitize a feature geometry.
QgsMapToolCapture::Capabilities capabilities() const override
Returns flags containing the supported capabilities.
void notifyNotVectorLayer()
Display a timed message bar noting the active layer is not vector.
void notifyNotEditableLayer()
Display a timed message bar noting the active vector layer is not editable.
QgsVectorLayer * currentVectorLayer()
Returns the current vector layer of the map canvas or 0.
QPointer< QgsMapCanvas > mCanvas
The pointer to the map canvas.
Definition: qgsmaptool.h:338
QString mToolName
The translated name of the map tool.
Definition: qgsmaptool.h:356
void messageEmitted(const QString &message, Qgis::MessageLevel=Qgis::MessageLevel::Info)
emit a message
static QgsProject * instance()
Returns the QgsProject singleton instance.
Definition: qgsproject.cpp:477
void cleared()
Emitted when the project is cleared (and additionally when an open project is cleared just before a n...
void readProject(const QDomDocument &)
Emitted when a project is being read.
T value(const QString &dynamicKeyPart=QString()) const
Returns settings value.
static const QgsSettingsEntryDouble settingsDigitizingDefaultZValue
Settings entry digitizing default z value.
static const QgsSettingsEntryDouble settingsDigitizingDefaultMValue
Settings entry digitizing default m value.
This is the base class for vector data providers.
@ AddFeatures
Allows adding features.
virtual Q_INVOKABLE QgsVectorDataProvider::Capabilities capabilities() const
Returns flags containing the supported capabilities.
Represents a vector layer which manages a vector based data sets.
Q_INVOKABLE QgsWkbTypes::Type wkbType() const FINAL
Returns the WKBType or WKBUnknown in case of error.
Q_INVOKABLE QgsWkbTypes::GeometryType geometryType() const
Returns point, line or polygon.
bool isSpatial() const FINAL
Returns true if this is a geometry layer and false in case of NoGeometry (table only) or UnknownGeome...
QgsFields fields() const FINAL
Returns the list of fields of this layer.
bool isEditable() const FINAL
Returns true if the provider is in editing mode.
QgsVectorDataProvider * dataProvider() FINAL
Returns the layer's data provider, it may be nullptr.
static Type linearType(Type type) SIP_HOLDGIL
Returns the linear type for a WKB type.
Definition: qgswkbtypes.h:622
Type
The WKB type describes the number of dimensions a geometry has.
Definition: qgswkbtypes.h:70
static QString displayString(Type type) SIP_HOLDGIL
Returns a non-translated display string type for a WKB type, e.g., the geometry name used in WKT geom...