private void MapView_Loaded(object sender, RoutedEventArgs e)
        {
            mapView.MapUnit       = GeographyUnit.DecimalDegree;
            mapView.CurrentExtent = new RectangleShape(-177.39584350585937, 83.113876342773437, -52.617362976074219, 14.550546646118164);

            ShapeFileFeatureLayer worldLayer = new ShapeFileFeatureLayer(SampleHelper.Get("Countries02_3857.shp"));

            worldLayer.Open();
            ProjectionConverter project = new ProjectionConverter(3857, 4326);

            project.Open();
            Feature feature = project.ConvertToExternalProjection(worldLayer.QueryTools.GetFeatureById("135", new string[0]));

            project.Close();
            areaBaseShape = (AreaBaseShape)feature.GetShape();
            worldLayer.Close();

            InMemoryFeatureLayer simplificationLayer = new InMemoryFeatureLayer();

            simplificationLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
            simplificationLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColor.FromArgb(255, 233, 232, 214), GeoColor.FromArgb(255, 118, 138, 69));
            simplificationLayer.InternalFeatures.Add(feature);

            LayerOverlay simplificationOverlay = new LayerOverlay();

            simplificationOverlay.TileType = TileType.SingleTile;
            simplificationOverlay.Layers.Add(new BackgroundLayer(new GeoSolidBrush(GeoColors.DeepOcean)));
            simplificationOverlay.Layers.Add("SimplificationLayer", simplificationLayer);
            mapView.Overlays.Add("SimplificationOverlay", simplificationOverlay);

            cmbSimplificationType.SelectedIndex = 0;
            cmbTolerance.SelectedIndex          = 0;
            mapView.Refresh();
        }
Пример #2
0
        private void mapView_MapClick(object sender, MapClickMapViewEventArgs e)
        {
            FeatureLayer worldLayer = mapView.FindFeatureLayer("WorldLayer");

            // Find the country the user clicked on.
            worldLayer.Open();
            Collection <Feature> selectedFeatures = worldLayer.QueryTools.GetFeaturesContaining(e.WorldLocation, new string[1] {
                "CNTRY_NAME"
            });

            worldLayer.Close();

            // Determine the area of the country.
            if (selectedFeatures.Count > 0)
            {
                ProjectionConverter project = new ProjectionConverter(3857, 4326);
                project.Open();
                AreaBaseShape areaShape = (AreaBaseShape)project.ConvertToExternalProjection(selectedFeatures[0].GetShape());
                project.Close();
                double area        = areaShape.GetArea(GeographyUnit.DecimalDegree, AreaUnit.SquareKilometers);
                string areaMessage = string.Format(CultureInfo.InvariantCulture, "{0} has an area of \r{1:N0} square kilometers.", selectedFeatures[0].ColumnValues["CNTRY_NAME"].Trim(), area);

                Popup popup = new Popup(e.WorldLocation);
                popup.Content = areaMessage;
                PopupOverlay popupOverlay = (PopupOverlay)mapView.Overlays["PopupOverlay"];
                popupOverlay.Popups.Clear();
                popupOverlay.Popups.Add(popup);
                popupOverlay.Refresh();
            }
        }
