Exemplo n.º 1
0
            private void ProcessFeature(Feature feature, [CanBeNull] Polygon perimeter)
            {
                Polyline curve;

                var shape = feature.GetShape();

                if (shape is Polygon polygon)
                {
                    var before = GetPointIDs(polygon);                     // TODO DEBUG DROP
                    curve = GeometryUtils.Boundary(polygon);
                }
                else if (shape is Polyline polyline)
                {
                    var before = GetPointIDs(polyline);                     // TODO DEBUG DROP
                    curve = polyline;
                }
                else
                {
                    curve = null;
                    Assert.Fail("Input shape is neither Polyline nor Polygon");
                }

                if (_simplificationTolerance > 0)
                {
                    curve = GeometryUtils.Generalize(curve, _simplificationTolerance);
                    curve = GeometryUtils.Simplify(curve);
                }

                var builder = new PolylineBuilder(curve)
                {
                    HasID = true
                };

                builder.SetEmpty();

                int controlPointsAdded   = 0;
                int controlPointsRemoved = 0;

                // Things to watch out:
                // - preserve non-linear segments
                // - process each part separately
                // - remember Start/EndPoint or rings

                foreach (var part in curve.Parts)
                {
                    var numSegments = part.Count;
                    if (numSegments < 1)
                    {
                        continue;
                    }
                    bool startNewPart = true;

                    var one = part[0];
                    for (int i = 1; i < numSegments; i++)
                    {
                        var two = part[i];

                        var centerPoint = two.StartPoint;
                        if (ProcessingUtils.WithinPerimeter(centerPoint, perimeter))
                        {
                            DoVertex(ref one, ref two, ref controlPointsAdded, ref controlPointsRemoved);
                        }

                        builder.AddSegment(one, startNewPart);
                        startNewPart = false;

                        one = two;
                    }

                    // For polygons (closed rings), also look at Start/EndPoint
                    if (shape is Polygon)
                    {
                        var two         = part[0];
                        var centerPoint = two.StartPoint;
                        if (ProcessingUtils.WithinPerimeter(centerPoint, perimeter))
                        {
                            DoVertex(ref one, ref two, ref controlPointsAdded, ref controlPointsRemoved);
                        }
                    }

                    builder.AddSegment(one, startNewPart);
                }

                if (controlPointsAdded > 0 || controlPointsRemoved > 0)
                {
                    bool wantPolygon = shape is Polygon;

                    if (wantPolygon)
                    {
                        var polyline = builder.ToGeometry();
                        shape = PolygonBuilder.CreatePolygon(polyline);
                    }
                    else
                    {
                        shape = builder.ToGeometry();
                    }

                    var after = GetPointIDs((Multipart)shape);

                    feature.SetShape(shape);
                    feature.Store();                     // TODO requires an edit session

                    _msg.DebugFormat("Feature {0}: {1} control points added",
                                     ProcessingUtils.Format(feature), controlPointsAdded);

                    ControlPointsAdded   += controlPointsAdded;
                    ControlPointsRemoved += controlPointsRemoved;
                }
            }