public IWallTracingStrategy GoToNextVertex(out MapVector foundVertex) { do { _vertexPosition.x += 1; if (_fields[_vertexPosition.z - 1, _vertexPosition.x] == FieldType.Inaccessible ) // we've lost touch of the wall (inaccessible is the interior) { foundVertex = _vertexPosition; return(new DownWallTracingStrategy( new MapVector(_vertexPosition.x, _vertexPosition.z - 1), _fields)); } if (_fields[_vertexPosition.z, _vertexPosition.x] != FieldType.Inaccessible ) // we've hit a wall with a face { foundVertex = _vertexPosition; return(new UpWallTracingStrategy(new MapVector(_vertexPosition.x - 1, _vertexPosition.z), _fields)); } } while (_vertexPosition.x < 128); throw new ApplicationException("Area is not inside a provided space."); }
/// <summary> /// Gets a given tile at a specific zoom level. /// Checks the current caching provider for the file. If the file is present within /// the caching provider, a stream to it's contents is returned. This stream should be disposed as soon as the /// data from it is fully used. /// /// If the tile is not present within the tile cache, it is checked if the tile is currently being downloaded. /// If not so, a download job to download the tile is enqueued. /// /// In both cases - tile being downloaded or not - null is returned. /// </summary> /// <param name="zoom">The zoom level to get the tile from.</param> /// <param name="tile">The tile X/Y coordinates.</param> /// <returns>A stream to the tiles contents or null.</returns> public Stream GetTile(int zoom, MapVector tile) { TileDescriptor desc = new TileDescriptor(zoom, tile); if (_cachingProvider.HasTile(desc)) { return(_cachingProvider.GetTile(desc)); } else if (!_enqueuedTiles.Contains(desc)) { DownloadJob job = new DownloadJob(_mapProvider.GetTileUrl(GetNextServer(), desc.Zoom, desc.Tile), desc); job.OnFinished += Job_OnFinished; job.OnFailed += Job_OnFailed; try { _downloadMutex.WaitOne(); _enqueuedTiles.Add(desc); } finally { _downloadMutex.ReleaseMutex(); } _download.AddJob(job); } return(null); }
/// <summary> /// Draw a solid box with a black outline. /// </summary> /// <param name="m"></param> /// <param name="left"></param> /// <param name="bot"></param> /// <param name="cell"></param> /// <param name="color"></param> private void DrawSolidRectangle(MapVector m, float left, float bot, float cell, Color color) { var x = left + m.x * cell; var z = bot + m.z * cell; Handles.DrawSolidRectangleWithOutline( new Vector3[] { new Vector3(x, 0, z), new Vector3(x + cell, 0, z), new Vector3(x + cell, 0, z + cell), new Vector3(x, 0, z + cell) }, color, Color.black); }
public BitmapSize GetOffsetFromCoordinates(MapPoint coordinates, BitmapSize totalSize, double mapZoom) { // double correctionScale = Math.Pow(2.0, mapZoom - _tile.Zoom); double xScale = (double)_bounds.Width / _square.Size.LongitudeOffset;// *correctionScale; MapVector leftTopOffset = new MapVector(_square.LeftTop.Latitude - coordinates.Latitude, coordinates.Longitude - _square.LeftTop.Longitude); int x = (int)Math.Round(/*(double)totalSize.Width / 2.0 */ leftTopOffset.LongitudeOffset * xScale); double yTiles = CoordinatesHelper.GetTilesFromLatitude(_square.LeftTop.Latitude, _tile.Zoom) - CoordinatesHelper.GetTilesFromLatitude(coordinates.Latitude, _tile.Zoom); int y = (int)Math.Round(/*(double)totalSize.Height / 2.0*/ -(double)_bounds.Height * yTiles);// * correctionScale); return(new BitmapSize(x, y)); }
public UcSectionImage(MapInfo theMapInfo, MapSection section) { InitializeComponent(); this.theMapInfo = theMapInfo; Section = section; VectorHeadToTail = new MapVector(Section.TailAddress.Position.X - Section.HeadAddress.Position.X, Section.TailAddress.Position.Y - Section.HeadAddress.Position.Y); Id = Section.Id; label1.Text = Id; labelSize = label1.Size; DrawSectionImage(bluePen); SetupShowSectionInfo(); }
private BitmapRect GetSquareBitmapBounds(MapTile tile) { MapSquare square = tile.GetActualSquare(); double correctionScale = Math.Pow(2.0, _zoom - tile.Zoom); MapVector leftTopOffset = new MapVector(square.LeftTop.Latitude - _center.Latitude, square.LeftTop.Longitude - _center.Longitude); MapVector squareSize = square.Size; double xScale = (double)_tileSize.Width / squareSize.LongitudeOffset * correctionScale; int x = (int)Math.Round((double)_totalSize.Width / 2.0 + leftTopOffset.LongitudeOffset * xScale); double yTiles = CoordinatesHelper.GetTilesFromLatitude(square.LeftTop.Latitude, tile.Zoom) - CoordinatesHelper.GetTilesFromLatitude(_center.Latitude, tile.Zoom); int y = (int)Math.Round((double)_totalSize.Height / 2.0 + (double)_tileSize.Height * yTiles * correctionScale); return(new BitmapRect(x, y, (int)Math.Ceiling(_tileSize.Width * correctionScale), (int)Math.Ceiling(_tileSize.Height * correctionScale))); }
/// <summary> /// Transforms a Point from the MapCoordinates system to the GeoCoordinates system. /// </summary> /// <param name="mapVector">A Point within the MapCoordinates system.</param> /// <returns>The corresponding point in the GeoCoordinates system.</returns> public MapPointLatLon MapPointToLatLon(MapVector mapVector) { if (mapVector.X > MapCoordinatesWidth || mapVector.Y > MapCoordinatesHeight) { throw new ArgumentException("Coordinates of the tile are out of map size.", nameof(mapVector)); } double projectedlon = ((double)mapVector.X / MapCoordinatesWidth) * 360 - 180; double projectedlat = (-2 * ((double)mapVector.Y / MapCoordinatesHeight) + 1) * 180; return(Provider.Projection.FromProjection(new MapPointLatLon() { Lat = projectedlat, Lon = projectedlon })); }
/// <summary> /// Zoom the map around the given view coordinate within the displayed map. /// </summary> /// <param name="zoom">The new zoom level</param> /// <param name="mousePos">The point within the view coordinate system to zoom the map around</param> private void SetZoomMouse(int zoom, MapVector mousePos) { MapVectorD mouse = new MapVectorD(mousePos); MapVectorD middle = new MapVectorD() { X = _map.ViewBounds.Width / 2.0, Y = _map.ViewBounds.Height / 2.0 }; MapVectorD offset = middle - mouse; // Vector from mouse position to middle position // 1. move the map to the position the mouse is at _map.Position = _map.ViewPointToLatLon(mouse); // 2. zoom the map _map.Zoom = zoom; // 3. move the map back about the same amount we move it in (1.) _map.Position = _map.ViewPointToLatLon(middle + offset); // Plus here because the offset is mouse -> middle }
/// <summary> /// Returns the Lat/Lon geo-coordinates for a tile /// </summary> /// <param name="zoom">The zoom level the tile is at</param> /// <param name="tile">The tile coordinates in X/Y</param> /// <returns>The Geo-Point the top-left corner of the tile is at.</returns> public MapPointLatLon GetPointForTile(int zoom, MapVector tile) { double n = GetTileCount(zoom); if (tile.X > n || tile.Y > n) { throw new ArgumentException("Coordinates of the tile are out of the given zoom's range.", nameof(tile)); } double projectedlon = (tile.X / n) * 360 - 180; double projectedlat = (-2 * (tile.Y / n) + 1) * 180; return(_projection.FromProjection(new MapPointLatLon() { Lat = projectedlat, Lon = projectedlon })); }
public List <MapVector> GetRegion(MapVector start, MapVector end) { var list = new List <MapVector>(); MapVector s = new MapVector(MathfExtender.MinInt(start.x, end.x), MathfExtender.MinInt(start.z, end.z)); MapVector e = new MapVector(MathfExtender.MaxInt(start.x, end.x), MathfExtender.MaxInt(start.z, end.z)); for (var x = s.x; x <= e.x; x++) { for (var z = s.z; z <= e.z; z++) { list.Add(new MapVector(x, z)); } } return(list); }
public MapPoint?MoveCenterForView(float xOffset, float yOffset) { BitmapTile tile = _collection.FirstOrDefault() ?? EnumerateBitmapTiles().FirstOrDefault(); if (tile == null || tile.Bounds.Width * tile.Bounds.Height == 0) { return(null); } double correctionScale = Math.Pow(2.0, _zoom - tile.Tile.Zoom); MapVector size = tile.Tile.GetActualSquare().Size; double xScale = size.LongitudeOffset / (double)_tileSize.Width / correctionScale; double yScale = size.LatitudeOffset / (double)_tileSize.Height / correctionScale; double longitudeOffset = xScale * xOffset; double latitudeOffset = yScale * yOffset; _center = new MapPoint(_center.Latitude - latitudeOffset, _center.Longitude + longitudeOffset); return(_center); }
/// <summary> /// Transforms a point from the GeoCoordinates system to the MapCoordinates system. /// </summary> /// <param name="pt">A Point within the GeoCoordinates system.</param> /// <returns>The corresponding point within the MapCoordinates system.</returns> public MapVector LatLonToMapPoint(MapPointLatLon pt) { MapPointLatLon proj = Provider.Projection.ToProjection(pt); MapVector newP = new MapVector(); double shiftedLon = (1 + (proj.Lon / 180)) / 2; double shiftedLat = (1 - (proj.Lat / 180)) / 2; int x = (int)Math.Floor(MapCoordinatesWidth * shiftedLon); int y = (int)Math.Floor(MapCoordinatesHeight * shiftedLat); newP.X = x; newP.Y = y; return(newP); }
public static Vector2 ToVector2(this MapVector vect) { return(new Vector2((float)vect.X, (float)vect.Y)); }
public List <TileDrawInfo> GetDrawTiles() { List <TileDrawInfo> info = new List <TileDrawInfo>(); // 1. Get center point MapCoordinates MapVector centerMapVector = LatLonToMapPoint(Position); // 2. Calculate offset from center point to topleft point in map coordinates int topLeftXOffset = (int)((ViewBounds.Width / 2.0) / CoordinateScale); int topLeftYOffset = (int)((ViewBounds.Height / 2.0) / CoordinateScale); // 3. Calculate the top left point in map coordinates MapVector topLeftMapVector = new MapVector() { // real a mod b: // a mod b = (a % b + b) % b // https://de.wikipedia.org/wiki/Division_mit_Rest#Modulo X = (((centerMapVector.X - topLeftXOffset) % MapCoordinatesWidth) + MapCoordinatesWidth) % MapCoordinatesWidth, Y = (((centerMapVector.Y - topLeftYOffset) % MapCoordinatesHeight) + MapCoordinatesHeight) % MapCoordinatesHeight }; // 4. Calculate Tile X/Y directly from Map Coordiantes MapVector tileCoord = new MapVector() { X = (int)Math.Floor(topLeftMapVector.X / (Provider.TileSize / CoordinateScale)), Y = (int)Math.Floor(topLeftMapVector.Y / (Provider.TileSize / CoordinateScale)) }; // 5. Calculate the Top-Left point of the top-left tile //PointXY tileMapVector = LatLonToMapPoint(Provider.GetPointForTile(Zoom, tileCoord)); MapVector tileMapVector = new MapVector() { X = (int)(tileCoord.X * (Provider.TileSize / CoordinateScale)), Y = (int)(tileCoord.Y * (Provider.TileSize / CoordinateScale)) }; // 6. Get the offset of the top-left-point of the top-left-tile to the top-left point of the map // So we know if it is outside of the viewable port. MapVector offset = (tileMapVector - topLeftMapVector) * CoordinateScale; // 7. Create a rectangle for the top-left tile MapRectangle imgRect = new MapRectangle(offset.X, offset.Y, Provider.TileSize, Provider.TileSize); // 8. The top-left tile TileDescriptor descriptor = new TileDescriptor(Zoom, tileCoord); // 9. Now iterate over all viewable tiles and add them to the list // Handling the source and destination rectangles is done by special functions. int currentTileY = descriptor.Tile.Y; int currentTileX = descriptor.Tile.X; int currentRectY = imgRect.Y; int currentRectX = imgRect.X; int tileCount = Provider.GetTileCount(Zoom); while (currentRectX < ViewBounds.Width) { while (currentRectY < ViewBounds.Height) { TileDescriptor desc = new TileDescriptor(descriptor.Zoom, currentTileX, currentTileY); // 10. Create rectangle of the "full" tile, might lap over the borders of the viewport, i.e. // having negative offsets here. MapRectangle cRect = new MapRectangle(currentRectX, currentRectY, Provider.TileSize, Provider.TileSize); // 11. Get the part of the tile that is being rendered. MapRectangle tileSrcRect = GetSourceRectangle(cRect); // 12. Get the position and the size in the viewport where the tile will be rendered. MapRectangle viewDstRect = GetDestRectangle(cRect); TileDrawInfo i = new TileDrawInfo(); i.Tile = new TileDescriptor(Zoom, currentTileX, currentTileY); i.SourceRectangle = tileSrcRect; i.DestinationRectangle = viewDstRect; info.Add(i); currentRectY += Provider.TileSize; currentTileY = (currentTileY + 1) % tileCount; } currentRectY = imgRect.Y; currentTileY = descriptor.Tile.Y; currentTileX = (currentTileX + 1) % tileCount; currentRectX += Provider.TileSize; } return(info); }
public MapPointLatLon ViewPointToLatLon(MapVector viewPoint) => ViewPointToLatLon(new MapVectorD(viewPoint));
public MapVector ViewPointToMapPoint(MapVector viewPoint) => ViewPointToMapPoint(new MapVectorD(viewPoint));
private void RecieveInput(SceneView view) { // Disables all standard input HandleUtility.AddDefaultControl(GUIUtility.GetControlID(FocusType.Passive)); view.orthographic = true; // Get basic variables float bot = -(instance.width / 2) * instance.cellsize; float left = -(instance.length / 2) * instance.cellsize; float cell = instance.cellsize; Event e = Event.current; // Mouse if (e.isMouse) { // Only works in ortho mode. This is why we force it. Vector3 mousePosition = HandleUtility.GUIPointToWorldRay(e.mousePosition).origin; // Left click down and drag if (e.type == EventType.MouseDown || e.type == EventType.MouseDrag) { // Translate mouse position to cell position var x = Mathf.FloorToInt((mousePosition.x - left) / cell); var z = Mathf.FloorToInt((mousePosition.z - bot) / cell); // Check if within zone if (instance.WithinBox(x, z)) { // Click if (e.type == EventType.MouseDown) { dragActiveBox = true; dragSetState = instance.GetCellType(instance.GetIndex(x, z), (int)selectedCellType) ? 0 : (int)selectedCellType; dragStartIndex = new MapVector(x, z); dragEndIndex = new MapVector(x, z); } // Drag else { dragEndIndex = new MapVector(x, z); } e.Use(); view.Repaint(); } } // Left click up else if (e.type == EventType.MouseUp) { if (dragActiveBox) { // Set all blocks foreach (var k in instance.GetRegion(dragStartIndex, dragEndIndex)) { instance.SetCellType(instance.GetIndex(k.x, k.z), dragSetState); } e.Use(); } dragActiveBox = false; view.Repaint(); } } }
/// <summary> /// Handles the logic of Dragging/Dropping/Zooming the map. /// This is basically said the logic handler of the control. /// It is called quite a lot of times, the delta of two calls may be calculated out of the passed GameTime parameter. /// </summary> /// <param name="time">The time passed since the game started.</param> public void Update(GameTime time, InputArgs input) { // Clean up icon texture cache... var keys = _markerTextures.Keys; foreach (string key in keys) { if (Markers.All(m => m.TextureIdentifier != key)) { _markerTextures[key].Dispose(); _markerTextures.Remove(key); } } // drag&drop handling MouseState currentState = input.MouseState; MapVector mousePos = new MapVector() { X = currentState.X, Y = currentState.Y }; if (_dragging && CanMove) { MapVector oldVector = new MapVector() { X = _oldMouseState.X, Y = _oldMouseState.Y }; MapVector offset = (oldVector - mousePos) / _map.CoordinateScale; MapVector centerMapVector = _map.LatLonToMapPoint(_map.Position); MapVector newCenterMapVector = centerMapVector + offset; // real a mod b: // a mod b = (a % b + b) % b // https://de.wikipedia.org/wiki/Division_mit_Rest#Modulo // We do this to allow scrollen over the maps borders. newCenterMapVector.X = ((newCenterMapVector.X % _map.MapCoordinatesWidth) + _map.MapCoordinatesWidth) % _map.MapCoordinatesWidth; newCenterMapVector.Y = ((newCenterMapVector.Y % _map.MapCoordinatesHeight) + _map.MapCoordinatesHeight) % _map.MapCoordinatesHeight; MapPointLatLon newCenterGeoPoint = _map.MapPointToLatLon(newCenterMapVector); _map.Position = newCenterGeoPoint; OnMoved?.Invoke(this, _map.Position); } int wheel = _oldMouseState.ScrollWheelValue - currentState.ScrollWheelValue; bool zoom = false; int newZoom = 0; if (wheel < 0) { if (_map.Zoom < _map.MaxZoom) { zoom = true; newZoom = _map.Zoom + 1; } } else if (wheel > 0) { if (_map.Zoom > _map.MinZoom) { zoom = true; newZoom = _map.Zoom - 1; } } if (zoom && CanZoom) { switch (ZoomMode) { case ZoomingType.Center: SetZoomCenter(newZoom); break; case ZoomingType.Mouse: MapVector viewPos = mousePos - _map.ViewBounds.Location; SetZoomMouse(newZoom, viewPos); break; } OnZoomed?.Invoke(this, _map.Zoom); } if ((_oldMouseState.LeftButton == ButtonState.Pressed) && currentState.LeftButton == ButtonState.Released) { // Mouse up _dragging = false; } else if ((_oldMouseState.LeftButton == ButtonState.Released) && currentState.LeftButton == ButtonState.Pressed) { // Mouse down _dragging = true; } if (_oldMouseState.RightButton == ButtonState.Pressed && currentState.RightButton == ButtonState.Released) { OnRightClick?.Invoke(this, _map.ViewPointToLatLon(mousePos)); } _oldMouseState = currentState; }
public UpWallTracingStrategy(MapVector fieldPosition, FieldType[,] fields) { _fieldPosition = fieldPosition; _fields = fields; }
public MapChunk(int x, int y) { MapVector = new MapVector(x, y); Weight = 1; }
public RightWallTracingStrategy(MapVector vertexVertexPosition, FieldType[,] fields) { _vertexPosition = vertexVertexPosition; _fields = fields; }
public string GetTileUrl(int server, int zoom, MapVector tile) { return($"http://{(server < _servers.Length ? _servers[server] : _servers[0])}.tile.openstreetmap.de/tiles/osmde/{zoom}/{tile.X}/{tile.Y}.png"); }
// Convert the mapVector to global unity 2d position. public Vector2 GetGlobalPosition(MapVector vector) { return((Vector2)transform.position + (Vector2)vector); }