Пример #3
0
        private void mapView_Loaded(object sender, RoutedEventArgs e)
        {
            mapView.MapUnit       = GeographyUnit.Meter;
            mapView.ZoomLevelSet  = new ThinkGeoCloudMapsZoomLevelSet();
            mapView.CurrentExtent = new RectangleShape(-15495673, 20037508, 13458526, -20037508);

            // Create background world map with vector tile requested from ThinkGeo Cloud Service.
            ThinkGeoCloudVectorMapsOverlay thinkGeoCloudVectorMapsOverlay = new ThinkGeoCloudVectorMapsOverlay(SampleHelper.ThinkGeoCloudId, SampleHelper.ThinkGeoCloudSecret, ThinkGeoCloudVectorMapsMapType.Light);

            mapView.Overlays.Add(thinkGeoCloudVectorMapsOverlay);

            // Setup the shapefile layer.
            ShapeFileFeatureLayer worldLayer = new ShapeFileFeatureLayer(SampleHelper.Get("Countries02_3857.shp"));

            worldLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColors.Transparent, GeoColor.FromArgb(100, GeoColors.Green));
            worldLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            // Setup the mapshape layer.
            InMemoryFeatureLayer bitmapLayer = new InMemoryFeatureLayer();

            bitmapLayer.ZoomLevelSet.ZoomLevel01.DefaultPointStyle.PointType = PointType.Image;
            bitmapLayer.ZoomLevelSet.ZoomLevel01.DefaultPointStyle.Image     = new GeoImage(SampleHelper.Get("Prop Plane.png"));
            bitmapLayer.ZoomLevelSet.ZoomLevel01.DefaultLineStyle            = LineStyle.CreateSimpleLineStyle(GeoColors.Red, 1F, LineDashStyle.Dash, false);
            bitmapLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel         = ApplyUntilZoomLevel.Level20;

            ProjectionConverter project = new ProjectionConverter(4326, 3857);

            project.Open();
            PointShape     planeShape       = new PointShape(-95.2806, 38.9554);
            PointShape     destinationPoint = new PointShape(36.04, 48.49);
            MultilineShape airLineShape     = (MultilineShape)project.ConvertToExternalProjection(planeShape.GreatCircle(destinationPoint));

            airLineShape.Id = "AirLine";
            bitmapLayer.Open();
            bitmapLayer.EditTools.BeginTransaction();
            bitmapLayer.EditTools.Add(new Feature(project.ConvertToExternalProjection(planeShape).GetWellKnownBinary(), "Plane"));
            bitmapLayer.EditTools.Add(new Feature(airLineShape.GetWellKnownBinary(), "AirLine"));
            bitmapLayer.EditTools.CommitTransaction();
            bitmapLayer.Close();
            project.Close();

            LayerOverlay worldOverlay = new LayerOverlay();

            worldOverlay.Layers.Add("WorldLayer", worldLayer);
            mapView.Overlays.Add("WorldOverlay", worldOverlay);

            LayerOverlay planeOverlay = new LayerOverlay();

            planeOverlay.TileType = TileType.SingleTile;
            planeOverlay.Layers.Add("BitmapLayer", bitmapLayer);
            mapView.Overlays.Add("PlaneOverlay", planeOverlay);

            mapView.Refresh();

            timer.Start();
        }
Пример #4
0
        private void mapView_MapClick(object sender, MapClickMapViewEventArgs e)
        {
            ProjectionConverter project = new ProjectionConverter(3857, 4326);

            project.Open();
            var worldPointInDecimalDegree = project.ConvertToExternalProjection(e.WorldX, e.WorldY);

            TBLonLat.Text = string.Format(CultureInfo.InvariantCulture, "X={0}, Y={1}", worldPointInDecimalDegree.X.ToString("N4", CultureInfo.InvariantCulture), worldPointInDecimalDegree.Y.ToString("N4", CultureInfo.InvariantCulture));
            project.Close();
        }
        private void mapView_MapClick(object sender, MapClickMapViewEventArgs e)
        {
            screenPosition.Text = "(" + e.ScreenX + ", " + e.ScreenY + ")";
            ProjectionConverter project = new ProjectionConverter(3857, 4326);

            project.Open();
            var worldPointInDecimalDegree = project.ConvertToExternalProjection(e.WorldX, e.WorldY);

            worldPosition.Text = string.Format(CultureInfo.InvariantCulture, "({0}, {1})", worldPointInDecimalDegree.X.ToString("N4", CultureInfo.InvariantCulture), worldPointInDecimalDegree.Y.ToString("N4", CultureInfo.InvariantCulture));
            project.Close();
        }
Пример #6
0
        /// <summary>
        /// Use the ProjectionConverter to reproject multiple features
        /// </summary>
        private Collection <Feature> ReprojectMultipleFeatures(Collection <Feature> decimalDegreeFeatures)
        {
            //Create a new ProjectionConverter to convert between Decimal Degrees(4326) and Spherical Mercator(3857)
            ProjectionConverter projectionConverter = new ProjectionConverter(4326, 3857);

            //Convert the feature to Spherical Mercator
            projectionConverter.Open();
            Collection <Feature> sphericalMercatorFeatures = projectionConverter.ConvertToExternalProjection(decimalDegreeFeatures);

            projectionConverter.Close();

            //Return the reprojected features
            return(sphericalMercatorFeatures);
        }
