// public static void InfuseLanduse(
        //     this IEnumerable<(CompleteWay, List<(long, long)>)> polygons,
        //     CompleteWay landusePolygon, string classification)
        // {
        //     if (landusePolygon.IsClockwise())
        //     {
        //         Array.Reverse(landusePolygon.Nodes);
        //     }
        //
        //     var landuseBBox = new BBox(landusePolygon);
        //
        //     var key = "_classification:" + classification;
        //
        //     foreach (var (polygon , _) in polygons)
        //     {
        //         Array.Reverse(polygon.Nodes);
        //         var totalSize = 0.0;
        //
        //         if (polygon.Tags == null)
        //         {
        //             polygon.Tags = new TagsCollection();
        //         }
        //
        //         if (polygon.Tags.TryGetValue(key, out var value))
        //         {
        //             double.TryParse(value, out totalSize);
        //         }
        //
        //
        //         var polygonBBox = new BBox(polygon);
        //         if (!polygonBBox.OverlapsWith(landuseBBox))
        //         {
        //             continue;
        //         }
        //
        //
        //         var allWays = new[] {polygon, landusePolygon}.SplitAllWays();
        //
        //         // We use splitAllWays to intersect the polygon
        //         // Note that this is invoked by but two lines, which either intersect or do not intersect at all.
        //
        //         if (allWays.Count == 2)
        //         {
        //             // If there are but two lines, these are the same as the original lines.
        //             // Here, three things can happen:
        //             // - The landusepolygon is completely contained into the polygon,
        //             // - The polygon is completely contained in the landuse polygon
        //             // - There is no overlap at all
        //
        //             if (landusePolygon.FullyContains(polygon))
        //             {
        //                 totalSize += polygon.Area();
        //             }
        //             else if (polygon.FullyContains(landusePolygon))
        //             {
        //                 totalSize += landusePolygon.Area();
        //             }
        //
        //             // No overlap - we don't do anything
        //         }
        //         else
        //         {
        //             // There is overlap in the polygon
        //             totalSize += SplitWays.IntersectionSurfaceBetween(polygon, landusePolygon);
        //         }
        //
        //
        //         polygon.Tags[key] = "" + totalSize;
        //     }
        // }

        public static IEnumerable <(long from, long to)> IdPairs(this CompleteWay way)
        {
            for (var i = 1; i < way.Nodes.Length; i++)
            {
                yield return(way.Nodes[i - 1].Id.Value, way.Nodes[i].Id.Value);
            }
        }
