gpt4 book ai didi

java - 将纬度/经度点转换为墨卡托投影上的像素 (x,y)

转载 作者:IT老高 更新时间:2023-10-28 13:53:03 26 4
gpt4 key购买 nike

我正在尝试将 lat/long 点转换为 2d 点,以便可以将其显示在世界图像上——这是一个墨卡托投影。

我已经看到了执行此操作的各种方法以及一些关于堆栈溢出的问题 - 我尝试了不同的代码片段,虽然我得到了正确的像素经度,但纬度总是偏离似乎越来越多不过合理。

我需要公式来考虑图像大小、宽度等。

我试过这段代码:

double minLat = -85.05112878;
double minLong = -180;
double maxLat = 85.05112878;
double maxLong = 180;

// Map image size (in points)
double mapHeight = 768.0;
double mapWidth = 991.0;

// Determine the map scale (points per degree)
double xScale = mapWidth/ (maxLong - minLong);
double yScale = mapHeight / (maxLat - minLat);

// position of map image for point
double x = (lon - minLong) * xScale;
double y = - (lat + minLat) * yScale;

System.out.println("final coords: " + x + " " + y);

在我正在尝试的示例中,纬度似乎偏离了大约 30 像素。有什么帮助或建议吗?

更新

基于这个问题:Lat/lon to xy

我已经尝试使用提供的代码,但我仍然遇到一些纬度转换问题,经度很好。

int mapWidth = 991;
int mapHeight = 768;

double mapLonLeft = -180;
double mapLonRight = 180;
double mapLonDelta = mapLonRight - mapLonLeft;

double mapLatBottom = -85.05112878;
double mapLatBottomDegree = mapLatBottom * Math.PI / 180;
double worldMapWidth = ((mapWidth / mapLonDelta) * 360) / (2 * Math.PI);
double mapOffsetY = (worldMapWidth / 2 * Math.log((1 + Math.sin(mapLatBottomDegree)) / (1 - Math.sin(mapLatBottomDegree))));

double x = (lon - mapLonLeft) * (mapWidth / mapLonDelta);
double y = 0.1;
if (lat < 0) {
lat = lat * Math.PI / 180;
y = mapHeight - ((worldMapWidth / 2 * Math.log((1 + Math.sin(lat)) / (1 - Math.sin(lat)))) - mapOffsetY);
} else if (lat > 0) {
lat = lat * Math.PI / 180;
lat = lat * -1;
y = mapHeight - ((worldMapWidth / 2 * Math.log((1 + Math.sin(lat)) / (1 - Math.sin(lat)))) - mapOffsetY);
System.out.println("y before minus: " + y);
y = mapHeight - y;
} else {
y = mapHeight / 2;
}
System.out.println(x);
System.out.println(y);

使用原始代码时,如果纬度值为正,则返回负点,因此我对其稍作修改并使用极纬度进行了测试——应该是点 0 和点 766,它工作正常。但是,当我尝试不同的纬度值例如:58.07(就在英国北部)时,它显示为西类牙北部。

最佳答案

The Mercator map projection is a special limiting case of the Lambert Conic Conformal map projection with the equator as the single standard parallel. All other parallels of latitude are straight lines and the meridians are also straight lines at right angles to the equator, equally spaced. It is the basis for the transverse and oblique forms of the projection. It is little used for land mapping purposes but is in almost universal use for navigation charts. As well as being conformal, it has the particular property that straight lines drawn on it are lines of constant bearing. Thus navigators may derive their course from the angle the straight course line makes with the meridians. [1.]

Mercator projection

从球面纬度 φ 和经度 λ 推导出东向和北向投影坐标的公式是:

E = FE + R (λ – λₒ)
N = FN + R ln[tan(π/4 + φ/2)]

其中 λO 是自然起源的经度,FE 和 FN 是东偏和北偏。在球形墨卡托中,实际上并没有使用这些值,因此您可以将公式简化为

derivation of the mercator projection (wikipedia)

伪代码示例,因此可以适应每种编程语言。

latitude    = 41.145556; // (φ)
longitude = -73.995; // (λ)

mapWidth = 200;
mapHeight = 100;

// get x value
x = (longitude+180)*(mapWidth/360)

// convert from degrees to radians
latRad = latitude*PI/180;

// get y value
mercN = ln(tan((PI/4)+(latRad/2)));
y = (mapHeight/2)-(mapWidth*mercN/(2*PI));

来源:

  1. OGP Geomatics Committee,指导说明第 7 号,第 2 部分:坐标转换和转换
  2. Derivation of the Mercator projection
  3. National Atlas: Map Projections
  4. Mercator Map projection

编辑用 PHP 创建了一个工作示例(因为我不擅长 Java)

https://github.com/mfeldheim/mapStuff.git

EDIT2

墨卡托投影的漂亮动画 https://amp-reddit-com.cdn.ampproject.org/v/s/amp.reddit.com/r/educationalgifs/comments/5lhk8y/how_the_mercator_projection_distorts_the_poles/?usqp=mq331AQJCAEoAVgBgAEB&amp_js_v=0.1

关于java - 将纬度/经度点转换为墨卡托投影上的像素 (x,y),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14329691/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com