Пример #7
0
        /// <summary>
        /// Use the ProjectionConverter to reproject a single feature
        /// </summary>
        private Feature ReprojectFeature(Feature decimalDegreeFeature)
        {
            //Create a new ProjectionConverter to convert between Decimal Degrees(4326) and Spherical Mercator(3857)
            ProjectionConverter projectionConverter = new ProjectionConverter(4326, 3857);

            //Convert the feature to Spherical Mercator
            projectionConverter.Open();
            Feature sphericalMercatorFeature = projectionConverter.ConvertToExternalProjection(decimalDegreeFeature);

            projectionConverter.Close();

            //Return the reprojected feature
            return(sphericalMercatorFeature);
        }
        private void btnGetDistance_Click(object sender, RoutedEventArgs e)
        {
            InMemoryFeatureLayer usInMemoryLayer    = (InMemoryFeatureLayer)mapView.FindFeatureLayer("USInMemoryFeatureLayer");
            InMemoryFeatureLayer chinaInMemoryLayer = (InMemoryFeatureLayer)mapView.FindFeatureLayer("ChinaInMemoryFeatureLayer");

            ProjectionConverter project = new ProjectionConverter(3857, 4326);

            project.Open();
            BaseShape usShape    = project.ConvertToExternalProjection(usInMemoryLayer.InternalFeatures["US"].GetShape());
            BaseShape chinaShape = project.ConvertToExternalProjection(chinaInMemoryLayer.InternalFeatures["CHINA"].GetShape());

            project.Close();

            double distance = usShape.GetDistanceTo(chinaShape, GeographyUnit.DecimalDegree, DistanceUnit.Kilometer);

            txtDistance.Text = string.Format(CultureInfo.InvariantCulture, "{0 :N4} Km", distance);
        }
Пример #9
0
        /// <summary>
        /// Zoom to a lat/lon at a desired scale by converting the lat/lon to match the map's projection
        /// </summary>
        private async void ZoomToLatLon_Click(object sender, EventArgs e)
        {
            await CollapseExpander();

            // Create a PointShape from the lat-lon
            var latlonPoint = new PointShape(Convert.ToDouble(latitude.Text), Convert.ToDouble(longitude.Text));

            // Convert the lat-lon projection to match the map
            var projectionConverter = new ProjectionConverter(4326, 3857);

            projectionConverter.Open();
            var convertedPoint = (PointShape)projectionConverter.ConvertToExternalProjection(latlonPoint);

            projectionConverter.Close();

            // Zoom to the converted lat-lon at the desired scale
            mapView.ZoomTo(convertedPoint, Convert.ToDouble(latlonScale.Text));
        }