示例#2
0
        public void PreprocessWithPlaceAndWay_ShouldMergePlaceIntoIt()
        {
            var node1 = CreateNode(1, 0, 0);
            var node2 = CreateNode(2, 0, 1);
            var node3 = CreateNode(3, 1, 1);
            var node4 = CreateNode(4, 1, 0);
            var node5 = CreateNode(5, 0.5, 0.6);

            node5.Tags.Add("place", "any");
            var way1 = new CompleteWay
            {
                Id   = 6,
                Tags = new TagsCollection {
                    { FeatureAttributes.NAME, "name" }
                },
                Nodes = new[] { node1, node2, node3, node4, node1 }
            };
            var osmElements = new List <ICompleteOsmGeo> {
                node5, way1
            };

            var dictionary = new Dictionary <string, List <ICompleteOsmGeo> > {
                { FeatureAttributes.NAME, osmElements }
            };

            var results = _preprocessorExecutor.Preprocess(dictionary);

            Assert.AreEqual(1, results[results.Keys.First()].Count);
            var geoLocation = results[results.Keys.First()].First().Attributes[FeatureAttributes.GEOLOCATION] as AttributesTable;

            Assert.IsNotNull(geoLocation);
            Assert.AreEqual(0.5, geoLocation[FeatureAttributes.LAT]);
            Assert.AreEqual(0.6, geoLocation[FeatureAttributes.LON]);
        }
        public void PreprocessOneWayAndOneRelation_ShouldRemoveWayAndAddItToRelation()
        {
            var node1 = CreateNode(1);
            var node2 = CreateNode(2);
            var node3 = CreateNode(3);
            var node4 = CreateNode(4);
            var way1  = new CompleteWay
            {
                Id    = 5,
                Tags  = new TagsCollection(),
                Nodes = new[] { node1, node2 }
            };

            way1.Tags.Add("waterway", "stream");
            var way2 = new CompleteWay
            {
                Id    = 6,
                Tags  = new TagsCollection(),
                Nodes = new[] { node3, node4 }
            };
            var osmElements = new List <ICompleteOsmGeo> {
                node1, node2, node3, node4, way1, way2
            };
            var dictionary = new Dictionary <string, List <ICompleteOsmGeo> > {
                { FeatureAttributes.NAME, osmElements }
            };

            var results = _preprocessorExecutor.Preprocess(dictionary);

            Assert.AreEqual(5, results.Count);
            Assert.AreEqual(4, results.Count(f => f.Geometry is Point));
            Assert.AreEqual(1, results.Count(f => f.Geometry is LineString));
        }
        public void TestUpdate_OsmChangeFileWithModification_ShouldUpdateDatabase()
        {
            var way = new CompleteWay()
            {
                Id   = 1,
                Tags = new TagsCollection {
                    { "highway", "track" }, { "route", "bicycle" }
                },
                Nodes = new Node[0]
            };
            var changes = new OsmChange
            {
                Create = new OsmGeo[0],
                Modify = new OsmGeo[] { way.ToSimple() },
                Delete = new OsmGeo[0]
            };
            var list = new List <Feature> {
                new Feature(new LineString(new Coordinate[0]), new AttributesTable())
            };

            _geoJsonPreprocessorExecutor
            .Preprocess(Arg.Is <Dictionary <string, List <ICompleteOsmGeo> > >(x => x.Values.Count == 1))
            .Returns(list);
            _geoJsonPreprocessorExecutor
            .Preprocess(Arg.Is <List <CompleteWay> >(x => x.Count == 1))
            .Returns(list);
            _osmGateway.GetCompleteWay(1).Returns(way);

            _service.Update(changes).Wait();

            _elasticSearchGateway.Received(1).UpdatePointsOfInterestData(Arg.Is <List <Feature> >(x => x.Count == 1));
            _elasticSearchGateway.Received(1).UpdateHighwaysData(Arg.Is <List <Feature> >(x => x.Count == 1));
        }
        /// <summary>
        /// Returns a linestring exactly representing the way.
        /// </summary>
        /// <param name="way">The way.</param>
        /// <returns>A linestring.</returns>
        public static LineString ToLineString(this CompleteWay way)
        {
            if (way == null)
            {
                throw new ArgumentNullException(nameof(way));
            }
            if (way.Nodes == null)
            {
                throw new ArgumentException($"{nameof(way)} has no nodes.");
            }
            if (way.Nodes.Length < 2)
            {
                throw new ArgumentException($"{nameof(way)} has not enough nodes.");
            }

            var coordinates = new Coordinate[way.Nodes.Length];

            for (var n = 0; n < way.Nodes.Length; n++)
            {
                var node = way.Nodes[n];

                if (node.Longitude == null || node.Latitude == null)
                {
                    continue;
                }

                coordinates[n] = new Coordinate(node.Longitude.Value, node.Latitude.Value);
            }

            return(new LineString(coordinates));
        }
        /// <summary>
        /// Compares the two complete objects.
        /// </summary>
        public static void CompareComplete(CompleteWay expected, CompleteWay actual)
        {
            if (expected == null)
            { // ok, if the value is also null.
                Assert.IsNull(actual);
            }
            else
            { // check and compare the value.
                Assert.IsNotNull(actual);
                Assert.AreEqual(expected.Id, actual.Id);
                Assert.AreEqual(expected.ChangeSetId, actual.ChangeSetId);
                Assert.AreEqual(expected.TimeStamp, actual.TimeStamp);
                Assert.AreEqual(expected.User, actual.User);
                Assert.AreEqual(expected.UserId, actual.UserId);
                Assert.AreEqual(expected.Version, actual.Version);
                Assert.AreEqual(expected.Visible, actual.Visible);

                if (expected.Nodes == null)
                { // ok, if the value is also null.
                    Assert.IsNotNull(actual.Nodes);
                }
                else
                { // check and compare the nodes.
                    Assert.AreEqual(expected.Nodes.Count, actual.Nodes.Count);
                    for (int idx = 0; idx < expected.Nodes.Count; idx++)
                    {
                        ComparisonHelpers.CompareComplete(
                            expected.Nodes[idx], actual.Nodes[idx]);
                    }
                }
            }
        }
        public void PreprocessWaysWithSameDirection_ShouldReturnOneLineString()
        {
            var node1 = CreateNode(1);
            var node2 = CreateNode(2);
            var node3 = CreateNode(3);
            var way1  = new CompleteWay {
                Id = 4, Tags = new TagsCollection()
            };

            way1.Tags.Add(FeatureAttributes.NAME, "name");
            way1.Tags.Add("place", "name");
            way1.Nodes = new[] { node2, node3 };
            var way2 = new CompleteWay {
                Id = 5, Tags = new TagsCollection()
            };

            way2.Tags.Add(FeatureAttributes.NAME, "name");
            way2.Tags.Add("place", "name");
            way2.Nodes = new[] { node1, node3 };
            var osmElements = new List <ICompleteOsmGeo> {
                node1, node2, node3, way1, way2
            };
            var dictionary = new Dictionary <string, List <ICompleteOsmGeo> > {
                { FeatureAttributes.NAME, osmElements }
            };

            var results = _preprocessorExecutor.Preprocess(dictionary);

            Assert.AreEqual(1, results.Count(f => f.Geometry is LineString));
        }
