首先下载必须插件: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》
源码下载:http://files.cnblogs.com/Health/WindowsFormsApplication1.rar