Пример #10
0
        private void MapView_Loaded(object sender, RoutedEventArgs e)
        {
            project = new ProjectionConverter(3857, 4326);
            project.Open();

            mapView.MapUnit       = GeographyUnit.Meter;
            mapView.ZoomLevelSet  = new ThinkGeoCloudMapsZoomLevelSet();
            mapView.CurrentExtent = new RectangleShape(-15963215, 20037508, 12990985, -13516534);

            // Create background world map with vector tile requested from ThinkGeo Cloud Service.
            ThinkGeoCloudVectorMapsOverlay thinkGeoCloudVectorMapsOverlay = new ThinkGeoCloudVectorMapsOverlay(SampleHelper.ThinkGeoCloudId, SampleHelper.ThinkGeoCloudSecret, ThinkGeoCloudVectorMapsMapType.Light);

            mapView.Overlays.Add(thinkGeoCloudVectorMapsOverlay);

            ShapeFileFeatureLayer worldLayer = new ShapeFileFeatureLayer(SampleHelper.Get("Countries02_3857.shp"));

            worldLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColors.Transparent, GeoColor.FromArgb(100, GeoColors.Green));
            worldLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            InMemoryFeatureLayer highlightLayer = new InMemoryFeatureLayer();

            highlightLayer.ZoomLevelSet.ZoomLevel01.DefaultPointStyle   = PointStyle.CreateCompoundPointStyle(PointSymbolType.Square, GeoColors.White, GeoColors.Black, 1F, 8F, PointSymbolType.Square, GeoColors.Navy, GeoColors.Transparent, 0F, 4F);
            highlightLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColor.FromArgb(150, 154, 205, 50));
            highlightLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            LayerOverlay worldOverlay = new LayerOverlay();

            worldOverlay.Layers.Add("WorldLayer", worldLayer);
            mapView.Overlays.Add("WorldOverlay", worldOverlay);

            LayerOverlay dynamicOverlay = new LayerOverlay();

            dynamicOverlay.TileType = TileType.SingleTile;
            dynamicOverlay.Layers.Add("HighlightLayer", highlightLayer);
            mapView.Overlays.Add("HighlightOverlay", dynamicOverlay);

            mapView.MapClick     += new EventHandler <MapClickMapViewEventArgs>(mapView_MapClick);
            mapView.CurrentExtent = new RectangleShape(-14833496, 20037508, 14126965, -20037508);
            mapView.Refresh();
        }
        private void mapView_MapClick(object sender, MapClickMapViewEventArgs e)
        {
            FeatureLayer         worldLayer     = mapView.FindFeatureLayer("RoadLayer");
            InMemoryFeatureLayer highlightLayer = (InMemoryFeatureLayer)mapView.FindFeatureLayer("HighlightLayer");
            Overlay highlightOverlay            = mapView.Overlays["HighlightOverlay"];

            // Find the road the user clicked on.
            worldLayer.Open();
            Collection <Feature> selectedFeatures = worldLayer.QueryTools.GetFeaturesNearestTo(e.WorldLocation, GeographyUnit.Meter, 1, new string[1] {
                "FENAME"
            });

            worldLayer.Close();

            //Determine the length of the road.
            if (selectedFeatures.Count > 0)
            {
                LineBaseShape lineShape = (LineBaseShape)selectedFeatures[0].GetShape();
                highlightLayer.Open();
                highlightLayer.InternalFeatures.Clear();
                highlightLayer.InternalFeatures.Add(new Feature(lineShape));
                highlightLayer.Close();
                ProjectionConverter project = new ProjectionConverter(3857, 4326);
                project.Open();
                double length = ((LineBaseShape)project.ConvertToExternalProjection(lineShape)).GetLength(GeographyUnit.DecimalDegree, DistanceUnit.Meter);
                project.Close();
                string lengthMessage = string.Format(CultureInfo.InvariantCulture, "{0} has a length of {1:F2} meters.", selectedFeatures[0].ColumnValues["FENAME"].Trim(), length);

                Popup popup = new Popup(e.WorldLocation);
                popup.Content = lengthMessage;
                PopupOverlay popupOverlay = (PopupOverlay)mapView.Overlays["PopupOverlay"];
                popupOverlay.Popups.Clear();
                popupOverlay.Popups.Add(popup);

                highlightOverlay.Refresh();
                popupOverlay.Refresh();
            }
        }
Пример #12
0
        /// <summary>
        /// Use the TimezoneCloudClient to query for timezone information
        /// </summary>
        private async Task GetTimeZoneInfo(double lon, double lat)
        {
            CloudTimeZoneResult result;

            try
            {
                // Show a loading graphic to let users know the request is running
                loadingIndicator.IsRunning = true;
                loadingLayout.IsVisible    = true;

                // Get timezone info based on the lon, lat, and input projection (Spherical Mercator in this case)
                result = await timeZoneCloudClient.GetTimeZoneByCoordinateAsync(lon, lat, 3857);
            }
            catch (Exception ex)
            {
                await DisplayAlert("Error", ex.Message, "OK");

                return;
            }
            finally
            {
                loadingIndicator.IsRunning = false;
                loadingLayout.IsVisible    = false;
            }

            // Get the timezone info popup overlay from the mapview
            PopupOverlay timezoneInfoPopupOverlay = (PopupOverlay)mapView.Overlays["Timezone Info Popup Overlay"];

            // Clear the existing info popups from the map
            timezoneInfoPopupOverlay.Popups.Clear();

            // Build a string description of the timezone
            StringBuilder timezoneInfoString = new StringBuilder();

            timezoneInfoString.AppendLine($"Time Zone: {result.TimeZone}");
            timezoneInfoString.AppendLine($"Current Local Time: {result.CurrentLocalTime}");
            timezoneInfoString.AppendLine($"Daylight Savings Active: {result.DaylightSavingsActive}");

            // Display the timezone info on a popup on the map
            Popup popup = new Popup();

            popup.Content  = timezoneInfoString.ToString();
            popup.Position = new PointShape(lon, lat);
            timezoneInfoPopupOverlay.Popups.Add(popup);

            // Clear the timezone feature layer of previous features
            InMemoryFeatureLayer timezonesFeatureLayer = (InMemoryFeatureLayer)mapView.FindFeatureLayer("Timezone Feature Layer");

            timezonesFeatureLayer.Open();
            timezonesFeatureLayer.InternalFeatures.Clear();

            // Use a ProjectionConverter to convert the shape to Spherical Mercator
            ProjectionConverter converter = new ProjectionConverter(3857, 4326);

            converter.Open();

            // Add the new timezone polygon to the map
            timezonesFeatureLayer.InternalFeatures.Add(new Feature(converter.ConvertToInternalProjection(result.Shape)));
            converter.Close();
            timezonesFeatureLayer.Close();

            // Refresh and redraw the map
            mapView.Refresh();
        }