示例#8
0
文件: Utils.cs 项目: sk-zk/OsmProto
        /// <summary>
        /// Returns the coordinates of a way's nodes projected and with elevation.
        /// </summary>
        /// <param name="way"></param>
        /// <param name="offsetX"></param>
        /// <param name="offsetY"></param>
        /// <returns></returns>
        public static List<Vector3> ProjectWay(CompleteWay way, Point offset,
            IProjection projection, Elevation elevation, bool fetchElevation = true)
        {
            var nodes = new List<Vector3>();
            for (int i = 0; i < way.Nodes.Length; i++)
            {
                var node = way.Nodes[i];
                // convert to X/Y
                var projPos = projection.Project(node);

                // apply offset
                projPos.X -= offset.X;
                projPos.Y -= offset.Y;

                // flip vertically because Z is down
                projPos.Y *= -1;

                double el = 0;
                if (fetchElevation)
                    el = elevation.GetElevation(node.Latitude.Value, node.Longitude.Value);

                var vector = new Vector3((float)projPos.X, (float)el, (float)projPos.Y);
                nodes.Add(vector);
            }

            return nodes;
        }
        /// <summary>
        /// Compares what is in the complete list against the objects in the reference source.
        /// </summary>
        /// <param name="expected"></param>
        /// <param name="actual"></param>
        private void Compare(MemoryDataSource expected, List <ICompleteOsmGeo> actual)
        {
            var exectedList = new List <ICompleteOsmGeo>();

            foreach (var node in expected.GetNodes())
            {
                var completeNode = node;
                if (completeNode != null)
                {
                    exectedList.Add(completeNode);
                }
            }
            foreach (var way in expected.GetWays())
            {
                var completeWay = CompleteWay.CreateFrom(way, expected);
                if (completeWay != null)
                {
                    exectedList.Add(completeWay);
                }
            }
            foreach (var relation in expected.GetRelations())
            {
                var completeRelation = CompleteRelation.CreateFrom(relation, expected);
                if (completeRelation != null)
                {
                    exectedList.Add(completeRelation);
                }
            }

            ComparisonHelpers.CompareComplete(exectedList, actual);
        }
示例#10
0
        public void PreprocessPlaceNodeWithContainerPlaceFromDatabase_ShouldUpdateAddress()
        {
            var node1 = CreateNode(1, 0, 0);
            var node2 = CreateNode(2, 0, 1);
            var node3 = CreateNode(3, 1, 1);
            var node4 = CreateNode(4, 1, 0);
            var node5 = CreateNode(5, 0.5, 0.6);

            node5.Tags.Add("place", "any");
            var way1 = new CompleteWay
            {
                Id   = 6,
                Tags = new TagsCollection
                {
                    { FeatureAttributes.NAME, FeatureAttributes.NAME },
                    { "place", "any" }
                },
                Nodes = new[] { node1, node2, node3, node4, node1 }
            };
            var dictionary = new Dictionary <string, List <ICompleteOsmGeo> >
            {
                { FeatureAttributes.NAME, new List <ICompleteOsmGeo> {
                      node5, way1
                  } },
            };
            var databaseMock = _preprocessorExecutor.Preprocess(dictionary);
            var cloned       = _preprocessorExecutor.Preprocess(dictionary);

            databaseMock.First().Geometry = databaseMock.Last().Geometry;
            var results = _preprocessorExecutor.MergePlaceNodes(cloned.Take(1).ToList(), databaseMock.Where(f => f.Geometry is Polygon).ToList());

            Assert.AreEqual(1, results.Count);
            Assert.IsTrue(results.First().Geometry is Polygon);
        }
