/// <summary> /// Converts into a basic entry. /// </summary> /// <param name="id"></param> /// <param name="icon"></param> /// <param name="styleId"></param> /// <returns></returns> internal static Icon2DEntry From(uint id, Icon2D icon, ushort styleId) { Icon2DEntry entry = new Icon2DEntry(); entry.Id = id; entry.X = icon.X; entry.Y = icon.Y; entry.StyleId = styleId; return(entry); }
/// <summary> /// Extracts style information. /// </summary> /// <param name="icon"></param> /// <returns></returns> public static Icon2DStyle From(Icon2D icon, int layer) { Icon2DStyle newStyle = new Icon2DStyle(); newStyle.Image = icon.Image; newStyle.MaxZoom = icon.MaxZoom; newStyle.MinZoom = icon.MinZoom; newStyle.Layer = layer; return(newStyle); }
/// <summary> /// Converts this basic entry into a scene object. /// </summary> /// <param name="style"></param> /// <returns></returns> internal Icon2D To(Icon2DStyle style) { Icon2D icon = new Icon2D(); icon.Image = style.Image; icon.MaxZoom = style.MaxZoom; icon.MinZoom = style.MinZoom; icon.X = this.X; icon.Y = this.Y; return(icon); }
/// <summary> /// Adds a new style and returns it's index. /// </summary> /// <param name="icon"></param> /// <param name="layer"></param> /// <returns></returns> public ushort AddStyle(Icon2D icon, int layer) { Icon2DStyle newStyle = Icon2DStyle.From(icon, layer); int indexOf = this.IconStyles.IndexOf(newStyle); if (indexOf < 0) { // the style is not found yet. indexOf = this.IconStyles.Count; this.IconStyles.Add(newStyle); } return((ushort)indexOf); }
public override IEnumerable <Primitive2D> Get(float zoomFactor, View2D view) { var result = new List <Primitive2D>(); var viewBox = view.OuterBox; var box = new GeoCoordinateBox(_projection.ToGeoCoordinates(viewBox.Min[0], viewBox.Min[1]), _projection.ToGeoCoordinates(viewBox.Max[0], viewBox.Max[1])); var point = _projection.ToPixel(box.Center.Latitude, box.Center.Longitude); var p = new Icon2D(point[0], point[1], Create("")); p.ToolTip = "Подсказка"; result.Add(p); return(result); }
/// <summary> /// Renders the primities for the given scene. /// </summary> /// <param name="target"></param> /// <param name="view"></param> /// <param name="zoomFactor"></param> /// <param name="primitives"></param> private bool RenderPrimitives(Target2DWrapper <TTarget> target, View2D view, float zoomFactor, IEnumerable <Primitive2D> primitives) { try { // calculate current simplification epsilon. double epsilon = Scene2D.CalculateSimplificationEpsilon(new WebMercator(), zoomFactor); // loop over all primitives in the scene. int simplifiedLines = 0; int droppedLines = 0; foreach (Primitive2D primitive in primitives) { // the primitive is visible. if (_cancelFlag) { return(false); // stop rendering on cancel and return false for an incomplete rendering. } if (primitive == null) { continue; } double[] x, y; switch (primitive.Primitive2DType) { case Primitive2DType.Line2D: Line2D line = (Line2D)primitive; x = line.X; y = line.Y; if (x.Length > 4 && line.MaxZoom > zoomFactor * 2 && line.MaxZoom < 512) { // try and simplify. double[][] simplified = OsmSharp.Math.Algorithms.SimplifyCurve.Simplify(new double[][] { x, y }, epsilon); if (simplified[0].Length < line.X.Length) { simplifiedLines++; x = simplified[0]; y = simplified[1]; } double distance = epsilon * 2; if (simplified[0].Length == 2) { // check if the simplified version is smaller than epsilon. distance = System.Math.Sqrt( System.Math.Pow((simplified[0][0] - simplified[0][1]), 2) + System.Math.Pow((simplified[1][0] - simplified[1][1]), 2)); } if (distance < epsilon) { droppedLines++; continue; } } this.DrawLine(target, x, y, line.Color, this.FromPixels(target, view, line.Width), line.LineJoin, line.Dashes); break; case Primitive2DType.Polygon2D: Polygon2D polygon = (Polygon2D)primitive; x = polygon.X; y = polygon.Y; //if (x.Length > 4 && polygon.MaxZoom > zoomFactor * 2 && polygon.MaxZoom < 512) //{ // try and simplify. // double[][] simplified = OsmSharp.Math.Algorithms.SimplifyCurve.Simplify(new double[][] { x, y }, // epsilon); // if (simplified[0].Length < polygon.X.Length) // { // simplifiedLines++; // x = simplified[0]; // y = simplified[1]; // } // double distance = epsilon * 2; // if (simplified[0].Length == 2) // { // check if the simplified version is smaller than epsilon. // distance = System.Math.Sqrt( // System.Math.Pow((simplified[0][0] - simplified[0][1]), 2) + // System.Math.Pow((simplified[1][0] - simplified[1][1]), 2)); // } // //if (distance < epsilon) // //{ // // droppedLines++; // // continue; // //} //} this.DrawPolygon(target, x, y, polygon.Color, this.FromPixels(target, view, polygon.Width), polygon.Fill); break; case Primitive2DType.LineText2D: LineText2D lineText = (LineText2D)primitive; this.DrawLineText(target, lineText.X, lineText.Y, lineText.Text, lineText.Color, this.FromPixels(target, view, lineText.Size), lineText.HaloColor, lineText.HaloRadius, lineText.Font); break; case Primitive2DType.Point2D: Point2D point = (Point2D)primitive; this.DrawPoint(target, point.X, point.Y, point.Color, this.FromPixels(target, view, point.Size)); break; case Primitive2DType.Icon2D: Icon2D icon = (Icon2D)primitive; this.DrawIcon(target, icon.X, icon.Y, icon.Image); break; case Primitive2DType.ImageTilted2D: ImageTilted2D imageTilted = (ImageTilted2D)primitive; this.DrawImage(target, imageTilted.Bounds, imageTilted.NativeImage); break; case Primitive2DType.Image2D: Image2D image = (Image2D)primitive; this.DrawImage(target, image.Left, image.Top, image.Right, image.Bottom, image.NativeImage); break; case Primitive2DType.Text2D: Text2D text = (Text2D)primitive; this.DrawText(target, text.X, text.Y, text.Text, text.Color, this.FromPixels(target, view, text.Size), text.HaloColor, text.HaloRadius, text.Font); break; } } return(true); } catch (Exception ex) { OsmSharp.Logging.Log.TraceEvent("Renderer2D", OsmSharp.Logging.TraceEventType.Error, ex.Message); throw ex; } }
/// <summary> /// Sets the style information. /// </summary> /// <param name="icon"></param> public void Set(Icon2D icon) { icon.Image = this.Image; icon.MaxZoom = this.MaxZoom; icon.MinZoom = this.MinZoom; }
/// <summary> /// Deserializes the given leaf. /// </summary> /// <param name="typeModel"></param> /// <param name="data"></param> /// <param name="boxes"></param> /// <returns></returns> protected override List <Primitive2D> DeSerialize(RuntimeTypeModel typeModel, byte[] data, out List <BoxF2D> boxes) { if (_compressed) { // decompress if needed. data = GZipStream.UncompressBuffer(data); } List <Primitive2D> dataLists = new List <Primitive2D>(); boxes = new List <BoxF2D>(); int scaleFactor = _scaleFactor; // Assume the following stuff already exists in the current scene: // - ZoomRanges // - Styles // deserialize the leaf data. SceneObjectBlock leafData = typeModel.Deserialize( new MemoryStream(data), null, typeof(SceneObjectBlock)) as SceneObjectBlock; // decode for (int idx = 0; idx < leafData.PointsX.Count; idx++) { leafData.PointsX[idx] = leafData.PointsX[idx] + leafData.PointsXMin; leafData.PointsY[idx] = leafData.PointsY[idx] + leafData.PointsYMin; } // store the next points. bool[] pointsStarts = new bool[leafData.PointsX.Count]; // loop over all points. for (int idx = 0; idx < leafData.PointPointId.Count; idx++) { pointsStarts[leafData.PointPointId[idx]] = true; } // loop over all text-points. for (int idx = 0; idx < leafData.TextPointPointId.Count; idx++) { pointsStarts[leafData.TextPointPointId[idx]] = true; } // loop over all icons. for (int idx = 0; idx < leafData.IconPointId.Count; idx++) { pointsStarts[leafData.IconPointId[idx]] = true; } // loop over all lines. for (int idx = 0; idx < leafData.LinePointsId.Count; idx++) { pointsStarts[leafData.LinePointsId[idx]] = true; } // loop over all polygons. for (int idx = 0; idx < leafData.PolygonPointsId.Count; idx++) { pointsStarts[leafData.PolygonPointsId[idx]] = true; } // loop over all line-texts. for (int idx = 0; idx < leafData.LineTextPointsId.Count; idx++) { pointsStarts[leafData.LineTextPointsId[idx]] = true; } Dictionary <int, int> pointsBoundaries = new Dictionary <int, int>(); int previous = 0; for (int idx = 1; idx < pointsStarts.Length; idx++) { if (pointsStarts[idx]) { // there is a start here. pointsBoundaries[previous] = idx - previous; previous = idx; } } pointsBoundaries[previous] = pointsStarts.Length - previous; // loop over all points. for (int idx = 0; idx < leafData.PointPointId.Count; idx++) { // get properties. int pointId = leafData.PointPointId[idx]; uint styleId = leafData.PointStyleId[idx]; // get point/style/zoomrange. double x = (double)leafData.PointsX[pointId] / (double)scaleFactor; double y = (double)leafData.PointsY[pointId] / (double)scaleFactor; StylePoint style = _index.PointStyles[styleId]; // build the primitive. Point2D point = new Point2D(x, y, style.Color, style.Size); point.Layer = style.Layer; point.MinZoom = style.MinZoom; point.MaxZoom = style.MaxZoom; dataLists.Add(point); boxes.Add(new BoxF2D(new PointF2D(x, y))); } // loop over all text-points. for (int idx = 0; idx < leafData.TextPointPointId.Count; idx++) { // get properties. int pointId = leafData.TextPointPointId[idx]; uint styleId = leafData.TextPointStyleId[idx]; string text = leafData.TextPointText[idx]; // get point/style/zoomrange. float x = (float)leafData.PointsX[pointId] / (float)scaleFactor; float y = (float)leafData.PointsY[pointId] / (float)scaleFactor; StyleText style = _index.TextStyles[styleId]; // build the primitive. Text2D text2D = new Text2D(x, y, text, style.Color, style.Size); text2D.Layer = style.Layer; text2D.HaloColor = style.HaloColor; text2D.HaloRadius = style.HaloRadius; text2D.MinZoom = style.MinZoom; text2D.MaxZoom = style.MaxZoom; dataLists.Add(text2D); boxes.Add(new BoxF2D(new PointF2D(x, y))); } // loop over all icons. for (int idx = 0; idx < leafData.IconPointId.Count; idx++) { // get properties. int pointId = leafData.IconPointId[idx]; uint imageId = leafData.IconImageId[idx]; // get point/style/zoomrange. double x = (double)leafData.PointsX[pointId] / (double)scaleFactor; double y = (double)leafData.PointsY[pointId] / (double)scaleFactor; byte[] image = _index.IconImage[(int)imageId]; // build the primitive. Icon2D icon = new Icon2D(x, y, image); icon.Layer = 0; // TODO: layer and zoom level. style.MinZoom, style.MaxZoom dataLists.Add(icon); boxes.Add(new BoxF2D(new PointF2D(x, y))); } // loop over all lines. for (int idx = 0; idx < leafData.LinePointsId.Count; idx++) { // get properties. int pointsId = leafData.LinePointsId[idx]; uint styleId = leafData.LineStyleId[idx]; // get points/style/zoomrange. int pointsCount = pointsBoundaries[pointsId]; double[] x = leafData.PointsX.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); double[] y = leafData.PointsY.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); StyleLine style = _index.LineStyles[styleId]; // build the primitive. Line2D line = new Line2D(x, y, style.Color, style.Width, style.LineJoin, style.Dashes); line.Layer = style.Layer; line.MinZoom = style.MinZoom; line.MaxZoom = style.MaxZoom; dataLists.Add(line); boxes.Add(new BoxF2D(x, y)); } // loop over all polygons. for (int idx = 0; idx < leafData.PolygonPointsId.Count; idx++) { // get properties. int pointsId = leafData.PolygonPointsId[idx]; uint styleId = leafData.PolygonStyleId[idx]; // get points/style/zoomrange. int pointsCount = pointsBoundaries[pointsId]; double[] x = leafData.PointsX.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); double[] y = leafData.PointsY.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); StylePolygon style = _index.PolygonStyles[styleId]; // build the primitive. Polygon2D polygon = new Polygon2D(x, y, style.Color, style.Width, style.Fill); polygon.Layer = style.Layer; polygon.MaxZoom = style.MaxZoom; polygon.MinZoom = style.MinZoom; dataLists.Add(polygon); boxes.Add(new BoxF2D(x, y)); } // loop over all line-texts. for (int idx = 0; idx < leafData.LineTextPointsId.Count; idx++) { // get properties. int pointsId = leafData.LineTextPointsId[idx]; uint styleId = leafData.LineTextStyleId[idx]; string text = leafData.LineTextText[idx]; // get points/style/zoomrange. int pointsCount = pointsBoundaries[pointsId]; double[] x = leafData.PointsX.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); double[] y = leafData.PointsY.GetRange(pointsId, pointsCount).ConvertFromLongArray(scaleFactor); StyleText style = _index.TextStyles[styleId]; // build the primitive. LineText2D lineText = new LineText2D(x, y, style.Color, style.Size, text); lineText.Layer = style.Layer; lineText.Font = style.Font; lineText.HaloColor = style.HaloColor; lineText.HaloRadius = style.HaloRadius; lineText.MinZoom = style.MinZoom; lineText.MaxZoom = style.MaxZoom; dataLists.Add(lineText); boxes.Add(new BoxF2D(x, y)); } return(dataLists); }
/// <summary> /// Serializes the actual data. /// </summary> /// <param name="typeModel"></param> /// <param name="data"></param> /// <param name="boxes"></param> /// <returns></returns> protected override byte[] Serialize(RuntimeTypeModel typeModel, List <Scene2DEntry> data, List <BoxF2D> boxes) { var icons = new List <Icon2DEntry>(); var images = new List <Image2DEntry>(); var lines = new List <Line2DEntry>(); var points = new List <Point2DEntry>(); var polygons = new List <Polygon2DEntry>(); var texts = new List <Text2DEntry>(); var lineTexts = new List <LineText2DEntry>(); // build the collection object. var collection = new PrimitivesCollection(); for (int idx = 0; idx < data.Count; idx++) { IScene2DPrimitive primitive = data[idx].Scene2DPrimitive; if (primitive is Icon2D) { Icon2D icon = primitive as Icon2D; icons.Add(Icon2DEntry.From(data[idx].Id, icon, _styleIndex.AddStyle(icon, data[idx].Layer))); } else if (primitive is Image2D) { Image2D image = primitive as Image2D; images.Add(Image2DEntry.From(data[idx].Id, image, _styleIndex.AddStyle(image, data[idx].Layer))); } else if (primitive is Line2D) { Line2D line = primitive as Line2D; lines.Add(Line2DEntry.From(data[idx].Id, line, _styleIndex.AddStyle(line, data[idx].Layer))); } else if (primitive is Point2D) { Point2D point = primitive as Point2D; points.Add(Point2DEntry.From(data[idx].Id, point, _styleIndex.AddStyle(point, data[idx].Layer))); } else if (primitive is Polygon2D) { Polygon2D polygon = primitive as Polygon2D; polygons.Add(Polygon2DEntry.From(data[idx].Id, polygon, _styleIndex.AddStyle(polygon, data[idx].Layer))); } else if (primitive is Text2D) { Text2D text = primitive as Text2D; texts.Add(Text2DEntry.From(data[idx].Id, text, _styleIndex.AddStyle(text, data[idx].Layer))); } else if (primitive is LineText2D) { LineText2D lineText = primitive as LineText2D; lineTexts.Add(LineText2DEntry.From(data[idx].Id, lineText, _styleIndex.AddStyle(lineText, data[idx].Layer))); } else { throw new Exception("Primitive type not supported by serializer."); } } collection.Icons = icons.ToArray(); collection.Images = images.ToArray(); collection.Lines = lines.ToArray(); collection.Points = points.ToArray(); collection.Polygons = polygons.ToArray(); collection.Texts = texts.ToArray(); collection.LineTexts = lineTexts.ToArray(); // create the memory stream. var stream = new MemoryStream(); typeModel.Serialize(stream, collection); if (!_compress) { return(stream.ToArray()); } return(GZipStream.CompressBuffer(stream.ToArray())); }
/// <summary> /// Deserializes the actual data. /// </summary> /// <param name="typeModel"></param> /// <param name="data"></param> /// <param name="boxes"></param> /// <returns></returns> protected override List <Scene2DEntry> DeSerialize(RuntimeTypeModel typeModel, byte[] data, out List <BoxF2D> boxes) { // decompress if needed. Stream stream = null; if (_compress) { stream = new GZipStream(new MemoryStream(data), CompressionMode.Decompress); } else { // uncompressed stream. stream = new MemoryStream(data); } // create the memory stream. var collection = typeModel.Deserialize(stream, null, typeof(PrimitivesCollection)) as PrimitivesCollection; if (collection == null) { throw new Exception("Could not deserialize primitives."); } // create the collection var primitives = new List <Scene2DEntry>(); if (collection.Icons != null) { foreach (var primitive in collection.Icons) { Icon2DStyle style = _styleIndex.IconStyles[primitive.StyleId]; Icon2D icon = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = icon }); } } if (collection.Images != null) { foreach (var primitive in collection.Images) { Image2DStyle style = _styleIndex.ImageStyles[primitive.StyleId]; Image2D image = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = image }); } } if (collection.Lines != null) { foreach (var primitive in collection.Lines) { Line2DStyle style = _styleIndex.LineStyles[primitive.StyleId]; Line2D line = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = line }); } } if (collection.Points != null) { foreach (var primitive in collection.Points) { Point2DStyle style = _styleIndex.PointStyles[primitive.StyleId]; Point2D point = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = point }); } } if (collection.Polygons != null) { foreach (var primitive in collection.Polygons) { Polygon2DStyle style = _styleIndex.PolygonStyles[primitive.StyleId]; Polygon2D polygon = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = polygon }); } } if (collection.Texts != null) { foreach (var primitive in collection.Texts) { Text2DStyle style = _styleIndex.TextStyles[primitive.StyleId]; Text2D text = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = text }); } } if (collection.LineTexts != null) { foreach (var primitive in collection.LineTexts) { LineText2DStyle style = _styleIndex.LineTextStyles[primitive.StyleId]; LineText2D lineText = primitive.To(style); primitives.Add(new Scene2DEntry() { Id = primitive.Id, Layer = style.Layer, Scene2DPrimitive = lineText }); } } // build the boxes list. boxes = new List <BoxF2D>(); for (int idx = 0; idx < primitives.Count; idx++) { boxes.Add(primitives[idx].Scene2DPrimitive.GetBox()); } return(primitives); }