html5学习笔记地理定位

来源:互联网 发布:刷留言软件 编辑:程序博客网 时间:2024/04/30 09:18

navigator.geolocation.getCurrentPosition(successCallback,errorCallback, options); 

这是地理定位中重要的 API。对于一大类应用程序,只需用到这个 API。地理定位对象是标准导航器对象的一部分,它有几个方法,最常用的是 getCurrentPosition。访问用户位置是耗时的操作(就像在太空中找个卫星一样!),它还要取得用户的同意。因此这是一个异步操作。它的参数是回调函数:一个用于成功,一个用于失败。

成功函数将通过一个单独的 Position 类型的参数传递。这个对象有两个属性:一个时间戳的属性和称为坐标的 Coordinates 类型的属性。一个 Coordinates 对象有几个属性:

  1. latitude 
  2. longitude 
  3. altitude 
  4. accuracy 
  5. altitudeAccuracy 
  6. heading 
  7. speed 

这些参数不是在所有设备上都可用,除了 latitude、longitude 和 accuracy。如果支持地理定位 API,并且设备可以解析位置,就可以获取 latitude、longitude 和 accuracy。

失败 callback 函数将传递一个 PositionError 类型参数。PositionError 实例有两个参数:code 和 message。message 是设备特定的,可用于调试。code 有以下三个取值:

  1. PERMISSION_DENIED (1) 
  2. POSITION_UNAVAILABLE (2) 
  3. TIMEOUT (3) 

应用程序将根据 code 向用户友好显示失败消息。

请注意,W3C 规范还允许选择第三个参数。这包含花费多长时间取得用户位置的超时时间。尽管如此,像 iPhone 这样的设备目前还不支持,因此不建议使用。既然已经详细看过 API,看看实际如何使用的例子吧。

与 Twitter 集成

现在 hello world 混搭程序可通过某种方式使用 Twitter。在第一个例子中,将使用 Twitter 的搜索 API。它支持根据位置范围搜索微博。清单 2 显示的是本地 Twitter 搜索。

清单 2. 本地 Twitter 搜索

XML/HTML Code复制内容到剪贴板
  1. <!DOCTYPE html> 
  2. <html> 
  3. <head> 
  4. <meta name = "viewport" content = "width = device-width"/> 
  5. <title>Local Twitter Search</title> 
  6. <script type="text/javascript"> 
  7.     function startSearch(){ 
  8.         var gps = navigator.geolocation; 
  9.         if (gps){ 
  10.             gps.getCurrentPosition(searchTwitter,   
  11.                    function(error){ 
  12.                 alert("Got an error, code: " + error.code + " message: "   
  13. + error.message); 
  14.              }); 
  15.         } else { 
  16.             searchTwitter(); 
  17.         } 
  18.     } 
  19.     function searchTwitter(position){ 
  20.         var query = "http://search.twitter.com/search.json?callback=showResults&q="
  21.         query += $("kwBox").value; 
  22.         if (position){ 
  23.             var lat = position.coords.latitude; 
  24.             var long = position.coords.longitude; 
  25.             query += "&geocode=" + escape(lat + "," + long + ",50mi"); 
  26.         } 
  27.         var script = document.createElement("script"); 
  28.         script.src = query
  29.         document.getElementsByTagName("head")[0].appendChild(script); 
  30.     } 
  31. </script> 
  32. </head> 
  33. <body> 
  34.     <div id="main"> 
  35.         <label for="kwBox">Search Twitter:</label> 
  36.         <input type="text" id="kwBox"/> 
  37.         <input type="button" value="Go!" onclick="startSearch()"/> 
  38.     </div> 
  39.     <div id="results"> 
  40.     </div> 
  41. </body> 
  42. </html> 

用户可以在文本框输入搜索条目。单击按钮调用 startSearch 函数。此处就使用地理定位 API。首先检查其是否可用。如果可用,就调用 getCurrentPosition API。如回调成功,就使用 searchTwitter 函数。如果 callback 函数失败,就传递一个显示失败信息的终止参数。

如果浏览器成功找到位置,就调用 searchTwitter 函数。这里使用传递给函数的位置来向 Twitter 搜索查询添加 geocode 参数。清单 2搜索指定位置 50 英里内的帖子。为了调用 Twitter,要使用动态脚本标签,这是一项常称为 JSONP 的技术。Twitter 搜索 API 对此提供支持,它允许直接从浏览器调用 Twitter 搜索,不需要服务器。这由查询中的 callback 参数指出。请注意它设置成 showResults。这是所要调用的函数名称。在 清单 2 中未显示,因为这只是用来创建 UI,但在本文的源代码中已有包含(查看 下载)。 图 1 显示的是 清单 2 中代码的屏幕截图,这是在 iPhone 上运行的。


图 1. 从 iPhone 上搜索 Twitter
截屏显示iPhone 50 英里以内帖子的搜索结果 

本应用程序和其他位置感知应用程序一样,只要一次获得位置。尽管如此,其他应用程序在用户移动时要保持追踪。这些应用程序需要使用其他更高级的地理定位 API。

更高级的内容:追踪

有时候应用程序不只需要知道用户的当前位置,还需要在用户每次改变位置时及时更新。有个用于此目的的 API,是watchPosition。它与 getCurrentPosition 很相似,接收同样的参数。最大的不同是它返回 ID。这个 ID 可与最后的地理定位 APIclearWatch 联合使用。该函数会用到从 watchPosition 获得的 ID。当您调用 watchPosition,浏览器将会一直向您传入的成功回调函数发送更新,直到调用 clearWatch。持续不断获取用户位置信息将会耗尽设备资源,所以请谨慎使用这些 API。现在看看例子。

