25
25
#include " qgisapp.h"
26
26
27
27
QgsMapToolOffsetCurve::QgsMapToolOffsetCurve ( QgsMapCanvas* canvas ): QgsMapToolEdit( canvas ), mRubberBand( 0 ),
28
- mOriginalGeometry( 0 ), mGeometryModified( false ), mDistanceItem( 0 ), mDistanceSpinBox( 0 ), mSnapVertexMarker( 0 ), mForceCopy( false )
28
+ mOriginalGeometry( 0 ), mGeometryModified( false ), mDistanceItem( 0 ), mDistanceSpinBox( 0 ), mSnapVertexMarker( 0 ), mForceCopy( false ), mMultiPartGeometry( false )
29
29
{
30
30
}
31
31
@@ -90,6 +90,11 @@ void QgsMapToolOffsetCurve::canvasReleaseEvent( QMouseEvent * e )
90
90
return ;
91
91
}
92
92
93
+ if ( mMultiPartGeometry )
94
+ {
95
+ mModifiedGeometry .convertToMultiType ();
96
+ }
97
+
93
98
vlayer->beginEditCommand ( tr ( " Offset curve" ) );
94
99
95
100
bool editOk;
@@ -218,27 +223,30 @@ QgsGeometry* QgsMapToolOffsetCurve::createOriginGeometry( QgsVectorLayer* vl, co
218
223
{
219
224
return 0 ;
220
225
}
226
+ mMultiPartGeometry = false ;
227
+ // assign feature part by vertex number (snap to vertex) or by before vertex number (snap to segment)
228
+ int partVertexNr = ( sr.snappedVertexNr == -1 ? sr.beforeVertexNr : sr.snappedVertexNr );
221
229
222
230
if ( vl == currentVectorLayer () && !mForceCopy )
223
231
{
224
232
// don't consider selected geometries, only the snap result
225
- return snappedFeature.geometryAndOwnership ();
233
+ return convertToSingleLine ( snappedFeature.geometryAndOwnership (), partVertexNr, mMultiPartGeometry );
226
234
}
227
235
else // snapped to a background layer
228
236
{
229
237
// if source layer is polygon / multipolygon, create a linestring from the snapped ring
230
238
if ( vl->geometryType () == QGis::Polygon )
231
239
{
232
240
// make linestring from polygon ring and return this geometry
233
- return linestringFromPolygon ( snappedFeature.geometry (), sr. snappedVertexNr );
241
+ return linestringFromPolygon ( snappedFeature.geometry (), partVertexNr );
234
242
}
235
243
236
244
237
245
// for background layers, try to merge selected entries together if snapped feature is contained in selection
238
246
const QgsFeatureIds& selection = vl->selectedFeaturesIds ();
239
247
if ( selection.size () < 1 || !selection.contains ( sr.snappedAtGeometry ) )
240
248
{
241
- return snappedFeature.geometryAndOwnership ();
249
+ return convertToSingleLine ( snappedFeature.geometryAndOwnership (), partVertexNr, mMultiPartGeometry );
242
250
}
243
251
else
244
252
{
@@ -256,7 +264,7 @@ QgsGeometry* QgsMapToolOffsetCurve::createOriginGeometry( QgsVectorLayer* vl, co
256
264
if ( geom->isMultipart () )
257
265
{
258
266
delete geom;
259
- return snappedFeature.geometryAndOwnership ();
267
+ return convertToSingleLine ( snappedFeature.geometryAndOwnership (), sr. snappedVertexNr , mMultiPartGeometry );
260
268
}
261
269
262
270
return geom;
@@ -416,3 +424,43 @@ void QgsMapToolOffsetCurve::configureSnapper( QgsSnapper& s )
416
424
s.setSnapLayers ( snapLayers );
417
425
s.setSnapMode ( QgsSnapper::SnapWithOneResult );
418
426
}
427
+
428
+ QgsGeometry* QgsMapToolOffsetCurve::convertToSingleLine ( QgsGeometry* geom, int vertex, bool & isMulti )
429
+ {
430
+ if ( !geom )
431
+ {
432
+ return 0 ;
433
+ }
434
+
435
+ isMulti = false ;
436
+ QGis::WkbType geomType = geom->wkbType ();
437
+ if ( geomType == QGis::WKBLineString || geomType == QGis::WKBLineString25D )
438
+ {
439
+ return geom;
440
+ }
441
+ else if ( geomType == QGis::WKBMultiLineString || geomType == QGis::WKBMultiLineString25D )
442
+ {
443
+ // search vertex
444
+ isMulti = true ;
445
+ int currentVertex = 0 ;
446
+ QgsMultiPolyline multiLine = geom->asMultiPolyline ();
447
+ QgsMultiPolyline::const_iterator it = multiLine.constBegin ();
448
+ for ( ; it != multiLine.constEnd (); ++it )
449
+ {
450
+ currentVertex += it->size ();
451
+ if ( vertex < currentVertex )
452
+ {
453
+ QgsGeometry* g = QgsGeometry::fromPolyline ( *it );
454
+ delete geom;
455
+ return g;
456
+ }
457
+ }
458
+ }
459
+ delete geom;
460
+ return 0 ;
461
+ }
462
+
463
+ QgsGeometry* QgsMapToolOffsetCurve::convertToMultiLine ( QgsGeometry* geom )
464
+ {
465
+ return 0 ;
466
+ }
0 commit comments