public Node[] AddArray(Node[] array1, Node[] array2) { Node[] res = null; if (array1 != null && array2 != null) { res = new Node[array1.Length + array2.Length]; Array.Copy(array1, res, array1.Length); Array.Copy(array2, 0, res, array1.Length, array2.Length); } return res; }
/// <summary> /// Operation to add two routes together where /// the second route is just put after the first route. /// </summary> public static Route operator +(Route A, Route B) { if (A == null) return B; else if (B == null) return A; else { Node[] nodes = new Node[A.NumOfNodes + B.NumOfNodes]; A.Points.CopyTo(nodes, 0); B.Points.CopyTo(nodes, A.NumOfNodes); Route res = new Route(nodes, A.GetVehicle(0)); res.Length = A.Length + B.length; res.Time = A.Time + B.Time; Vehicle prev = res.GetVehicle(0); Vehicle cur; for (int i = 1; i < A.NumOfNodes; i++) { cur = A.GetVehicle(i); if (prev != cur) res.SetVehicle(cur, i); prev = cur; } for (int i = 0; i < B.NumOfNodes; i++) { cur = B.GetVehicle(i); if (prev != cur) res.SetVehicle(cur, i + A.NumOfNodes); prev = cur; } return res; } }
public Route(Node[] nodes, Vehicle v) { this.route = nodes; this.vehicles = new SortedList<int, Vehicle>(); vehicles.Add(0, v); }
public Location(Node n, LocationType type) : base(n.Longitude, n.Latitude, n.ID) { this.type = type; }
/// <summary> /// Returns the distance between two nodes A and B in kilometre using the great-circle distance. /// Documentation: http://en.wikipedia.org/wiki/Great-circle_distance /// </summary> public static double Distance(Node A, Node B) { double labda1 = A.Longitude * TO_RADIANS; double phi1 = A.Latitude * TO_RADIANS; double labda2 = B.Longitude * TO_RADIANS; double phi2 = B.Latitude * TO_RADIANS; return EARTH_RADIUS * Math.Acos(Math.Sin(phi1) * Math.Sin(phi2) + Math.Cos(phi1) * Math.Cos(phi2) * Math.Cos(labda2 - labda1)); }
public Way(Node n1, Node n2) { Start = n1; End = n2; }
/// <summary> /// Calculates the middle (Centroid) of a polygon with points 'nodes'. /// Documentation: http://en.wikipedia.org/wiki/Centroid /// </summary> public Coordinate FindCentroid(List<long> nodeIDs) { double Area = 0; Node[] nodes = new Node[nodeIDs.Count]; nodes[0] = GetNode(nodeIDs[0]); for (int i = 0; i < nodes.Length - 1; i++) { nodes[i + 1] = GetNode(nodeIDs[i + 1]); Area += nodes[i].Longitude * nodes[i + 1].Latitude - nodes[i + 1].Longitude * nodes[i].Latitude; } Area += nodes[nodes.Length - 1].Longitude * nodes[0].Latitude - nodes[0].Longitude * nodes[nodes.Length - 1].Latitude; Area /= 2; double longitude = 0; double latitude = 0; double a; for (int i = 0; i < nodes.Length - 1; i++) { a = nodes[i].Longitude * nodes[i + 1].Latitude - nodes[i + 1].Longitude * nodes[i].Latitude; longitude += (nodes[i].Longitude + nodes[i + 1].Longitude) * a; latitude += (nodes[i].Latitude + nodes[i + 1].Latitude) * a; } a = nodes[nodes.Length - 1].Longitude * nodes[0].Latitude - nodes[0].Longitude * nodes[nodes.Length - 1].Latitude; longitude += (nodes[nodes.Length - 1].Longitude + nodes[0].Longitude) * a; latitude += (nodes[nodes.Length - 1].Latitude + nodes[0].Latitude) * a; longitude /= 6 * Area; latitude /= 6 * Area; return new Coordinate(longitude, latitude); }
/* * Returns the node with the given id, either from cache * or from disk. * Returns null if the node is not found on either one. */ public Node GetNode(long id) { // First check if we have it in the cache Node n = nodeCache.Get(id); if(n != null) return n; if(datasource == null) throw new Exception("Node not found"); // At what position in the file would our node be? RBNode<long> node = nodeBlockIndexes.GetNode(id); // That is the node that would be in the tree if the id // was in the tree, which it prolly isn't long blockToRead = node.Content; // The id was not in the tree, so we need to find the first // node with a lower id than that. Remember, the node has no // children. if(blockToRead == 0) { if (node.Parent != null) node = node.Parent; while (node.ID > id) if (node.Parent != null) node = node.Parent; else break; blockToRead = node.Content; } PrimitiveBlock pb = cache.Get(blockToRead); if(pb == null) { // Now, check the needed block from the disk FileStream file = new FileStream(datasource, FileMode.Open, FileAccess.Read, FileShare.Read, 8600); file.Position = blockToRead; BlobHeader blobHead = readBlobHeader(file); byte[] blockData = readBlockData(file, blobHead.Datasize); pb = PrimitiveBlock.ParseFrom(blockData); file.Close(); cache.Add(blockToRead, pb); } for(int i = 0; i < pb.PrimitivegroupCount; i++) { PrimitiveGroup pg = pb.GetPrimitivegroup(i); if(pg.HasDense) { long tmpid = 0; double latitude = 0; double longitude = 0; for(int j = 0; j < pg.Dense.IdCount; j++) { tmpid += pg.Dense.GetId(j); latitude += .000000001 * (pb.LatOffset + pb.Granularity * pg.Dense.GetLat(j)); longitude += .000000001 * (pb.LonOffset + pb.Granularity * pg.Dense.GetLon(j)); if (tmpid == id) { n = new Node(longitude, latitude, id); nodeCache.Insert(id, n); return n; } } } } n = new Node(0, 0, id); nodeCache.Insert(id, n); return n; }
public MyVehicle(Vehicle vehicle, Node location) { this.vehicle = vehicle; this.location = location; }
/// <summary> /// Adds a mapIcon to the map at the node 'location'. /// </summary> public void SetMapIcon(IconType type, Node location, MapDragButton button) { MapIcon newIcon; switch (type) { case IconType.Start: if (!isCalculatingRoute) { MapIcon start = GetMapIcon(IconType.Start); if (start != null) icons.Remove(start); newIcon = new MapIcon(IconType.Start, this, button); newIcon.Location = location; icons.Add(newIcon); CalcRoute(); MapIconPlaced(this, new MapDragEventArgs(button)); } break; case IconType.End: if (!isCalculatingRoute) { MapIcon end = GetMapIcon(IconType.End); if (end != null) icons.Remove(end); newIcon = new MapIcon(IconType.End, this, button); newIcon.Location = location; icons.Add(newIcon); CalcRoute(); MapIconPlaced(this, new MapDragEventArgs(button)); } break; case IconType.Via: newIcon = new MapIcon(IconType.Via, this, button); newIcon.Location = location; icons.Add(newIcon); CalcRoute(); MapIconPlaced(this, new MapDragEventArgs(button)); break; } }
/// <summary> /// Returns a Point in pixel-coordinates from a Node with /// geological coordinates. The Point is in coordinates for the /// entire map so it should be converted to coordinates for the /// specific tile that is drawn. /// </summary> private Point nodeToTilePoint(BBox box, Bitmap tile, Node node) { Coordinate c = new Coordinate(node.Longitude, node.Latitude); Projection p = new Projection(box.Width, tile.Width, new Coordinate(box.XMin, box.YMax)); return p.CoordToPoint(c); }