本文共 6729 字,大约阅读时间需要 22 分钟。
源代码地址:
我在使用Windows Mobile向请求基站信息时,发现第一次发送基站信息能够获取到一个经纬度,第二次却失败,直接导致异常退出应用程序。由于基站信息只能在真机上才能获取,无法进行调试,我就以一个中间web页面来向手机发送位置信息,再者拼接Json和解析的Json都放在web上进行处理,也减少Windows Mobile应用程序的负担,Windows Mobile只单纯的负责接收一个经纬度字符串。
1. 具体思路
首先要清楚一点的是,每一个基站都能够通过请求获取到一个经纬度。如果用户能够在短时间内获取到较多的基站信息,比如4个或5个,可以通过这几个基站的经纬度计算出比较准确的用户位置。
举个例子,比如我在WM上取到4个基站信息:
50554,9513,460,1
50325,9513,460,1
50584,9513,460,1
50041,9513,460,1
每一行的4个数值分别对应:CID, LAC, MCC, MNC
说明: |
---|
CID——CellID,表示基站号 LAC——Location Area Code,表示区域编号 MCC——Mobile Country Code,表示国家编号,中国是460 MNC——Mobile Network Code,表示移动网络编号,移动是0,联通是1 更详细的MCC, MNC信息可以查看: |
然后向Google发送基站信息是通过JSON串以Post的形式发送到,然后它会返回一个包含经纬度信息的JSON串。
RequestJson范例
{ "version": "1.1.0", "host": "maps.google.com", "cell_towers": [ { "cell_id": 42, "location_area_code": 415, "mobile_country_code": 310, "mobile_network_code": 410, "age": 0, "signal_strength": -60, "timing_advance": 5555 }, { "cell_id": 88, "location_area_code": 415, "mobile_country_code": 310, "mobile_network_code": 580, "age": 0, "signal_strength": -70, "timing_advance": 7777 } ], "wifi_towers": [ { "mac_address": "01-23-45-67-89-ab", "signal_strength": 8, "age": 0 }, { "mac_address": "01-23-45-67-89-ac", "signal_strength": 4, "age": 0 } ] }
然后从google那边返回来的位置信息如下:
ResponseJson样例
{ "location": { "latitude": 51.0, "longitude": -0.1, "altitude": 30.1, "accuracy": 1200.4, "altitude_accuracy": 10.6, "address": { "street_number": "100", "street": "Amphibian Walkway", "postal_code": "94043", "city": "Mountain View", "county": "Mountain View County", "region": "California", "country": "United States of America", "country_code": "US" } }, "access_token": "2:k7j3G6LaL6u_lafw:4iXOeOpTh1glSXe" }
说明: |
---|
即使只发送一个基站信息,也能够获取到一个经纬度。以上的RequestJson和ResponseJson只是样例,在实际Windows Mobile运用中,有可能取不到timing_adavance和singal_strength这两个参数,结合这两个参数定位会更准确一些。在我的代码例子中,我只取了CID, LAC, MCC, MNC参数。 关于JSON串中的属性各代表什么意思,详细请看: |
从上面的两端代码中我们可以大致了解到如何向Google发送基站请求,获取经纬度,下面我就以简单的代码来实现获取经纬度的方法。其实了解了上面的代码后,我们主要的工作就是拼接RequestJson串和解析
ResponseJson串,解析Json串我使用的是。2.实现
using System; ////// CellInfocs 的摘要说明 /// public class CellInfo { public string cid; public string lac; public string mcc; public string mnc; public string CID { get { return cid; } set { cid = value; } } public string LAC { get { return lac; } set { lac = value; } } public string MCC { get { return mcc; } set { mcc = value; } } public string MNC { get { return mnc; } set { mnc = value; } } }
using System; using System.Collections.Generic; using System.Text; using System.Net; using System.IO; using Newtonsoft.Json.Linq; ////// LocationService 的摘要说明 /// public class LocationService { public static string ErrorMessage; public LocationService(string postData) { GetLocationInfomation(postData); } ////// 返回经纬度信息 /// 格式如下: /// 22.506421,113.918245|22.497636,113.912647|22.496063,113.91121 /// /// ///public string GetLocationInfomation(string postData) { List list = GetCellInfos(postData); StringBuilder sb = new StringBuilder(); for (int i = 0; i < list.Count; i++) { CellInfo info = list[i]; //基本步骤 //1. 生成发往google的json串 //2. 接收google返回的json串 //3. 解析json串,只取得经纬度 //4. 拼接经纬度 string json = GenerateRequestJson(info); string content = GetResponseJson(json); string latLon = ParseResponseJson(content); sb.Append(latLon); sb.Append("|"); } return sb.ToString().Substring(0, sb.Length - 1); //return sb.ToString(); } /// /// 接收从手机端发送过来的数据 /// '|'分割对象,','分割属性 /// /// ///private List GetCellInfos(string postData) { string[] strInfos = postData.Split('|'); List list = new List (); for (int i = 0; i < strInfos.Length; i++) { string[] properties = strInfos[i].Split(','); CellInfo info = new CellInfo(); info.CID = properties[0]; info.LAC = properties[1]; info.MCC = properties[2]; info.MNC = properties[3]; list.Add(info); } return list; } /// /// 发送一个基站信息,并返回一个位置信息 /// 位置信息是以json串的形式存在 /// 需要对json串进行解析 /// /// private string GetResponseJson(string requestJson) { string responseJson = string.Empty; try { ServicePointManager.Expect100Continue = false; System.Text.ASCIIEncoding encoding = new System.Text.ASCIIEncoding(); byte[] data = encoding.GetBytes(requestJson); HttpWebRequest myRequest = (HttpWebRequest)WebRequest.Create(@"http://www.google.com/loc/json"); myRequest.Method = "POST"; myRequest.ContentType = "application/requestJson"; myRequest.ContentLength = data.Length; Stream newStream = myRequest.GetRequestStream(); // Send the data. newStream.Write(data, 0, data.Length); newStream.Close(); // Get response JSON string HttpWebResponse myResponse = (HttpWebResponse)myRequest.GetResponse(); StreamReader reader = new StreamReader(myResponse.GetResponseStream(), System.Text.Encoding.Default); responseJson = reader.ReadToEnd(); } catch (Exception ex) { ErrorMessage = ex.Message; } return responseJson; } ////// 解析从google Response的JSON串,获取经纬度 /// /// ///private string ParseResponseJson(string responseJson) { StringBuilder latLon = new StringBuilder(); JObject obj = JObject.Parse(responseJson); string lat = obj["location"]["latitude"].ToString(); string lon = obj["location"]["longitude"].ToString(); latLon.Append(lat); latLon.Append(","); latLon.Append(lon); return latLon.ToString(); } /// /// 生成发往http://www.google.com/loc/json的json串 /// 仅仅只有一个基站 /// /// ///private string GenerateRequestJson(CellInfo info) { string json = ""; json += "{"; json += "\"version\":\"1.1.0\"" + ","; json += "\"host\":\"maps.google.com\"" + ","; json += "\"cell_towers\":["; json += "{"; json += "\"cell_id\":" + info.CID + ","; json += "\"location_area_code\":" + info.LAC + ","; json += "\"mobile_country_code\":" + info.MCC + ","; json += "\"mobile_network_code\":" + info.MNC; json += "}"; json += "],"; json += "\"wifi_towers\": [{}]"; json += "}"; return json; } }
中间的web页面:Default.aspx(发送请求时,就请求这个页面)
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>
using System; public partial class _Default : System.Web.UI.Page { protected void Page_Load(object sender, EventArgs e) { string postData = Request.Form["POST_DATA"]; ResponseLocation(postData); } ////// 向手机端返回位置信息 /// /// public void ResponseLocation(string postData) { LocationService service = new LocationService(postData); string location = service.GetLocationInfomation(postData); Response.Write(location); } }
测试页面:index.html
本文转自94cool博客园博客,原文链接:http://www.cnblogs.com/94cool/archive/2012/05/22/2512745.html如需转载请自行联系原作者Index Page