示例#11
0
        public void ToGeoJson_RelationWithOuterOnly_ShouldReturnMultiPolygon()
        {
            var node1 = CreateNode(1);
            var node2 = CreateNode(2);
            var node3 = CreateNode(3);
            var node4 = CreateNode(1);
            var way   = new CompleteWay
            {
                Id    = 4,
                Nodes = new[] { node1, node2, node3, node4 }
            };
            var relation = new CompleteRelation {
                Id = 5, Tags = new TagsCollection()
            };

            relation.Tags.Add("type", "boundary");
            relation.Members = new[] { new CompleteRelationMember {
                                           Member = way, Role = "outer"
                                       } };

            var feature      = _converter.ToGeoJson(relation);
            var multiPolygon = feature.Geometry as MultiPolygon;

            Assert.IsNotNull(multiPolygon);
            Assert.AreEqual(4, multiPolygon.Coordinates.Length);
            Assert.AreEqual(node1.Latitude, multiPolygon.Coordinates.First().Y);
            Assert.AreEqual(node4.Longitude, multiPolygon.Coordinates.Last().X);
        }
示例#12
0
        public void ToGeoJson_RelationWithPolygonAndLineString_ShouldReturnMultiLineStringAfterGrouping()
        {
            var node1 = CreateNode(1);
            var node2 = CreateNode(2);
            var node3 = CreateNode(3);
            var node4 = CreateNode(4);
            var node5 = CreateNode(5);
            var node6 = CreateNode(6);
            var node7 = CreateNode(7);
            var wayPartOfLineString1 = new CompleteWay {
                Id = 8
            };
            var wayPartOfLineString2 = new CompleteWay {
                Id = 9
            };

            wayPartOfLineString1.Nodes = new[] { node1, node2 };
            wayPartOfLineString2.Nodes = new[] { node2, node3 };
            var wayPartOfPolygon1 = new CompleteWay {
                Id = 10
            };
            var wayPartOfPolygon2 = new CompleteWay {
                Id = 11
            };

            wayPartOfPolygon1.Nodes = new[] { node4, node5, node6 };
            wayPartOfPolygon2.Nodes = new[] { node4, node7, node6 };
            var relation = new CompleteRelation {
                Id = 12, Tags = new TagsCollection()
            };

            relation.Tags.Add(NAME, NAME);
            relation.Members = new[] {
                new CompleteRelationMember {
                    Member = wayPartOfLineString1
                },
                new CompleteRelationMember {
                    Member = wayPartOfLineString2
                },
                new CompleteRelationMember {
                    Member = wayPartOfPolygon1
                },
                new CompleteRelationMember {
                    Member = wayPartOfPolygon2
                },
            };

            var feature         = _converter.ToGeoJson(relation);
            var multiLineString = feature.Geometry as MultiLineString;

            Assert.IsNotNull(multiLineString);
            Assert.AreEqual(2, multiLineString.Geometries.Length);
            var lineString = multiLineString.Geometries.First();

            Assert.AreEqual(3, lineString.Coordinates.Length);
            var lineString2 = multiLineString.Geometries.Last();

            Assert.AreEqual(5, lineString2.Coordinates.Length);
            Assert.AreEqual(lineString2.Coordinates.First(), lineString2.Coordinates.Last());
        }
示例#13
0
 public static void CombineSegments(CompleteWay subject, CompleteWay reference)
 {
     if (subject.Nodes.Last().Id == reference.Nodes.First().Id)
     {
         subject.Nodes = subject.Nodes.Concat(reference.Nodes.Skip(1)).ToArray();
     }
     else if (subject.Nodes.Last().Id == reference.Nodes.Last().Id)
     {
         if (reference.Tags != null && reference.Tags.ContainsKey("oneway"))
         {
             throw new InvalidOperationException("Reversing a oneway");
         }
         subject.Nodes = subject.Nodes.Concat(reference.Nodes.Reverse().Skip(1)).ToArray();
     }
     else if (subject.Nodes.First().Id == reference.Nodes.Last().Id)
     {
         subject.Nodes = reference.Nodes.Concat(subject.Nodes.Skip(1)).ToArray();
     }
     else if (subject.Nodes.First().Id == reference.Nodes.First().Id)
     {
         if (reference.Tags != null && reference.Tags.ContainsKey("oneway"))
         {
             throw new InvalidOperationException("Reversing a oneway");
         }
         subject.Nodes = reference.Nodes.Reverse().Concat(subject.Nodes.Skip(1)).ToArray();
     }
     else
     {
         throw new Exception("Ways are not end-to-end, and can't be combined");
     }
 }
