当鼠标滑过地图,我们会扫一眼鼠标的地理位置,至少要能看到经纬度,好确认当前的范围和地物是否处在正常的位置。这对于C/S应用来说,是最为常见的辅助功能,即使是在B/S中,这似乎也不是难事,比如谷歌地图等都能提供这个功能,但是我们也知道,这些地图数据是固定投影的,获取经纬度坐标的途径是单一的,而这也不是本文要考虑的内容。

在系统应用中,B/S结构的GIS系统会发布具有不同投影类型的地图数据,而在客户端系统中为了显示鼠标的当前地理位置信息,通常我们会有三种解决办法:第一种,直接将鼠标的屏幕坐标转换为经纬度坐标并显示——仅限于发布的地图采用了经纬度坐标系;第二种,鼠标MouseMove过程中与服务器进行实时通信,将鼠标坐标转换为经纬度后返回给客户端显示——这要取决于网络是否稳定;第三种,则是在客户端进行坐标投影转换,相对来说,前两种解决办法都有一定的限制,而第三种解决办法则相对通用,也就是本文所讨论的话题。

当然,在开始讨论前,先明确一下有关的背景知识。坐标投影转换的资料,参考LionGG的文章http://hi.baidu.com/liongg/blog/item/81d7b48f8bdfb0ebf01f36fd.html,内容很详尽。有关Proj4http://trac.osgeo.org/proj/,是著名的开源C语言投影库,现在也包括了Javascript版(proj4js),ActionScript版(proj4as)等语言的实现。有关各种投影的参数定义,可参考,如果已经有定义,例如EPSG:2334:Xian 1980,可以搜索并查看其定义,我们能看到投影信息的多种表述,如proj4类型的表述为http://spatialreference.org/ref/epsg/2334/proj4/)。

本文主要针对客户端坐标投影转换的实现,通过实践SuperMap iClient for Flex与Openscales-proj4as,整理该流程如下:

1、获取openscales-proj4as-1.2.1.swc,当然现在以后会有更新版本,或者直接获取openscales的整个库——有API文档和源码,本文中直接使用源代码进行调试;

2、获取SuperMap iClient for Flex,当然也要有配套的SuperMap iServer,为了配合本次实践,这里发布了一个China400的地图,采用了Lambert Conformal Conic投影,中央经线104°,第一标准纬线24°,第二标准纬线40°,单位米;

1

2 3 4

效果如下图

3、现在利用Label显示鼠标的坐标位置看看效果。

1 privatefunction init():void

2 {3 this.myMap.addEventListener(MouseEvent.MOUSE_MOVE, mouseMoveHandler);4 }5 privatefunction mouseMoveHandler(event:MouseEvent):void6 {7 var point:Point=newPoint(event.stageX, event.stageY);8 var point2D:Point2D=this.myMap.screenToMap(point);9 this.coordInfo.text=point2D.x+""+point2D.y;10 }

效果如图

这个坐标的单位是米,对于我们来说这个坐标没能带来实际意义,我们还是要靠经纬度坐标来判断地理位置的。

4、现在我们使用openscales-proj4as来实现坐标转换的工作。想要熟悉openscales-proj4as的接口不是那么容易,API接口文档轻描淡写,如果不是GIS或测绘专业的人,是较难理解其含义的。现有的两个Package中,org.openscales.proj4as是主要的投影基础类定义,而org.openscales.proj4as.proj则是一些预定义的投影,见下表:

Package

Class

Description

org.openscales.proj4as

Datum

大地基准面,例如北京54

Proj4as

主类,提供静态方法做投影转换,transform方法是将一种投影类型的坐标转换为另一种投影类型的坐标值

ProjConstants

常量,其中有一些很实用

ProjPoint

坐标点

ProjProjection

投影类,任何投影的定义都可以继承该类,defs静态常量可以通过键值定义投影类型,forward方法是将经纬度坐标转换为投影坐标,inverse方法是将投影坐标转换为经纬度坐标

org.openscales.proj4as.proj

ProjParams

投影参数类,用于初始化各种预定义的投影

ProjLcc

预定义的兰伯特投影类

其他投影类