Пример #13
0
        private void ExtractTiles(PolygonShape polygonShape, string targetFilePath)
        {
            RectangleShape         bbox       = polygonShape.GetBoundingBox();
            List <VectorTileRange> tileRanges = new List <VectorTileRange>();

            for (int zoomLevel = 0; zoomLevel <= maxZoom; zoomLevel++)
            {
                VectorTileRange tileRange = GetTileRange(zoomLevel, bbox);
                tileRanges.Add(tileRange);
            }
            ThinkGeoMBTilesLayer.CreateDatabase(targetFilePath);

            var targetDBConnection = new SqliteConnection($"Data Source={targetFilePath}");

            targetDBConnection.Open();
            var targetMap      = new TilesTable(targetDBConnection);
            var targetMetadata = new MetadataTable(targetDBConnection);

            var sourceDBConnection = new SqliteConnection($"Data Source={mbtilesPathFilename}");

            sourceDBConnection.Open();
            var sourceMap      = new TilesTable(sourceDBConnection);
            var sourceMetadata = new MetadataTable(sourceDBConnection);

            sourceMetadata.ReadAllEntries();

            ProjectionConverter projection = new ProjectionConverter(3857, 4326);

            projection.Open();
            var wgs84BBox = projection.ConvertToExternalProjection(bbox);

            foreach (MetadataEntry entry in sourceMetadata.Entries)
            {
                if (entry.Name.Equals("center"))
                {
                    PointShape centerPoint = wgs84BBox.GetCenterPoint();
                    entry.Value = $"{centerPoint.X},{centerPoint.Y},{maxZoom}";
                }
                else if (entry.Name.Equals("bounds"))
                {
                    entry.Value = $"{wgs84BBox.UpperLeftPoint.X},{wgs84BBox.UpperLeftPoint.Y},{wgs84BBox.LowerRightPoint.X},{wgs84BBox.LowerRightPoint.Y}";
                }
            }
            targetMetadata.Insert(sourceMetadata.Entries);

            int recordLimit = 1000;

            foreach (var tileRange in tileRanges)
            {
                long offset = 0;
                bool isEnd  = false;
                while (!isEnd)
                {
                    string querySql = $"SELECT * FROM {sourceMap.TableName} WHERE " + ConvetToSqlString(tileRange) + $" LIMIT {offset},{recordLimit}";
                    var    entries  = sourceMap.Query(querySql);
                    for (int i = entries.Count - 1; i >= 0; i--)
                    {
                        RectangleShape pbfExtent = GetPbfTileExent((int)entries[i].ZoomLevel, entries[i].TileColumn, entries[i].TileRow);
                        if (polygonShape.IsDisjointed(pbfExtent))
                        {
                            entries.RemoveAt(i);
                        }
                    }
                    targetMap.Insert(entries);

                    if (entries.Count < recordLimit)
                    {
                        isEnd = true;
                    }

                    offset = offset + recordLimit;
                }
            }
        }