示例#14
0
        public void PreprocessArea_ShouldGetGeoLocationCenter()
        {
            var node1 = CreateNode(1, 0, 0);
            var node2 = CreateNode(1, 0, 1);
            var node3 = CreateNode(1, 1, 1);
            var node4 = CreateNode(1, 1, 0);
            var way   = new CompleteWay
            {
                Nodes = new[] { node1, node2, node3, node4, node1 },
                Tags  = new TagsCollection
                {
                    { FeatureAttributes.NAME, "name" }
                }
            };
            var osmElements = new List <ICompleteOsmGeo> {
                way
            };
            var dictionary = new Dictionary <string, List <ICompleteOsmGeo> > {
                { FeatureAttributes.NAME, osmElements }
            };

            var results = _preprocessorExecutor.Preprocess(dictionary);

            Assert.AreEqual(1, results.Count);
            var geoLocation = results.First().Attributes[FeatureAttributes.POI_GEOLOCATION] as IAttributesTable;

            Assert.IsNotNull(geoLocation);
            Assert.AreEqual(0.5, geoLocation[FeatureAttributes.LAT]);
            Assert.AreEqual(0.5, geoLocation[FeatureAttributes.LAT]);
        }
示例#15
0
        public void ToGeoJson_MultiPolygonWithTwoHoles_ShouldReturnMultiPlygonWithSinglePolygon()
        {
            var id     = 1;
            var node1  = CreateNode(id++, 0, 0);
            var node2  = CreateNode(id++, 1, 0);
            var node3  = CreateNode(id++, 1, 1);
            var node4  = CreateNode(id++, 0, 1);
            var node5  = CreateNode(id++, 0.5, 0.5);
            var node6  = CreateNode(id++, 0.5, 0.6);
            var node7  = CreateNode(id++, 0.6, 0.6);
            var node8  = CreateNode(id++, 0.6, 0.5);
            var node9  = CreateNode(id++, 0.3, 0.3);
            var node10 = CreateNode(id++, 0.3, 0.4);
            var node11 = CreateNode(id++, 0.4, 0.4);
            var node12 = CreateNode(id++, 0.4, 0.3);

            var wayOuter = new CompleteWay
            {
                Id    = id++,
                Nodes = new[] { node1, node2, node3, node4, node1 }
            };
            var wayInner1 = new CompleteWay
            {
                Id    = id++,
                Nodes = new[] { node5, node6, node7, node8, node5 }
            };
            var wayInner2 = new CompleteWay
            {
                Id    = id++,
                Nodes = new[] { node9, node10, node11, node12, node9 }
            };
            var relation = new CompleteRelation
            {
                Id      = id++,
                Tags    = new TagsCollection(),
                Members = new[]
                {
                    new CompleteRelationMember {
                        Member = wayInner1, Role = "inner"
                    },
                    new CompleteRelationMember {
                        Member = wayInner2, Role = "inner"
                    },
                    new CompleteRelationMember {
                        Member = wayOuter, Role = "outer"
                    }
                }
            };

            relation.Tags.Add("type", "boundary");

            var geoJson = _converter.ToGeoJson(relation);

            var multiPlygon = geoJson.Geometry as MultiPolygon;

            Assert.IsNotNull(multiPlygon);
            Assert.IsTrue(multiPlygon.IsValid);
            Assert.AreEqual(1, multiPlygon.Geometries.Length);
        }
示例#16
0
        public void ToGeoJson_RelationWithTwoSubRelationsWithInnerRole_ShouldReturnMultiPolygon()
        {
            int id    = 1;
            var node1 = CreateNode(id++);
            var node2 = CreateNode(id++);
            var node3 = CreateNode(id++);

            var way1 = new CompleteWay
            {
                Id    = 4,
                Nodes = new[] { node1, node2, node3, node1 }
            };
            var node4 = CreateNode(id++);
            var node5 = CreateNode(id++);
            var node6 = CreateNode(id++);
            var way2  = new CompleteWay
            {
                Id    = id++,
                Nodes = new[] { node4, node5, node6, node4 }
            };
            var subRelation1 = new CompleteRelation
            {
                Id      = id++,
                Members = new[] { new CompleteRelationMember {
                                      Member = way1, Role = "outer"
                                  } }
            };
            var subRelation2 = new CompleteRelation
            {
                Id      = id++,
                Members = new[] { new CompleteRelationMember {
                                      Member = way2, Role = "outer"
                                  } }
            };
            var relation = new CompleteRelation {
                Id = id++, Tags = new TagsCollection()
            };

            relation.Tags.Add("type", "multipolygon");
            relation.Members = new[] {
                new CompleteRelationMember {
                    Member = subRelation1
                },
                new CompleteRelationMember {
                    Member = subRelation2
                }
            };

            var feature      = _converter.ToGeoJson(relation);
            var multiPolygon = feature.Geometry as MultiPolygon;

            Assert.IsNotNull(multiPolygon);
            Assert.AreEqual(8, multiPolygon.Coordinates.Length);
            Assert.AreEqual(node1.Latitude, multiPolygon.Coordinates.First().Y);
            Assert.AreEqual(node4.Longitude, multiPolygon.Coordinates.Last().X);
        }