基于上表的描述就可以定义投影了,这里定义兰伯特投影的方式有两种,如下

1 privatestaticvar projLcc:Object;

1 /**

2 * 通过投影参数定义北京54兰伯特投影3 **/4 privatefunction defsProjLcc1():void5 {6 if(!projLcc)7 {8 //使用系统常量的定义Datum(大地基准面),Krassovsky 19429 var krass:Object=ProjConstants.Ellipsoid["krass"];10 var projLccData:ProjParams=newProjParams();11 //椭球长半轴12 projLccData.a=krass.a;13 //扁率14 projLccData.rf=krass.rf;15 //椭球长半轴,这里必须设置b,究其原因是功能接口没有利用a、b、rf关系做相互计算16 projLccData.b=projLccData.a*(1-1/projLccData.rf);17 //投影坐标系单位18 projLccData.units="m";19 //投影原点纬线20 projLccData.lat0=0.00000000;21 //投影中央经线22 projLccData.long0=104*Math.PI/180;23 //第一标准纬线24 projLccData.lat1=24*Math.PI/180;25 //第二标准纬线26 projLccData.lat2=40*Math.PI/180;27 //水平偏移量28 projLccData.x0=0.000;29 //垂直偏移量30 projLccData.y0=0.000;31 //使用投影参数实例化投影对象32 projLcc=newProjLcc(projLccData);33 //初始化投影参数,必须执行该接口34 projLcc.init();35 }36 }

1 /**

2 * 定义北京54兰伯特投影,3 * ProjProjection.defs[]静态常量定义键值对,4 * 10010为自定义的EPSG值5 * 键值内容参考投影参数6 **/7 privatefunction defsProjLcc2():void8 {9 if(!projLcc)10 {11 if(!ProjProjection.getProjProjection("10010"))12 {13 ProjProjection.defs["10010"]="+title=Beijing1954 +proj=lcc +towgs84=0.0000,0.0000,0.0000 +a=6378245.0000 +rf=298.3 +lat_0=0.00000000 +lon_0=104.000000000 +lat_1=24.000000000 +lat_2=40.000000000 +x_0=0.000 +y_0=0.000 +units=m +no_defs";14 }15 projLcc=ProjProjection.getProjProjection("10010");16 }17 }

接着获取鼠标的当前坐标信息,并转换为地理坐标,并采用投影转换的方法进行坐标转换,如下

privatefunction mouseMoveHandler(event:MouseEvent):void

{

var point:Point =newPoint(event.stageX, event.stageY);

var point2D:Point2D=this.myMap.screenToMap(point);

var sourceP:GeoPoint=newGeoPoint(point2D.x,point2D.y);

var destP:GeoPoint=coordTransform(sourceP);this.coordInfo.text=destP.x.toPrecision(8)+""+destP.y.toPrecision(8);

}

1 privatefunction coordTransform(sourceP:GeoPoint):GeoPoint2 {3 if(sourceP&&projLcc)4 {5 var sourceP2:ProjPoint=newProjPoint(sourceP.x, sourceP.y);6 var destP:ProjPoint=projLcc.inverse(sourceP2);7 var rp:GeoPoint=newGeoPoint(destP.x*180/Math.PI,destP.y*180/Math.PI);8 returnrp;9 }10 11 returnnull;

12 }

转换后的效果如下图

5、至此,本文就完成了基本的坐标转换,同时经过简单的测试,发现连续转换10000000对坐标点(兰伯托投影)共耗时17.689s,1000对则耗时2ms,性能适中,可以考虑做客户端地图动态投影。

结束之前,插上一句,不论是投影之间的坐标转换实现动态投影,还是投影的经纬度转换,都有应用价值,也希望各种客户端应用系统都能结合Proj4实现坐标转换。

proj4经纬度bl转换xy_在Web客户端中基于Proj4实现坐标转换相关推荐

  1. proj4经纬度bl转换xy_多种坐标系之间的转换之Proj.NET_转载

    Proj.NET (http://www.codeplex.com/ProjNET)是一个.NET下开源的空间参照和投影引擎,遵循OGC相关标准.负责人(Coordinators )是D_Guidi ...

  2. proj4经纬度bl转换xy_用Excel转换经纬度BL到北京54系平面坐标

    第三行,A3单元格输入所在地的中央子午线(如不知道可以查阅资料计算),以度分秒的形式输入. B3中输入=INT(A3) (INT(A3*100)-INT(A3)*100)/60 (A3*10000-I ...

  3. asp.net中使用excel类导出Excel文件,并导出到web客户端中遇到的问题

    asp.net中使用excel类导出Excel文件,并导出到web客户端中遇到错误: 检索Com类工厂中CLSID为{000245-0000-0000-C000-000000000046}的组件失败, ...

  4. Web应用中基于密码的身份认证机制(表单认证、HTTP认证: Basic、Digest、Mutual)

    Web应用中基于密码的身份认证机制 背景概念 认证(Authentication) 会话管理 1 表单认证(Form-Based Authentication) 1.1 介绍 1.2 流程 2 通用的 ...

  5. 初探Web客户端追踪技术

    初探Web客户端追踪技术 http://zoo.zhengcaiyun.cn/blog/article/webclient 前言 案例1 当我们首次浏览网站时,在网页的下方位置经常会出现提示,询问是否 ...

  6. Zimbra的Web客户端国际字体的控制机制及定制方法

    为什么80%的码农都做不了架构师?>>>    前些日子,在论坛中提出了一个"关于开发Zimbra增补程序的设想",有开客提到如何在Zimbra的Web界面中加入 ...

  7. Zoom的Web客户端与WebRTC有何不同?

    Zoom是非常出色的视频会议平台,拿Zoom的web客户端和WebRTC对比似乎有失公允.重要的是,未来WebRTC还会不断做明智的改进. 文 / Philipp Hancke 译 / 龙艳 原文 h ...

  8. php计算格子xy,经纬度BL和直角坐标XY的正算反算 PHP代码

    这篇文章主要介绍了经纬度BL和直角坐标XY的正算反算 PHP代码,有着一定的参考价值,现在分享给大家,有需要的朋友可以参考一下 这里是用的北京54坐标6度分带.需要用其他坐标可以修改参数$_a, $_ ...

  9. 【引用】在Eclipse中将java Project转换成Dynamic Web Project

    编辑工程的.project文件: 添加 <nature>org.eclipse.wst.common.project.facet.core.nature</nature> &l ...

最新文章

  1. 基础知识——列表简介(二)
  2. 开源WebGIS实施方案(一):开篇 [转]
  3. 【Socket】linux广播技术
  4. NestedScrollView平滑滑动嵌套 Fling
  5. 腾云驾雾的计算,让你蒙圈了么?
  6. 蓝桥杯之--神秘三位数
  7. Qt工作笔记-ListWidget拖动(拖拽)到QGraphicsScene【补坑】【Qt视图框架补坑】
  8. hibernate、java、数据库对应类型
  9. 芯片14纳米与7纳米相比,是不是芯片大一点,性能差不太多呢?
  10. “芯”视野主题系列—— 加密芯片在医疗、美容行业内的应用
  11. ZENG msgbox仿qq提示
  12. Fiddler原理~知多少?
  13. testmeshpro合批_UGUI合批原理笔记
  14. android 显示线方向,Android recycleview 分割线彩蛋
  15. AD8226+AD5293
  16. java 条形码校验_Java 之 商品条形码的验证
  17. MySQL之学生成绩表查询语句解析
  18. PKU ACM 1006 生理周期
  19. Android Studio 使用百度移动生态SDK(广告联盟)
  20. 1024•假如程序员心想事成

热门文章

  1. 域名中做负载均衡 同一个域名随机访问多个服务器IP(阿里云云解析DNS权重配置)
  2. php判断文件名字包含秘密,sublime text--你所不知道的12个秘密
  3. 学习使用 mockjs
  4. 让工作变简单的10种方法
  5. linux登陆终端自动打开core文件功能
  6. php+常用函数总结,php常用函数总结
  7. 考试的判卷系统-stdafx
  8. 推荐5个很牛的开源项目
  9. OO第三单元单元总结
  10. CRC16(modbus)校验计算器的实现