标签: gis投影坐标geotools
2015-12-11 09:28 3908人阅读 收藏 举报
昨天,有朋友要我帮忙看看一个将经纬度坐标转换成墨卡托投影(墨卡托投影有很多变种,我也不知道他说的是哪一种)的程序,他说转换以后的坐标精度太差。当时,他的程序没怎么看懂,然后研究了一下Geotools,自己写了一个转换小程序,很简单的几行代码!
Geotools是Java语言编写的开源GIS工具包。该项目已有十多年历史,生命力旺盛,代码非常丰富,包含多个开源GIS项目,并且基于标准的GIS接口。Geotools主要提供各种GIS算法,各种数据格式的读写和显示。由于Geotools库依赖比较复杂,所以在Eclipse中我采用Maven进行建构。对于在Eclipse下怎么使用Maven,请自己百度之。貌似最新的Eclipse是直接集成Maven插件的不需要自己单独安装了。虽说Eclipse不需要安装Maven插件了,可以使用Eclipse自带的Eclipse Maven插件,但是还是建议自己安装一个最新的Maven二进制包。
在Eclipse新建Maven工程,添加库和依赖:
这里主要添加的是要下载Geotools的库:
<repositories> <repository> <id>maven2-repository.dev.java.net</id> <name>Java.net repository</name> <url>http://download.java.net/maven/2</url> </repository> <repository> <id>osgeo</id> <name>Open Source Geospatial Foundation Repository</name> <url>http://download.osgeo.org/webdav/geotools/</url> </repository> </repositories>
以及用到的Geotools库:
<dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.12</version> <scope>test</scope> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-referencing</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-epsg-wkt</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-api</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>com.vividsolutions</groupId> <artifactId>jts</artifactId> <version>1.13</version> </dependency> </dependencies>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
最后的pom.xml文件如下:
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>cn.tzy</groupId> <artifactId>geotools</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>geotools</name> <url>http://maven.apache.org</url> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <geotools.version>14.1</geotools.version> </properties> <repositories> <repository> <id>maven2-repository.dev.java.net</id> <name>Java.net repository</name> <url>http://download.java.net/maven/2</url> </repository> <repository> <id>osgeo</id> <name>Open Source Geospatial Foundation Repository</name> <url>http://download.osgeo.org/webdav/geotools/</url> </repository> </repositories> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.12</version> <scope>test</scope> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-referencing</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-epsg-wkt</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>org.geotools</groupId> <artifactId>gt-api</artifactId> <version>${geotools.version}</version> </dependency> <dependency> <groupId>com.vividsolutions</groupId> <artifactId>jts</artifactId> <version>1.13</version> </dependency> </dependencies></project>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
下面开始写程序:
package cn.tzy.geotools;import org.geotools.geometry.jts.JTS;import org.geotools.referencing.CRS;import org.geotools.referencing.crs.DefaultGeographicCRS;import org.opengis.geometry.MismatchedDimensionException;import org.opengis.referencing.FactoryException;import org.opengis.referencing.crs.CoordinateReferenceSystem;import org.opengis.referencing.operation.MathTransform;import org.opengis.referencing.operation.TransformException;import com.vividsolutions.jts.geom.Coordinate;import com.vividsolutions.jts.geom.GeometryFactory;import com.vividsolutions.jts.geom.Point;/** * Hello world! * */public class CoordConverter { public static double[] convert(double lon, double lat) throws FactoryException, MismatchedDimensionException, TransformException { Coordinate sourceCoord = new Coordinate(lon, lat); GeometryFactory geoFactory = new GeometryFactory(); Point sourcePoint = geoFactory.createPoint(sourceCoord); final String strWKTMercator = "PROJCS[\"World_Mercator\"," + "GEOGCS[\"GCS_WGS_1984\"," + "DATUM[\"WGS_1984\"," + "SPHEROID[\"WGS_1984\",6378137,298.257223563]]," + "PRIMEM[\"Greenwich\",0]," + "UNIT[\"Degree\",0.017453292519943295]]," + "PROJECTION[\"Mercator_1SP\"]," + "PARAMETER[\"False_Easting\",0]," + "PARAMETER[\"False_Northing\",0]," + "PARAMETER[\"Central_Meridian\",0]," + "PARAMETER[\"latitude_of_origin\",0]," + "UNIT[\"Meter\",1]]"; CoordinateReferenceSystem mercatroCRS = CRS.parseWKT(strWKTMercator); MathTransform transform = CRS.findMathTransform(DefaultGeographicCRS.WGS84, mercatroCRS); Point targetPoint = (Point) JTS.transform(sourcePoint, transform); double[] targetCoord = {targetPoint.getX(), targetPoint.getY()}; return targetCoord; } public static double[] convert(double lon, double lat, String strWKT) throws FactoryException, MismatchedDimensionException, TransformException { Coordinate sourceCoord = new Coordinate(lon, lat); GeometryFactory geoFactory = new GeometryFactory(); Point sourcePoint = geoFactory.createPoint(sourceCoord); CoordinateReferenceSystem mercatroCRS = CRS.parseWKT(strWKT); MathTransform transform = CRS.findMathTransform(DefaultGeographicCRS.WGS84, mercatroCRS); Point targetPoint = (Point) JTS.transform(sourcePoint, transform); double[] targetCoord = {targetPoint.getX(), targetPoint.getY()}; return targetCoord; } public static void main( String[] args ) throws Exception { double longitude = 113.926982; double latitude = 22.53089; double[] coordinate = convert(longitude, latitude); System.out.println("X: " + coordinate[0] + ", Y: " + coordinate[1]); }}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
程序很简单:CRS.findMathTransform()方法定义转换的坐标系,JTS.transform()进行坐标的转换。
其中第一个方法是我专门写的将WGS84经纬度坐标转成World Mercator投影坐标的函数。第二个函数是对第一个函数的抽象,将要转换到的投影坐标提取出来作为参数,如果想要转换到某种投影坐标系,只需要传递一个该投影坐标系的OGC WKT(Well Known Text)给函数,就可以做转换了。常见投影的WKT表示可以在http://spatialreference.org/进行查询!
看懂了该程序的朋友,就可以写自己的实现了,上面只是一个简单的Hello World示例程序。