示例#17
0
        /// <summary>
        /// Returns the centroid of a building.
        /// </summary>
        private static LatLon GetCentroid(CompleteWay building)
        {
            var points = building.Nodes.Select(
                x => new GeoAPI.Geometries.Coordinate(x.Latitude.Value, x.Longitude.Value))
                         .ToArray();
            var poly     = new NetTopologySuite.Geometries.Polygon(new NetTopologySuite.Geometries.LinearRing(points));
            var centroid = poly.Centroid.Coordinate;

            return(new LatLon(centroid.X, centroid.Y));
        }
示例#18
0
 /// <summary>
 /// Splits a way into individual segments
 /// </summary>
 public static IEnumerable <CompleteWay> AsSegments(this CompleteWay way)
 {
     for (var i = 1; i < way.Nodes.Length; i++)
     {
         yield return(new CompleteWay()
         {
             Nodes = new[] { way.Nodes[i - 1], way.Nodes[i] }
         });
     }
 }
示例#19
0
        public void TestToSimple()
        {
            var completeWay = new CompleteWay()
            {
                ChangeSetId = 1,
                Id          = 10,
                Nodes       = new Node[]
                {
                    new Node()
                    {
                        Id = 1
                    },
                    new Node()
                    {
                        Id = 2
                    },
                    new Node()
                    {
                        Id = 3
                    }
                },
                Tags = new Tags.TagsCollection(
                    new Tags.Tag("tag1", "value1"),
                    new Tags.Tag("tag2", "value2")),
                TimeStamp = DateTime.Now,
                UserName  = "******",
                UserId    = 1,
                Version   = 23,
                Visible   = true
            };

            var osmGeo = completeWay.ToSimple();

            Assert.IsNotNull(osmGeo);
            Assert.IsInstanceOf <Way>(osmGeo);

            var way = osmGeo as Way;

            Assert.AreEqual(completeWay.Id, way.Id);
            Assert.AreEqual(completeWay.ChangeSetId, way.ChangeSetId);
            Assert.AreEqual(completeWay.TimeStamp, way.TimeStamp);
            Assert.AreEqual(completeWay.UserName, way.UserName);
            Assert.AreEqual(completeWay.UserId, way.UserId);
            Assert.AreEqual(completeWay.Version, way.Version);
            Assert.AreEqual(completeWay.Visible, way.Visible);
            Assert.IsNotNull(way.Nodes);
            Assert.AreEqual(completeWay.Nodes.Length, way.Nodes.Length);
            for (var i = 0; i < completeWay.Nodes.Length; i++)
            {
                Assert.AreEqual(completeWay.Nodes[i].Id, way.Nodes[i]);
            }
        }
示例#20
0
 /// <summary>
 /// Gets the coordinates from the given way.
 /// </summary>
 public static List <Coordinate> GetCoordinates(this CompleteWay way)
 {
     if (way.Nodes != null)
     {
         var coordinates = new List <Coordinate>();
         for (int i = 0; i < way.Nodes.Length; i++)
         {
             coordinates.Add(way.Nodes[i].GetCoordinate());
         }
         return(coordinates);
     }
     return(null);
 }