与 Google 地图集成

本例中,您将使用 Google 地图 API。这些 API 已对使用移动设备进行了优化,尤其是对 iPhone 和 Android 平台。这使得它们对移动 Web 开发人员很有吸引力,尤其是位置感知应用程序。以下的应用程序示例将会在地图上显示用户位置,并且在每次用户改变位置时更新。清单 3 是映射代码。

清单 3. 使用 Geolocation 映射应用程序

XML/HTML Code复制内容到剪贴板
  1. <html>   
  2. <head>   
  3. <meta name="viewport" content="initial-scale=1.0, user-scalable=no" /> 
  4. <meta http-equiv="content-type" content="text/html; charset=UTF-8"/>   
  5. <title>I'm tracking you!</title>   
  6. <script type="text/javascript" src="http://maps.google.com/maps/api/js? 
  7.      sensor=true"></script>   
  8. <script type="text/javascript"> 
  9.     var trackerId = 0
  10.     var geocoder; 
  11.     var theUser = {}; 
  12.     var map = {}; 
  13.     function initialize() { 
  14.         geocoder = new google.maps.Geocoder(); 
  15.         if (navigator.geolocation){ 
  16.             var gps = navigator.geolocation; 
  17.             gps.getCurrentPosition(function(pos){ 
  18.                 var latLng = new google.maps.LatLng(pos.coords. 
  19. latitude,pos.coords.longitude); 
  20.                 var opts = {zoom:12, center:latLng, mapTypeId:   
  21. google.maps.MapTypeId.ROADMAP}; 
  22.                 map = new google.maps.Map($("map_Canvas"), opts); 
  23.                 theUser = new google.maps.Marker({ 
  24.                     position: latLng, 
  25.                     map: map, 
  26.                     title: "You!" 
  27.                 }); 
  28.                 showLocation(pos); 
  29.             }); 
  30.             trackerId = gps.watchPosition(function(pos){ 
  31.                 var latLng = new google.maps.LatLng(pos.coords.latitude,pos. 
  32. coords.longitude); 
  33.                 map.setCenter(latLng); 
  34.                 theUser.setPosition(latLng); 
  35.                 showLocation(pos); 
  36.             }); 
  37.         } 
  38.   } 
  39. </script>   
  40. </head>   
  41. <body style="margin:0px; padding:0px;" onload="initialize()">   
  42.     <div id="superbar">       
  43.         <span class="msg">Current location:   
  44.               <span id="location"></span> 
  45.           </span> 
  46.           <input type="button" value="Stop tracking me!"   
  47. onclick="stopTracking()"/> 
  48.       </div> 
  49.   <div id="map_canvas" style="width:100%; height:90%; float:left;   
  50. border: 1px solid black;"> 
  51.   </div>   
  52. </body>   
  53. </html>   

一旦文档主体加载,就调用 initialize 函数。该函数检查浏览器是否支持地理定位。如果支持,就调用 getCurrentPosition,与 清单 2 中的前个例子一样。当它获取位置,就使用 Google 地图 API 创建地图。请注意如何使用纬度和经度来创建 google.maps.LatLng实例。该对象用于使地图居中。下一步,创建地图上的标记来表示用户当前位置。该标记再次用到从地理定位 API 接收到的纬度和经度。

创建地图并放置标记后,开始追踪用户。捕获从 watchPosition 中返回的 ID。无论何时接收到新的位置,都将地图在新位置重新居中,并将标记移到新位置。清单 4 显示了需要了解的另两个函数。

清单 4. 地理编码和取消追踪函数

JavaScript Code复制内容到剪贴板
  1. function showLocation(pos){ 
  2.     var latLng = new google.maps.LatLng(pos.coords.latitude,pos.coords.longitude); 
  3.     if (geocoder) { 
  4.         geocoder.geocode({'latLng': latLng}, function(results, status) { 
  5.           if (status == google.maps.GeocoderStatus.OK) { 
  6.             if (results[1]) { 
  7.                 $("location").innerHTML = results[1].Formatted_address; 
  8.             }   
  9.           }   
  10.         }); 
  11.       }         
  12. function stopTracking(){ 
  13.     if (trackerId){ 
  14.         navigator.geolocation.clearWatch(trackerId); 
  15.     } 

在 清单 3 中,当地图初始绘制及接收到用户位置更新时,调用 showLocation 函数。该函数如 清单 4 所示。它使用的是google.maps.Geocoder 实例(在 清单 3 的 initialize 函数开始处创建)。这个 API 可执行地理编码或者接收地址将其转换为映射坐标(纬度和经度)。它还执行逆向地理编码 — 将映射坐标转换成实际位置。本例中,使用了地理定位 API 生成的坐标,并使用 Google 地图 API 对其逆向编码。结果显示在屏幕上。

清单 4 中最后一个函数是 stopTracking 函数,当用户单击 清单 3 的 HTML 生成的按钮时调用。此处当首次调用 watchPosition 函数时得到 trackerId。只要简单地将其传递给 clearWatch 函数,浏览器/设备就会停止获取用户位置并停止调用 JavaScript。图 2 显示的是正在使用的追踪应用程序的屏幕截图。


图 2. 追踪应用程序
屏幕截图显示的是追踪应用程序创建的地图和位置标记。 

当然,要实际测试追踪,需要改变位置。可以使用 Google App Engine,因为它能将您的 Web 应用程序上传到公共可达位置。然后可以直接在连接良好的移动设备中测试。一旦完成,您可以乘坐公共交通工具,或者是让别人开车带您四处走走,看看您的 Web 应用程序对不断改变的位置做出的响应。



原创粉丝点击