zoukankan      html  css  js  c++  java
  • C#调用百度地图 api

    转  http://blog.csdn.net/kkkkkxiaofei/article/details/8663377

      这一篇,记录一下我调用的地图API实现的功能。下面介绍的都是一些片段的节选,不能直接复制就运行。在实现之前肯定要加载地图,先放一个webbroser控件,然后如下:

    [csharp] view plaincopyprint?
     
    1. private void Form1_Load(object sender, EventArgs e)  
    2.         {  
    3.   
    4.             string str_url = Application.StartupPath + "\最终合并版本(昨晚修改).html";  
    5.             Uri url = new Uri(str_url);  
    6.             webBrowser1.Url = url;  
    7.             webBrowser1.ObjectForScripting = this;  
    8.                      
    9.         }  



        而为了能与JS交互,首先引入using System.Security.Permissions;,然后在namespace下必须加入两行:

    [csharp] view plaincopyprint?
     
    1. namespace WebBroser_Test_V1._0  
    2. {  
    3.     [PermissionSet(SecurityAction.Demand, Name = "FullTrust")]  
    4.   
    5.     [System.Runtime.InteropServices.ComVisibleAttribute(true)]  
    6.   
    7.   
    8.     public partial class Form1 : Form  
    9.     {  
    10.                public Form1()  
    11.         {  
    12.             InitializeComponent();  
    13.         }  
    14.         private void Form1_Load(object sender, EventArgs e)  
    15.         {  
    16.   
    17.             string str_url = Application.StartupPath + "\最终合并版本(昨晚修改).html";  
    18.             Uri url = new Uri(str_url);  
    19.             webBrowser1.Url = url;  
    20.             webBrowser1.ObjectForScripting = this;  
    21.            // timer1.Enabled = true;           
    22.         }  
    23. }  


     

    有了上面的基础,就可以实现以下功能了。

    1.鼠标放在屏幕上移动时,实时的显示坐标。

    放入一个timer和一个StatusScrip:

    [csharp] view plaincopyprint?
     
    1. private void timer1_Tick(object sender, EventArgs e)  
    2.         {  
    3.             try  
    4.             {  
    5.                 string tag_lng = webBrowser1.Document.GetElementById("mouselng").InnerText;  
    6.                 string tag_lat = webBrowser1.Document.GetElementById("mouselat").InnerText;  
    7.                 double dou_lng, dou_lat;  
    8.                 if (double.TryParse(tag_lng, out dou_lng) && double.TryParse(tag_lat, out dou_lat))  
    9.                 {  
    10.                     toolstatus_CurrentLocation.Text ="当前坐标:"+ dou_lng.ToString("F5") + "," + dou_lat.ToString("F5");  
    11.                 }  
    12.             }  
    13.             catch (Exception ee)  
    14.             { MessageBox.Show(ee.Message); }  
    15.             
    16.         }  


     

    放入一个button命名及代码如下:

    [csharp] view plaincopyprint?
     
    1. private void btnGetLocation_Click(object sender, EventArgs e)  
    2.        {  
    3.            if (btnGetLocation.Text == "开启实时坐标")  
    4.            {  
    5.                timer1.Enabled = true;  
    6.                btnGetLocation.Text = "关闭实时坐标";  
    7.            }  
    8.            else  
    9.            {  
    10.                btnGetLocation.Text = "开启实时坐标";  
    11.                timer1.Enabled = false;  
    12.            }  
    13.        }  


    JS脚本如下:

    [javascript] view plaincopyprint?
     
    1. var map =new BMap.Map("allmap");  
    2. var first_locate=new BMap.Point(108.953098,34.2778);  
    3. map.centerAndZoom(first_locate,15);     
    4. map.enableScrollWheelZoom(true);  
    5. map.addEventListener("mousemove",GetlngAndlat);     
    6. function GetlngAndlat(e)  
    7. {if(e.point.lng!=null)  
    8.  {  
    9.    
    10.  document.getElementById("mouselng").innerHTML=e.point.lng;  
    11.   document.getElementById("mouselat").innerHTML=e.point.lat;  
    12.  }  
    13. }  


     

    2.开启测距工具(百度自己开发的)

    拖一个按钮:

    [csharp] view plaincopyprint?
     
    1. //开启测距工具按钮  
    2.         private void btnOpenDistance_Click(object sender, EventArgs e)  
    3.         {  
    4.             webBrowser1.Document.InvokeScript("openGetDistance");  
    5.         }  


     

    为了加载这个工具,是需要引入百度的另一个工具库:

    JS如下:

    [javascript] view plaincopyprint?
     
    1. <script type="text/javascript" src="./JScript/DistanceTool_min.js"></script>  
    2. function openGetDistance()  
    3. {  
    4.  var myDis=new BMapLib.DistanceTool(map);//map为上面已经初始化好的地图实例  
    5.  myDis.open();  
    6. }  


     

    //上面这个DistanceTool_min.js在百度的DEMO里有,我只是把它考到我的DEBUG下了,具体路径自己解决。

    3.右击鼠标给地图上放marker,每一个marker的icon换成小汽车,并且显示坐标编号和坐标值,然后每放置一次,将数据存入数据库。

    //放标注

    [csharp] view plaincopyprint?
     
    1. private void btnPutMarker_Click(object sender, EventArgs e)  
    2.        {  
    3.            if (radioButton1.Checked || radioButton2.Checked || radioButton3.Checked || radioButton4.Checked)  
    4.                webBrowser1.Document.InvokeScript("PUTANDSEND");  
    5.            else  
    6.            {  
    7.                MessageBox.Show("至少选择一项!");  
    8.            }  
    9.        }  
    10.        //得到Radiobutton的值  
    11.        public string setWhichCar()  
    12.        {  
    13.            if (radioButton1.Checked)  
    14.                return "1";  
    15.            if (radioButton2.Checked)  
    16.                return "2";  
    17.            if (radioButton3.Checked)  
    18.                return "3";  
    19.            if (radioButton4.Checked)  
    20.                return "4";  
    21.            return "Erro";  
    22.        }  
    23.        //将从JS里得到的汽车数据显示到文本框内,并且存入数据库  
    24.        public void PutIntotextBox(object markerIndex,object carNumber,object JSlng,object JSlat)  
    25.        {  
    26.            text_index.Text =markerIndex.ToString();  
    27.            text_num.Text = (string)carNumber;  
    28.            text_lng.Text = JSlng.ToString();  
    29.            text_lat.Text = JSlat.ToString();  
    30.            string sql = "insert into 汽车轨迹数据 values ('"+text_num.Text+"','"+text_index.Text+"','"+text_lng.Text+"','"+text_lat.Text+"','"+DateTime.Now.ToString()+"')";  
    31.            DBfunction.getcom(sql);  
    32.              
    33.        }  


           

    JS脚本如下:

    [javascript] view plaincopyprint?
     
    1. //---------------放标注,并且将JS的数据传送给WINFORM------------  
    2. function PUTANDSEND()  
    3. {  
    4.   map.addEventListener("rightclick",putAndsend);  
    5. }  
    6. function putAndsend(e)  
    7. {  
    8.   //放标注  
    9.   var p1=new BMap.Point(e.point.lng,e.point.lat);  
    10.   var marker = new BMap.Marker(p1,{icon:myIcon});//将标注的图标改为小汽车  
    11.   map.addOverlay(marker);  
    12.   marker_num++;//标注索引,这个是个全局变量  
    13.   var whichCar=window.external.setWhichCar();  
    14.   var label=new BMap.Label(whichCar+"号车-坐标"+marker_num+":"+  
    15. "("+e.point.lng+","+e.point.lat+")",{offset:new BMap.Size(20,-10)});  
    16.   marker.setLabel(label);  
    17.   //给WINFORM传值  
    18.   window.external.PutIntotextBox(marker_num,whichCar,e.point.lng,e.point.lat);  
    19.     
    20. }  



    4.根据上面已经模拟的汽车历史坐标,可以查询具体车辆的历史轨迹(即从数据库里提取数据,画轨迹)

    [csharp] view plaincopyprint?
     
    1. private void btnDrawOrit_Click(object sender, EventArgs e)  
    2.         {  
    3.             string ss = "^[0-9]*$"; //正则表达式  
    4.             string cc = text_whichCar.Text.Trim().ToString();  
    5.             bool match = Regex.IsMatch(cc, ss);  
    6.             if (Convert.ToInt32(text_whichCar.Text) > 4 || !match||text_whichCar.Text.Trim().Equals(String.Empty))  
    7.             // webBrowser1.Document.InvokeScript("PUTANDSEND");  
    8.             {  
    9.                 MessageBox.Show("您输入的不是数字,或者编号不在范围内!");  
    10.             }  
    11.             else  
    12.             {  
    13.                 string getdata_sql = "select * from 汽车轨迹数据 where 汽车编号=" + text_whichCar.Text;  
    14.                 whichCarData(getdata_sql);  
    15.             }  
    16.         }  


     

    //从数据库里的取出经纬度传送给JS
           

    [csharp] view plaincopyprint?
     
    1. public void whichCarData(string limit_sql)  
    2.        {        
    3.                OleDbDataReader DR = DBfunction.getread(limit_sql);  
    4.                ArrayList a = new ArrayList();  
    5.                while (DR.Read())  
    6.                {  
    7.                    a.Add(DR[2]);//经度  
    8.                    a.Add(DR[3]);//纬度  
    9.                    Rows_Num++;  
    10.                }  
    11.                if (Rows_Num == 0)  
    12.                    MessageBox.Show("该车辆,无历史信息!");  
    13.                else  
    14.                {  
    15.                    for (int i = 0; i <= 2 * Rows_Num - 1; i++)  
    16.                    {  
    17.                        pointArr[i] = Convert.ToDouble(a[i]);  
    18.                    }  
    19.   
    20.                    webBrowser1.Document.InvokeScript("DrawOrit1");  
    21.                }  
    22.        }  
    23.       //辅助方法  
    24.        //获取计数  
    25.        public int getRowsNumber()  
    26.        {  
    27.            return Rows_Num;  
    28.        }  
    29. //根据索引获取特定坐标  
    30.        public double Getpoints(int index)  
    31.        { return pointArr[index]; }  



    JS脚本如下:

    //------------从后台数据库获得点集合来画轨迹(无参数版本),测试可用

    [javascript] view plaincopyprint?
     
    1. function DrawOrit1()  
    2. {  
    3.  var Array=[];  
    4. var total_num= window.external.getRowsNumber();  
    5. for(var i=0;i<=2*total_num-1;i++)  
    6. {  
    7.  Array.push(window.external.Getpoints(i));  
    8. }  
    9.   
    10. var PointArr=[];  
    11. for(var i=0;i<=Array.length-1;i+=2)  
    12. {//偶数索引存经度,奇数存维度  
    13.   PointArr.push(new BMap.Point(Array[i],Array[i+1]));  
    14. }  
    15. var polyline = new BMap.Polyline(PointArr, {strokeColor:"blue", strokeWeight:6,   strokeOpacity:0.5});  //定义折线  
    16.   map.addOverlay(polyline);  
    17. window.external.ClearRows_num();//重置窗体计数器  
    18. }  


     


    5.打开绘图工具,这个工具可以画直线,圆,矩形等等,其中我这里用的主要是画圆的方法,画好圆后,可以得到哪些车辆在这个圆内,并将其标注出来(其实就是一个预警范围)。

    //开启画图工具按钮

    [csharp] view plaincopyprint?
     
    1. private void btnDrawPicture_Click(object sender, EventArgs e)  
    2.       {  
    3.           if (radio_Circle.Checked)  
    4.           { webBrowser1.Document.InvokeScript("drawCircle"); }  
    5.           else  
    6.           { webBrowser1.Document.InvokeScript("drawRec"); }  
    7.       }  


          

     //搜索当前车辆位置,返回各个车辆的坐标

    [csharp] view plaincopyprint?
     
    1. public double SearchAllCars(int index)  
    2.         {  
    3.              
    4.             string sql="select * from 汽车轨迹数据";  
    5.             OleDbDataReader dr= DBfunction.getread(sql);  
    6.            ArrayList allCars = new ArrayList();  
    7.             while (dr.Read())  
    8.             {  
    9.                 allCars.Add(dr[2]);  
    10.                 allCars.Add(dr[3]);  
    11.             }  
    12.             Danger_Num = allCars.Count;  
    13.             double[] sendto_JS = new double[allCars.Count];  
    14.             allCars.CopyTo(sendto_JS);  
    15.              
    16.                 return sendto_JS[index];  
    17.         }  
    18. //全局变量,返回有危险的车辆个数  
    19.         public int GetdangerNum()  
    20.         { return Danger_Num; }  


     

    JS脚本如下:

    [javascript] view plaincopyprint?
     
    1. <!--加载鼠标绘制工具-->  
    2. <script type="text/javascript" src="http://api.map.baidu.com/library/DrawingManager/1.4/src/DrawingManager_min.js"></script>  
    3. <link rel="stylesheet" href="http://api.map.baidu.com/library/DrawingManager/1.4/src/DrawingManager_min.css" />  
    4. //回调获得覆盖物的信息(修改后的版本,已测试可用)  
    5.     var complete=function(e)  
    6.    {  
    7.     overlays.push(e.overlay);  
    8.     if (e.drawingMode == BMAP_DRAWING_CIRCLE)   
    9.           {  
    10.             //随便赋值,刷新一遍数据库(此方法只为演示,实际中要另考虑算法)  
    11.           var test=  window.external.SearchAllCars(0);  
    12.              
    13.              
    14.          var circle_radius=e.overlay.getRadius();//半径  
    15.           //圆心  
    16.          var circle_point=new BMap.Point(e.overlay.getCenter().lng,e.overlay.getCenter().lat);  
    17.          //从WINFORM里取出数据  
    18.          var dangerCars=[];  
    19.          var pointlen=window.external.GetdangerNum();  
    20.    
    21.          for(var k=0;k<=pointlen-1;k++)  
    22.           {  
    23.              dangerCars.push(window.external.SearchAllCars(k));  
    24.           }  
    25.          var BMappoints=[];//创建百度地图接口规定的数组  
    26.          for(var j=0;j<=dangerCars.length-1;j+=2)  
    27.           {  
    28.             BMappoints.push(new BMap.Point(dangerCars[j],dangerCars[j+1]));  
    29.           }  
    30.             
    31.           for(var i=0;i<=BMappoints.length-1;i++)  
    32.           {  
    33.             if(map.getDistance(circle_point,BMappoints[i])<=circle_radius)  
    34.             {  
    35.                AddMarker(BMappoints[i]);//调用添加标注版本V3.0  
    36.             }      
    37.           }  
    38.             
    39.         }  
    40.             
    41.       };  
    42. //线条样式  
    43.     var styleOptions = {  
    44.         strokeColor:"blue",    //边线颜色。  
    45.         fillColor:"blue",      //填充颜色。当参数为空时,圆形将没有填充效果。  
    46.         strokeWeight: 3,       //边线的宽度,以像素为单位。  
    47.         strokeOpacity: 1,    //边线透明度,取值范围0 - 1。  
    48.         fillOpacity: 0.3,      //填充的透明度,取值范围0 - 1。  
    49.         strokeStyle: 'solid' //边线的样式,solid或dashed。  
    50.     }  
    51.     //实例化鼠标绘制工具  
    52.     var drawingManager = new BMapLib.DrawingManager(map, {  
    53.         isOpen: true, //是否开启绘制模式  
    54.         enableDrawingTool: true, //是否显示工具栏  
    55.         drawingToolOptions: {  
    56.             anchor: BMAP_ANCHOR_TOP_RIGHT, //位置  
    57.             offset: new BMap.Size(5, 5), //偏离值  
    58.             scale: 0.8, //工具栏缩放比例  
    59.             drawingTypes : [           
    60.             BMAP_DRAWING_CIRCLE,    
    61.             BMAP_DRAWING_RECTANGLE   
    62.          ]  
    63.   
    64.         },  
    65.         circleOptions: styleOptions, //圆的样式   
    66.         rectangleOptions: styleOptions //矩形的样式  
    67.     });  
    68.   
    69.       
    70.       
    71.     //添加鼠标绘制工具监听事件,用于获取绘制结果  
    72.    drawingManager.addEventListener('overlaycomplete',complete);  
    73.       
    74.  //drawingManager.enableCalculate();  
    75.   
    76.       
    77.     //----------------------公用方法,用元素id获取元素的值-------------------  
    78.     function $(id){  
    79.         return document.getElementById(id);  
    80.     }  
    81.   
    82.     //------------------画矩形,让WINFORM调用---------------  
    83.     function drawRec(){  
    84. drawingManager.setDrawingMode(BMAP_DRAWING_RECTANGLE);}  
    85.     //------------------画圆,让WINFORM调用----------------  
    86.      function drawCircle(){  
    87. drawingManager.setDrawingMode(BMAP_DRAWING_CIRCLE);}  
    88.     //------------------清除所有已画图形,让WINFORM调用--------------------  
    89.     function clearAll() {  
    90.         for(var i = 0; i < overlays.length; i++){  
    91.             map.removeOverlay(overlays[i]);  
    92.         }  
    93.         overlays.length = 0  
    94.     }  


     


        这个功能比较复杂,必须要加入前两行的库连接才可以。因为画圆可以得到圆心和半径,所以我只需要从数据库里取出点,然后一一测量其与圆心的距离,然后和半径比较,只要小于半径则就在圆内标注。起初头让我画矩形,画矩形的DEMO如下:

    [javascript] view plaincopyprint?
     
    1. //回调获得覆盖物信息,未使用该版本  
    2.     var overlaycomplete = function(e){  
    3.         overlays.push(e.overlay);  
    4.         var result = "";  
    5.          
    6.         result += e.drawingMode + ":";  
    7.          
    8.         if (e.drawingMode == BMAP_DRAWING_CIRCLE) {  
    9.              
    10.             var circle_radius=e.overlay.getRadius();  
    11.             var circle_point=new BMap.Point(e.overlay.getCenter().lng,e.overlay.getCenter().lat);  
    12.             alert(map.getDistance(circle_point,tests[1]));  
    13.              for(var i=0;i<3;i++)  
    14.           {  
    15.             if(map.getDistance(circle_point,tests[i])<=circle_radius)  
    16.             {  
    17.                AddMarker(tests[i]);  
    18.             }      
    19.           }  
    20.             alert(result);  
    21.         }  
    22.         if (e.drawingMode == BMAP_DRAWING_POLYLINE || e.drawingMode == BMAP_DRAWING_POLYGON || e.drawingMode == BMAP_DRAWING_RECTANGLE) {  
    23.             result += ' 所画的点个数:' + e.overlay.getPath()[1].lng;  
    24.             alert(result);  
    25.         }  
    26.           
    27.     };  


     

        这里是修改的百度DEMO,其中有一行result += ' 所画的点个数:' + e.overlay.getPath()[1].lng;在百度原有的demo里是这样写的result += ' 所画的点个数:' + e.overlay.getPath().length;只会返回一个数据,我仔细看了下函数名,getPath(),而且还有length的属性,那么肯定是数组,而且是返回的边或者点的个数,而边一定是由点组成的,根据之前的Ployline函数可以推测,这个函数必定是一个存放多边形点的数组,那么我就试了试e.overlay.getPath()[1].lng,看能不能取到某个点的经度值,果然不出我所料,可以的,当时兴奋了好一阵子,有了这个方法,矩形的四个点就都能记录,那么就可以跟数据库里取出的点直接进行经纬度比较,也可以标注预警范围,不过还是没有用圆方便。

        由于时间确实很紧,手头还有事要做,只能写到这里了,欢迎交流,喷也行,哈哈。

  • 相关阅读:
    英语八级之路
    ASP.NET MVC 简易在线书店
    MySql 笔记
    自定义函数标签(JSTL)
    自定义标签(JSTL)
    Xml读取异常--Invalid byte 1 of 1-byte UTF-8 sequence
    JSTL核心标签库
    JSTL简介
    修改Servlet模板
    获取GET/POST提交的数据,并处理中文问题
  • 原文地址:https://www.cnblogs.com/hdu-edu/p/4207060.html
Copyright © 2011-2022 走看看