示例#21
0
        public void ToGeoJson_WayWithOneNode_ShouldReturnNull()
        {
            var node = CreateNode(1);
            var way  = new CompleteWay {
                Id = 2, Tags = new TagsCollection()
            };

            way.Nodes = new[] { node };
            way.Tags.Add(NAME, NAME);

            var feature = _converter.ToGeoJson(way);

            Assert.IsNull(feature);
        }
        /// <summary>
        /// Completes an uncompleted ring.
        /// </summary>
        /// <param name="ways"></param>
        /// <param name="assignedFlags"></param>
        /// <param name="nodes"></param>
        /// <param name="role"></param>
        /// <returns></returns>
        private bool CompleteRing(List <KeyValuePair <bool, CompleteWay> > ways, bool[] assignedFlags,
                                  List <CompleteNode> nodes, bool?role)
        {
            for (int idx = 0; idx < ways.Count; idx++)
            {
                if (!assignedFlags[idx])
                { // way not assigned.
                    KeyValuePair <bool, CompleteWay> wayEntry = ways[idx];
                    CompleteWay nextWay = wayEntry.Value;
                    if (!role.HasValue || wayEntry.Key == role.Value)
                    { // only try matching roles if the role has been set.
                        List <CompleteNode> nextNodes = null;
                        if (nodes[nodes.Count - 1].Id == nextWay.Nodes[0].Id)
                        { // last node of the previous way is the first node of the next way.
                            nextNodes          = nextWay.Nodes.GetRange(1, nextWay.Nodes.Count - 1);
                            assignedFlags[idx] = true;
                        }
                        else if (nodes[nodes.Count - 1].Id == nextWay.Nodes[nextWay.Nodes.Count - 1].Id)
                        { // last node of the previous way is the last node of the next way.
                            nextNodes = nextWay.Nodes.GetRange(0, nextWay.Nodes.Count - 1);
                            nextNodes.Reverse();
                            assignedFlags[idx] = true;
                        }

                        // add the next nodes if any.
                        if (assignedFlags[idx])
                        { // yep, way was assigned!
                            nodes.AddRange(nextNodes);
                            if (nodes[nodes.Count - 1].Id == nodes[0].Id)
                            { // yes! a closed ring was found!
                                return(true);
                            }
                            else
                            {     // noo! ring not closed yet!
                                if (this.CompleteRing(ways, assignedFlags, nodes, role))
                                { // yes! a complete ring was found
                                    return(true);
                                }
                                else
                                { // damn complete ring not found. backtrack people!
                                    assignedFlags[idx] = false;
                                    nodes.RemoveRange(nodes.Count - nextNodes.Count, nextNodes.Count);
                                }
                            }
                        }
                    }
                }
            }
            return(false);
        }
示例#23
0
        private static Polygon ToPolygon(CompleteWay w)
        {
            var coordinates = new Coordinate[w.Nodes.Length];
            var i           = 0;

            foreach (var n in w.Nodes)
            {
                var p = new Coordinate(n.Longitude.Value, n.Latitude.Value);
                coordinates[i] = p;
                i++;
            }

            return(new Polygon(new LinearRing(coordinates)));
        }
示例#24
0
        public static CompleteWay Reduce(CompleteWay way)
        {
            var lineString = way.AsLineString();
            var reducer    = new NetTopologySuite.Precision.GeometryPrecisionReducer(new PrecisionModel()
            {
            });

            NetTopologySuite.Simplify.DouglasPeuckerLineSimplifier.Simplify(way.GetCoordinates().ToArray(), .0004);

            var geometry = (LineString)reducer.Reduce(lineString);

            //way =
            return(way);
        }
示例#25
0
        public void ToGeoJson_RelationWithTouchingPolygones_ShouldReturnValidMultiPolygon()
        {
            int id            = 1;
            var node1         = CreateNode(id++, 0, 0);
            var node2         = CreateNode(id++, 0, 1);
            var node3         = CreateNode(id++, 1, 1);
            var node4         = CreateNode(id++, 1, 0);
            var node5         = CreateNode(id++, 0, 2);
            var node6         = CreateNode(id++, 1, 2);
            var node7         = CreateNode(id++, -1, -1);
            var node8         = CreateNode(id++, 3, -1);
            var node9         = CreateNode(id++, 3, 3);
            var node10        = CreateNode(id++, -1, 3);
            var polygon1inner = new CompleteWay {
                Id = id++, Nodes = new[] { node1, node2, node3, node4, node1 }
            };
            var polygon2inner = new CompleteWay {
                Id = id++, Nodes = new[] { node2, node5, node6, node3, node2 }
            };
            var polygonOuter = new CompleteWay {
                Id = id++, Nodes = new[] { node7, node8, node9, node10, node7 }
            };

            var relation = new CompleteRelation {
                Id = id++, Tags = new TagsCollection()
            };

            relation.Tags.Add(NAME, NAME);
            relation.Tags.Add("type", "multipolygon");
            relation.Members = new[] {
                new CompleteRelationMember {
                    Member = polygonOuter, Role = "outer"
                },
                new CompleteRelationMember {
                    Member = polygon1inner
                },
                new CompleteRelationMember {
                    Member = polygon2inner
                }
            };

            var feature      = _converter.ToGeoJson(relation);
            var multiPolygon = feature.Geometry as MultiPolygon;

            Assert.IsNotNull(multiPolygon);
            var isValidOp = new IsValidOp(multiPolygon);

            Assert.IsTrue(isValidOp.IsValid);
        }
