Exemplo n.º 1
0
        private void AddSampleDataToLinesTable(LinesLayer layer, SpatialDataTable dt)
        {
            int nplines = 15 / Layers.CountAll((l) => l.Visible && l is LinesLayer);
            var rnd     = new Random(Layers.IndexOf(layer)); // this ensures same data for same layer but different points for different layers

            for (int i = 0; i < nplines; ++i)
            {
                LinesDataRow row       = (LinesDataRow)dt.NewRow();
                var          lineStyle = layer.LineStyle;
                row.Latitude0  = rnd.Next(SampleLatMin, SampleLatMax);
                row.Longitude0 = rnd.Next(SampleLonMin, SampleLonMax);
                row.Latitude1  = rnd.Next(SampleLatMin, SampleLatMax);
                row.Longitude1 = rnd.Next(SampleLonMin, SampleLonMax);
                row.LineStroke = lineStyle.StrokeColor;
                row.DashStyle  = lineStyle.DashStyle;
                dt.Add(row);
            }
        }
Exemplo n.º 2
0
        private Image BuildMap(List <SpatialDataTable> datas, bool designTime)
        {
            if (designTime)
            {
                foreach (KmlLayer layer in Layers.FindAll((l) => l is KmlLayer))
                {
                    layer.RemoveFromOwner();
                }
            }
            else
            {
                var calcLayers = GetCalculatedKmlLayers();
                calcLayers.ForEach((l) => l.RemoveFromOwner());
            }

            _c1mapper.ClearMarks();
            _c1mapper.ResetBoundingPoints();

            _c1mapper.Width  = (this.Width * ScreenDpiX) / TwipsIn;
            _c1mapper.Height = (this.Height * ScreenDpiY) / TwipsIn;

            // 1st pass: add KML layers, retrieve coordinates from other layers for auto-zoom/center:
            foreach (LayerBase layer in Layers.FindAll((l) => l.Visible && (l is KmlLayer || l.Track)))
            {
                if (layer is KmlLayer)
                {
                    ((KmlLayer)layer).SetKmlOnOwner();
                }
                else // layer.Track
                {
                    SpatialDataTable dt = datas.Find((t) => t.LayerKey == layer.Key);
                    dt.ForEach((row) => row.ForAllPoints((lon, lat) => _c1mapper.AddBoundingPoint(lon, lat)));
                }
            }

            // now we can auto zoom/center as all relevant spatial data has been given to the mapper:
            _c1mapper.DoCenterAndZoom();

            // 2nd pass: add points/lines layers:
            foreach (LayerBase layer in Layers.FindAll((l) => l.Visible && !(l is KmlLayer)))
            {
                // considering that no of layers should not be large, this is ok:
                SpatialDataTable dt = datas.Find((t) => t.LayerKey == layer.Key);
                if (dt.RowType == typeof(PointsDataRow))
                {
                    var l = (PointsLayer)layer;
                    // clustering:
                    var clusterDist    = l.ClusterDistance;
                    var maxClusterSize = 0;
                    if (clusterDist > 0)
                    {
                        for (int i = 0; i < dt.Count; ++i)
                        {
                            var r = (PointsDataRow)dt[i];
                            for (int j = dt.Count - 1; j > i; --j)
                            {
                                var r2 = (PointsDataRow)dt[j];
                                if (_c1mapper.DistancePix(r.Longitude, r.Latitude, r2.Longitude, r2.Latitude) < clusterDist)
                                {
                                    maxClusterSize = Math.Max(maxClusterSize, ++r.Count);
                                    dt.RemoveAt(j);
                                }
                            }
                        }
                    }
                    // spread styles among clusters:
                    var styleCount = l.ClusterStyles != null ? l.ClusterStyles.Count : 0;
                    var q          = l.ClusterDistribution == ScaleType.Linear ? ((styleCount - 1f) / (maxClusterSize - 2f)) : 1f;
                    // add clustered points to the map:
                    dt.ForEach((row) =>
                    {
                        PointsDataRow r = (PointsDataRow)row;
                        if (r.Count > 1)
                        {
                            r.Caption = r.Count.ToString(CultureInfo.InvariantCulture);
                            if (styleCount > 0)
                            {
                                // we have a style to apply:
                                int idx;
                                if (l.ClusterDistribution == ScaleType.Linear)
                                {
                                    idx = (int)Math.Round((r.Count - 2) * q);
                                }
                                else
                                {
                                    var t = Math.Log(r.Count - 1, maxClusterSize - 1);
                                    if (double.IsNaN(t))
                                    {
                                        t = 0;
                                    }
                                    idx = (int)Math.Round(t * (styleCount - 1d));
                                }
                                var s         = l.ClusterStyles[idx];
                                r.Font        = s.Font;
                                r.TextColor   = s.TextColor;
                                r.MarkerShape = s.Shape;
                                // todo: eval expr here, allow to use Count?
                                r.MarkerSize   = Maps.Util.GetDouble(s.SizeExpr, MarkerStyle.c_SizeValue);
                                r.MarkerStroke = s.StrokeColor;
                                r.MarkerFill   = s.FillColor;
                            }
                        }
                        _c1mapper.DrawPoint(layer.Key, r.Longitude, r.Latitude, r.Caption, r.Font, r.TextColor, r.MarkerShape, r.MarkerSize, r.MarkerStroke, r.MarkerFill);
                    }
                               );
                }
                else if (dt.RowType == typeof(LinesDataRow))
                {
                    // add lines to the map:
                    dt.ForEach((row) =>
                    {
                        LinesDataRow r = (LinesDataRow)row;
                        _c1mapper.DrawLine(layer.Key, r.Longitude0, r.Latitude0, r.Longitude1, r.Latitude1, r.LineStroke, r.DashStyle, r.LineThickness);
                    }
                               );
                }
            }

            // done:
            return(_c1mapper.GetImage(TargetDpi, TargetDpi));
        }