Пример #14
0
        /// <summary>
        /// Set up the map with the ThinkGeo Cloud Maps overlay and a feature layer containing Frisco zoning data
        /// </summary>
        protected override void OnAppearing()
        {
            base.OnAppearing();
            // Create the background world maps using vector tiles requested from the ThinkGeo Cloud Service.
            ThinkGeoCloudVectorMapsOverlay thinkGeoCloudVectorMapsOverlay = new ThinkGeoCloudVectorMapsOverlay("9ap16imkD_V7fsvDW9I8r8ULxgAB50BX_BnafMEBcKg~", "vtVao9zAcOj00UlGcK7U-efLANfeJKzlPuDB9nw7Bp4K4UxU_PdRDg~~", ThinkGeoCloudVectorMapsMapType.Light);

            thinkGeoCloudVectorMapsOverlay.VectorTileCache = new FileVectorTileCache(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "cache"), "CloudMapsVector");

            mapView.Overlays.Add(thinkGeoCloudVectorMapsOverlay);

            // Set the Map Unit to meters (used in Spherical Mercator)
            mapView.MapUnit = GeographyUnit.Meter;

            // Create a feature layer to hold and display the zoning data
            InMemoryFeatureLayer zoningLayer = new InMemoryFeatureLayer();

            // Add a style to use to draw the Frisco zoning polygons
            zoningLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
            zoningLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColor.FromArgb(50, GeoColors.MediumPurple), GeoColors.MediumPurple, 2);

            // Import the features from the Frisco zoning data shapefile
            ShapeFileFeatureSource zoningDataFeatureSource = new ShapeFileFeatureSource(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "Data/Shapefile/Zoning.shp"));

            // Create a ProjectionConverter to convert the shapefile data from North Central Texas (2276) to Spherical Mercator (3857)
            ProjectionConverter projectionConverter = new ProjectionConverter(3857, 2276);

            // For this sample, we have to reproject the features before adding them to the feature layer
            // This is because the topological equality query often does not work when used on a feature layer with a ProjectionConverter, due to rounding issues between projections
            zoningDataFeatureSource.Open();
            projectionConverter.Open();
            foreach (Feature zoningFeature in zoningDataFeatureSource.GetAllFeatures(ReturningColumnsType.AllColumns))
            {
                Feature reprojectedFeature = projectionConverter.ConvertToInternalProjection(zoningFeature);
                zoningLayer.InternalFeatures.Add(reprojectedFeature);
            }
            zoningDataFeatureSource.Close();
            projectionConverter.Close();

            // Set the map extent to Frisco, TX
            //mapView.CurrentExtent = new RectangleShape(-10781137.28, 3917162.59, -10774579.34, 3911241.35);

            // Create a layer to hold the feature we will perform the spatial query against
            InMemoryFeatureLayer queryFeatureLayer = new InMemoryFeatureLayer();

            queryFeatureLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColor.FromArgb(75, GeoColors.LightRed), GeoColors.LightRed);
            queryFeatureLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            // Create a layer to hold features found by the spatial query
            InMemoryFeatureLayer highlightedFeaturesLayer = new InMemoryFeatureLayer();

            highlightedFeaturesLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle    = AreaStyle.CreateSimpleAreaStyle(GeoColor.FromArgb(90, GeoColors.MidnightBlue), GeoColors.MidnightBlue);
            highlightedFeaturesLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            // Add each feature layer to it's own overlay
            // We do this so we can control and refresh/redraw each layer individually
            LayerOverlay layerOverlay = new LayerOverlay();

            layerOverlay.Layers.Add("Frisco Zoning", zoningLayer);
            layerOverlay.Layers.Add("Query Feature", queryFeatureLayer);
            layerOverlay.Layers.Add("Highlighted Features", highlightedFeaturesLayer);

            mapView.Overlays.Add("Layer Overlay", layerOverlay);

            // Create a sample shape using vertices from an existing feature, to ensure that it is touching other features
            zoningLayer.Open();
            MultipolygonShape firstFeatureShape = (MultipolygonShape)zoningLayer.FeatureSource.GetAllFeatures(ReturningColumnsType.NoColumns).First().GetShape();

            // Get vertices from an existing feature
            var vertices = firstFeatureShape.Polygons.First().OuterRing.Vertices;

            // Create a new feature using a subset of those vertices
            MultipolygonShape sampleShape = new MultipolygonShape(new Collection <PolygonShape> {
                new PolygonShape(new RingShape(new Collection <Vertex> {
                    vertices[0], vertices[1], vertices[2]
                }))
            });

            queryFeatureLayer.InternalFeatures.Add(new Feature(sampleShape));
            zoningLayer.Close();
            GetFeaturesTouching(sampleShape);

            // Set the map extent to the sample shape
            mapView.CurrentExtent = new RectangleShape(-10778499.3056056, 3920951.91647677, -10774534.1347853, 3917536.13679426);

            mapView.Refresh();
        }