QGIS API Documentation  3.20.0-Odense (decaadbb31)
qgsalgorithmsinglesidedbuffer.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsalgorithmsinglesidedbuffer.cpp
3  ---------------------
4  begin : November 2019
5  copyright : (C) 2019 by Alexander Bruy
6  email : alexander dot bruy 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 "qgsprocessing.h"
20 
22 
23 QString QgsSingleSidedBufferAlgorithm::name() const
24 {
25  return QStringLiteral( "singlesidedbuffer" );
26 }
27 
28 QString QgsSingleSidedBufferAlgorithm::displayName() const
29 {
30  return QObject::tr( "Single sided buffer" );
31 }
32 
33 QStringList QgsSingleSidedBufferAlgorithm::tags() const
34 {
35  return QObject::tr( "rectangle,perpendicular,right,angles,square,quadrilateralise" ).split( ',' );
36 }
37 
38 QString QgsSingleSidedBufferAlgorithm::group() const
39 {
40  return QObject::tr( "Vector geometry" );
41 }
42 
43 QString QgsSingleSidedBufferAlgorithm::groupId() const
44 {
45  return QStringLiteral( "vectorgeometry" );
46 }
47 
48 QString QgsSingleSidedBufferAlgorithm::shortHelpString() const
49 {
50  return QObject::tr( "This algorithm buffers lines by a specified distance on one "
51  "side of the line only.\n\nThe segments parameter controls "
52  "the number of line segments to use to approximate a quarter "
53  "circle when creating rounded buffers. The join style parameter "
54  "specifies whether round, miter or beveled joins should be used "
55  "when buffering corners in a line. The miter limit parameter is "
56  "only applicable for miter join styles, and controls the maximum "
57  "distance from the buffer to use when creating a mitered join." );
58 }
59 
60 QString QgsSingleSidedBufferAlgorithm::outputName() const
61 {
62  return QObject::tr( "Buffered" );
63 }
64 
65 QList<int> QgsSingleSidedBufferAlgorithm::inputLayerTypes() const
66 {
67  return QList<int>() << QgsProcessing::TypeVectorLine;
68 }
69 
70 QgsProcessing::SourceType QgsSingleSidedBufferAlgorithm::outputLayerType() const
71 {
73 }
74 
75 QgsWkbTypes::Type QgsSingleSidedBufferAlgorithm::outputWkbType( QgsWkbTypes::Type type ) const
76 {
77  Q_UNUSED( type );
78  return QgsWkbTypes::Polygon;
79 }
80 
81 QgsSingleSidedBufferAlgorithm *QgsSingleSidedBufferAlgorithm::createInstance() const
82 {
83  return new QgsSingleSidedBufferAlgorithm();
84 }
85 
86 void QgsSingleSidedBufferAlgorithm::initParameters( const QVariantMap & )
87 {
88  auto bufferParam = std::make_unique < QgsProcessingParameterDistance >( QStringLiteral( "DISTANCE" ), QObject::tr( "Distance" ), 10, QStringLiteral( "INPUT" ) );
89  bufferParam->setIsDynamic( true );
90  bufferParam->setDynamicPropertyDefinition( QgsPropertyDefinition( QStringLiteral( "Distance" ), QObject::tr( "Buffer distance" ), QgsPropertyDefinition::Double ) );
91  bufferParam->setDynamicLayerParameterName( QStringLiteral( "INPUT" ) );
92  addParameter( bufferParam.release() );
93 
94  addParameter( new QgsProcessingParameterEnum( QStringLiteral( "SIDE" ), QObject::tr( "Side" ), QStringList() << QObject::tr( "Left" ) << QObject::tr( "Right" ), false, 0 ) );
95  addParameter( new QgsProcessingParameterNumber( QStringLiteral( "SEGMENTS" ), QObject::tr( "Segments" ), QgsProcessingParameterNumber::Integer, 8, false, 1 ) );
96  addParameter( new QgsProcessingParameterEnum( QStringLiteral( "JOIN_STYLE" ), QObject::tr( "Join style" ), QStringList() << QObject::tr( "Round" ) << QObject::tr( "Miter" ) << QObject::tr( "Bevel" ), false, 0 ) );
97  addParameter( new QgsProcessingParameterNumber( QStringLiteral( "MITER_LIMIT" ), QObject::tr( "Miter limit" ), QgsProcessingParameterNumber::Double, 2, false, 1 ) );
98 }
99 
100 bool QgsSingleSidedBufferAlgorithm::prepareAlgorithm( const QVariantMap &parameters, QgsProcessingContext &context, QgsProcessingFeedback * )
101 {
102  mDistance = parameterAsDouble( parameters, QStringLiteral( "DISTANCE" ), context );
103  mDynamicDistance = QgsProcessingParameters::isDynamic( parameters, QStringLiteral( "DISTANCE" ) );
104  if ( mDynamicDistance )
105  mDistanceProperty = parameters.value( QStringLiteral( "DISTANCE" ) ).value< QgsProperty >();
106 
107  mSide = static_cast< QgsGeometry::BufferSide>( parameterAsInt( parameters, QStringLiteral( "SIDE" ), context ) );
108  mSegments = parameterAsInt( parameters, QStringLiteral( "SEGMENTS" ), context );
109  mJoinStyle = static_cast< QgsGeometry::JoinStyle>( 1 + parameterAsInt( parameters, QStringLiteral( "JOIN_STYLE" ), context ) );
110  mMiterLimit = parameterAsDouble( parameters, QStringLiteral( "MITER_LIMIT" ), context );
111 
112  return true;
113 }
114 
115 QgsFeatureList QgsSingleSidedBufferAlgorithm::processFeature( const QgsFeature &feature, QgsProcessingContext &context, QgsProcessingFeedback * )
116 {
117  QgsFeature f = feature;
118 
119  if ( f.hasGeometry() )
120  {
121  double distance = mDistance;
122  if ( mDynamicDistance )
123  distance = mDistanceProperty.valueAsDouble( context.expressionContext(), distance );
124 
125  QgsGeometry outputGeometry = f.geometry().singleSidedBuffer( distance, mSegments, mSide, mJoinStyle, mMiterLimit );
126  if ( outputGeometry.isNull() )
127  throw QgsProcessingException( QObject::tr( "Error calculating single sided buffer" ) );
128 
129  f.setGeometry( outputGeometry );
130  }
131 
132  return QgsFeatureList() << f;
133 }
134 
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Definition: qgsfeature.h:56
QgsGeometry geometry
Definition: qgsfeature.h:67
bool hasGeometry() const
Returns true if the feature has an associated geometry.
Definition: qgsfeature.cpp:205
void setGeometry(const QgsGeometry &geometry)
Set the feature's geometry.
Definition: qgsfeature.cpp:145
A geometry is the spatial representation of a feature.
Definition: qgsgeometry.h:124
JoinStyle
Join styles for buffers.
Definition: qgsgeometry.h:1244
BufferSide
Side of line to buffer.
Definition: qgsgeometry.h:1227
Q_GADGET bool isNull
Definition: qgsgeometry.h:126
QgsGeometry singleSidedBuffer(double distance, int segments, BufferSide side, JoinStyle joinStyle=JoinStyleRound, double miterLimit=2.0) const
Returns a single sided buffer for a (multi)line geometry.
Contains information about the context in which a processing algorithm is executed.
QgsExpressionContext & expressionContext()
Returns the expression context.
Custom exception class for processing related exceptions.
Definition: qgsexception.h:83
Base class for providing feedback from a processing algorithm.
An enum based parameter for processing algorithms, allowing for selection from predefined values.
A numeric parameter for processing algorithms.
static bool isDynamic(const QVariantMap &parameters, const QString &name)
Returns true if the parameter with matching name is a dynamic parameter, and must be evaluated once f...
SourceType
Data source types enum.
Definition: qgsprocessing.h:46
@ TypeVectorLine
Vector line layers.
Definition: qgsprocessing.h:50
@ TypeVectorPolygon
Vector polygon layers.
Definition: qgsprocessing.h:51
Definition for a property.
Definition: qgsproperty.h:48
@ Double
Double value (including negative values)
Definition: qgsproperty.h:58
A store for object properties.
Definition: qgsproperty.h:232
Type
The WKB type describes the number of dimensions a geometry has.
Definition: qgswkbtypes.h:70
QList< QgsFeature > QgsFeatureList
Definition: qgsfeature.h:736