GMap.Net根据地址搜索,并双击获得经纬度((Winform)最新版本的代码))

      首先下载必须插件:http://greatmaps.codeplex.com/。并引用里面的dll插件。

  在我们编码的时候,必须要弄懂地图是怎么构成的,是有三层构成的,图片如下(剪切地址:http://www.flickr.com/photos/33793929@N07/6008096410/):

最上层:GMapMarker.中间层:GMapOverlay。最底层:GMapControl。GMapMarker就是用户选中的地址做的水滴标记。当我们要添加水滴标记的时候,标记先添加进入GMapMarker,再把GMapMarker添加进GMapOverlay,最后把GMapOverlay添加进GMapMarker中,就会打到如下面图片中的水滴效果。如果是移除水滴标记,则以相反方向依次移除。下面就开始贴代码了。

     功能代码如下:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using GMap.NET;
using GMap.NET.WindowsForms.Markers;
using GMap.NET.WindowsForms;
using GMap.NET.MapProviders;
using GMap.NET.Projections;
using WindowsFormsApplication1.Properties;
using System.Windows;

namespace WindowsFormsApplication1
{
    public partial class FrmMap : Form
    {
        //地图由三层组成。最上层:GMapMarker.中间层:GMapOverlay。最底层:GMapControl。  
        GMapOverlay objects;
        GMapControl MainMap;

        public FrmMap()
        {
            InitializeComponent();

            //获得地图信息,默认北京位置。
            SuspendLayout();
            MainMap = new GMapControl();
            {
                //Google中国地图。
                MainMap.MapProvider = GMapProviders.GoogleChinaMap;
                MainMap.Position = new PointLatLng(39.904214, 116.407113);
                MainMap.MinZoom = 1;
                MainMap.MaxZoom = 19;
                MainMap.Zoom = 10;
                MainMap.Dock = DockStyle.Fill;
                MainMap.MarkersEnabled = true;

                this.label2.Text = this.label1.Text = "";
                this.label1.Text = "经度:" + MainMap.Position.Lng.ToString();
                this.label2.Text = "纬度:" + MainMap.Position.Lat.ToString();
            }

            //this.MainMap.ReloadMap();//重新加载地图。
            GMapProvider.Language = LanguageType.ChineseSimplified;

            //最上层的图标显示。
            Cursor.Current = Cursors.WaitCursor;
            var current = new PointLatLng(MainMap.Position.Lat, MainMap.Position.Lng);
            var currentMark = new GMapMarkerGoogleGreen(current);
            var overlay = new GMapOverlay(MainMap, "current");

            overlay.Markers.Add(currentMark);
            MainMap.Overlays.Add(overlay);
            Cursor.Current = Cursors.Default;

            //用户双击标记选中点。并获得当前的经纬度。
            {
                MainMap.MouseDoubleClick += new MouseEventHandler(MainMap_MouseDoubleClick);
            }

            gMapControl1.Controls.Add(MainMap);
            ResumeLayout(true);

            objects = new GMapOverlay(this.gMapControl1, "objects");
            this.gMapControl1.Overlays.Add(objects);
            GMapMarkerRect rect = new GMapMarkerRect(MainMap.Position);
            rect.Size = new System.Drawing.Size(0, 0);
            rect.ToolTipText = "北京市";
            rect.ToolTipMode = MarkerTooltipMode.Always;
            overlay.Markers.Add(rect);

            MainMap.DragButton = MouseButtons.Left;
            txtAddress.Focus();
        }

        //用户选中地图位置,获得经纬度。
        void MainMap_MouseDoubleClick(object sender, MouseEventArgs e)
        {
            if (e.Button == MouseButtons.Left)
            {
                //图标显示。
                Cursor.Current = Cursors.WaitCursor;

                PointLatLng latLng = MainMap.FromLocalToLatLng(e.X, e.Y);
                var current = new PointLatLng(Math.Abs(latLng.Lat), latLng.Lng);
                var currentMark = new GMapMarkerGoogleGreen(current);
                var overlay = new GMapOverlay(MainMap, "current");
                MainMap.MarkersEnabled = false;
                overlay.Markers.Clear();
                MainMap.Overlays.Clear();
                overlay.Markers.Add(currentMark);
                MainMap.Overlays.Add(overlay);
                MainMap.MarkersEnabled = true;
                Cursor.Current = Cursors.Hand;
                this.label2.Text = this.label1.Text = "";
                this.label1.Text = "经度:" + latLng.Lng.ToString();
                this.label2.Text = "纬度:" + latLng.Lat.ToString();
            }
        }

        //根据城市查询地图。
        private void btnSearch_Click(object sender, EventArgs e)
        {
            if (this.txtAddress.Text.Length == 0)
            {
                this.txtAddress.Focus();
                MessageBox.Show("请输入查询的地址");
                return;
            }

            this.MainMap.ReloadMap();
            GMapProvider.Language = LanguageType.ChineseSimplified;
            string search = string.Format("{0}", this.txtAddress.Text);

            //判断地址键是否存在。
            GeoCoderStatusCode code = MainMap.SetCurrentPositionByKeywords(search);
            if (code != GeoCoderStatusCode.G_GEO_SUCCESS)
            {
                MessageBox.Show("地址没有找到:'" + this.txtAddress.Text + "', 原因:" + code.ToString(), "GMap.NET", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                return;
            }

            objects = new GMapOverlay(MainMap, "objects");
            objects.Markers.Clear();
            this.MainMap.Overlays.Clear();

            AddLocation(txtAddress.Text);
        }

        //由地址获得经纬度,再显示地图位置。
        private void AddLocation(string place)
        {
            GeoCoderStatusCode unknow = GeoCoderStatusCode.Unknow;
            PointLatLng? latLngFromGeocoder = GMap.NET.MapProviders.GMapProviders.GoogleChinaMap.GetPoint(place, out unknow);
            if (latLngFromGeocoder.HasValue && (unknow == GeoCoderStatusCode.G_GEO_SUCCESS))
            {
                GMapMarker item = new GMapMarkerGoogleGreen(latLngFromGeocoder.Value);
                GMapMarkerRect rect = new GMapMarkerRect(latLngFromGeocoder.Value);
                rect.Size = new System.Drawing.Size(100, 100);
                rect.ToolTipText = place;
                rect.ToolTipMode = MarkerTooltipMode.Always;

                objects = new GMapOverlay(MainMap, "objects");
                objects.Markers.Add(item);
                objects.Markers.Add(rect);
                MainMap.Overlays.Add(objects);
                this.label2.Text = this.label1.Text = "";
                this.label1.Text = "经度:" + latLngFromGeocoder.Value.Lng.ToString();
                this.label2.Text = "纬度:" + latLngFromGeocoder.Value.Lat.ToString();
                if (txtAddress.Text.Length < 4)
                {
                    this.MainMap.Zoom = 10;
                }
                else
                {
                    this.MainMap.Zoom += 3;
                }
            }
        }
    }
}

 

界面如下:

 

 

加载运行后的效果如下:

 

 

其中搜索的方法AddLocation中有一个类GMapMarkerRect 需要重新建立一个类,类中代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WindowsFormsApplication1
{
    using System.Drawing;
    using GMap.NET.WindowsForms;
    using GMap.NET.WindowsForms.Markers;
    using GMap.NET;
    using System;
    using System.Runtime.Serialization;
    using System.Drawing.Drawing2D;

    [Serializable]
    public class GMapMarkerRect : GMapMarker, ISerializable
    {
        [NonSerialized]
        public Pen Pen;


        //[NonSerialized]
        //public GMarkerGoogle InnerMarker;
        public GMapMarkerRect(PointLatLng p): base(p)
        {
            Pen = new Pen(Brushes.Blue, 5);

            // do not forget set Size of the marker
            // if so, you shall have no event on it ;}
            Size = new System.Drawing.Size(111, 111);
            Offset = new System.Drawing.Point(-Size.Width / 2, -Size.Height / 2);
        }

        public override void OnRender(Graphics g)
        {
            g.DrawRectangle(Pen, new System.Drawing.Rectangle(LocalPosition.X, LocalPosition.Y, Size.Width, Size.Height));
        }
    }
}

 按地址搜索后的效果如下:

 

《参考文章:http://www.cnblogs.com/wuhuacong/archive/2010/03/10/1681790.html

 源码下载:https://files.cnblogs.com/Health/WindowsFormsApplication1.rar

posted @ 2012-02-23 16:32  悟行  阅读(6947)  评论(9编辑  收藏  举报