示例#26
0
        /// <summary>
        /// Interprets an OSM-object and returns the correctponding geometry.
        /// </summary>
        /// <param name="simpleOsmGeo"></param>
        /// <param name="data"></param>
        /// <returns></returns>
        public virtual GeometryCollection Interpret(OsmGeo simpleOsmGeo, IDataSourceReadOnly data)
        {
            switch (simpleOsmGeo.Type)
            {
            case OsmGeoType.Node:
                return(this.Interpret(simpleOsmGeo as Node));

            case OsmGeoType.Way:
                return(this.Interpret(CompleteWay.CreateFrom(simpleOsmGeo as Way, data)));

            case OsmGeoType.Relation:
                return(this.Interpret(CompleteRelation.CreateFrom(simpleOsmGeo as Relation, data)));
            }
            throw new ArgumentOutOfRangeException();
        }
示例#27
0
 public static Way AsOsmGeo(this CompleteWay way)
 {
     return(new Way()
     {
         Id = way.Id,
         Nodes = way.Nodes.Select(n => n.Id.Value).ToArray(),
         Tags = way.Tags,
         Version = way.Version,
         Visible = way.Visible,
         ChangeSetId = way.ChangeSetId,
         TimeStamp = way.TimeStamp,
         UserId = way.UserId,
         UserName = way.UserName
     });
 }
示例#28
0
        public void ToGeoJson_Convert8Shape_ShouldConvertToMultipolygon()
        {
            int id    = 1;
            var node1 = CreateNode(id++, 0, 0);
            var node2 = CreateNode(id++, 0, 1);
            var node3 = CreateNode(id++, 1, 1);

            var node4 = CreateNode(id++, 1, 0);
            var node5 = CreateNode(id++, 0, -1);
            var node6 = CreateNode(id++, -1, -1);

            var node7 = CreateNode(id++, -1, 0);
            var way1  = new CompleteWay {
                Id = id++, Nodes = new[] { node1, node2, node3 }
            };
            var way2 = new CompleteWay {
                Id = id++, Nodes = new[] { node3, node4, node1, node5, node6 }
            };
            var way3 = new CompleteWay {
                Id = id++, Nodes = new[] { node6, node7, node1 }
            };

            var relation = new CompleteRelation {
                Id = id++, Tags = new TagsCollection()
            };

            relation.Tags.Add(NAME, NAME);
            relation.Tags.Add("type", "multipolygon");
            relation.Members = new[] {
                new CompleteRelationMember {
                    Member = way1, Role = "outer"
                },
                new CompleteRelationMember {
                    Member = way2, Role = "outer"
                },
                new CompleteRelationMember {
                    Member = way3, Role = "outer"
                }
            };

            var feature      = _converter.ToGeoJson(relation);
            var multiPolygon = feature.Geometry as MultiPolygon;

            Assert.IsNotNull(multiPolygon);
            var isValidOp = new IsValidOp(multiPolygon);

            Assert.IsTrue(isValidOp.IsValid);
        }
示例#29
0
        /// <summary>
        /// Translates the given OSM objects into corresponding geometries.
        /// </summary>
        /// <param name="scene"></param>
        /// <param name="projection"></param>
        /// <param name="source"></param>
        /// <param name="osmGeo"></param>
        public virtual void Translate(Scene2D scene, IProjection projection, IDataSourceReadOnly source, OsmGeo osmGeo)
        {
            switch (osmGeo.Type)
            {
            case OsmGeoType.Node:
                this.Translate(scene, projection, CompleteNode.CreateFrom(osmGeo as Node));
                break;

            case OsmGeoType.Way:
                this.Translate(scene, projection, CompleteWay.CreateFrom(osmGeo as Way, source));
                break;

            case OsmGeoType.Relation:
                this.Translate(scene, projection, CompleteRelation.CreateFrom(osmGeo as Relation, source));
                break;
            }
        }
示例#30
0
        public virtual FeatureCollection Interpret(OsmGeo simpleOsmGeo, IDataSourceReadOnly data)
        {
            switch (simpleOsmGeo.Type)
            {
            case OsmGeoType.Node:
                return(this.Interpret((ICompleteOsmGeo)(simpleOsmGeo as Node)));

            case OsmGeoType.Way:
                return(this.Interpret((ICompleteOsmGeo)CompleteWay.CreateFrom(simpleOsmGeo as Way, (INodeSource)data)));

            case OsmGeoType.Relation:
                return(this.Interpret((ICompleteOsmGeo)CompleteRelation.CreateFrom(simpleOsmGeo as Relation, (IOsmGeoSource)data)));

            default:
                throw new ArgumentOutOfRangeException();
            }
        }