问题来源于4528投影使用4528投影view时间地图是空白的,所以开始正确Proj4js以及投影转换的剥茧,这里记录识和最终结论。
官网示例和Proj4js的使用
OL示例见wms-image-custom-proj 这里简单介绍一下proj4,我认知的proj4是一组基于一些约定参数组成的定义坐标参考的参数WKT比较简单,省略了WKT完整的参数定义。例如,4528wkt
PROJCRS["CGCS2000 / 3-degree Gauss-Kruger zone 40", BASEGEOGCRS["China Geodetic Coordinate System 2000", DATUM["China 2000", ELLIPSOID["CGCS2000",6378137,298.257222101, LENGTHUNIT["metre",1]]], PRIMEM["Greenwich",0, ANGLEUNIT["degree",0.0174532925199433]], ID["EPSG",4490]], CONVERSION["3-degree Gauss-Kruger zone 40", METHOD["Transverse Mercator", ID["EPSG",9807]], PARAMETER["Latitude of natural origin",0, ANGLEUNIT["degree",0.0174532925199433], ID["EPSG",8801]], PARAMETER["Longitude of natural origin",120, ANGLEUNIT["degree",0.0174532925199433], ID["EPSG",8802]], PARAMETER["Scale factor at natural origin",1, SCALEUNIT["unity",1], ID["EPSG",8805]], PARAMETER["False easting",40500000, LENGTHUNIT["metre",1], ID["EPSG",8806]], PARAMETER["False northing",0, LENGTHUNIT["metre",1], ID["EPSG",8807]]], CS[Cartesian,2], AXIS["northing (X)",north, ORDER[1], LENGTHUNIT["metre",1]], AXIS["easting (Y)",east, ORDER[2], LENGTHUNIT["metre",1]], USAGE[ SCOPE["Cadastre, engineering survey, topographic mapping (large scale)."], AREA["China - onshore between 118°30'E and 121°30'E."], BBOX[24.43,118.5,53.33,121.5]], ID["EPSG",4528]]
它的proj4
+proj=tmerc +lat_0=0 +lon_0=120 +k=1 +x_0=40500000 +y_0=0 +ellps=GRS80 +units=m +no_defs
详细介绍见参考 我对该示例做了简化,去掉了范围,更换图层为OSM,在vue里测试
import Map from "ol/Map";
import View from "ol/View";
import * as Layer from "ol/layer";
import * as Source from "ol/source";
import Projection from "ol/proj/Projection";
import {
fromLonLat } from "ol/proj";
import proj4 from "proj4";
import {
register } from "ol/proj/proj4";
private mounted() {
// 这里定义编码和proj4参数
proj4.defs(
"EPSG:4549",
"+proj=tmerc +lat_0=0 +lon_0=120 +k=1 +x_0=500000 +y_0=0 +ellps=GRS80 +units=m +no_defs"
);
// 注册之后就可以使用epsg编码调用
register(proj4);
// 定义了底图 用的OSM
const base = new Layer.Tile({
source: new Source.OSM(),
});
const projection = new Projection({
code: "EPSG:4549",
units: "m",
});
// 初始化地图对象
const map = new Map({
layers: [base],
target: "map",
view: new View({
projection,
center: fromLonLat([120.015, 36.408], "EPSG:4549"),
zoom: 8,
}),
});
}
获取Proj4的方法
比较方便的方法是在https://epsg.io/里查询,但我一直访问不了,作为替代可以在QGIS里查询 点击右下角的坐标参考按钮,很直观,亲测和网站里获取的是一样的
2000带投影的Proj4的问题
如果使用epsg:4528的proj4和编码,地图会一片空白还不报错。我尝试了其他坐标系,有的行有的不行,对比之后发现凡是以‘CGCS2000 / 3-degree Gauss-Kruger zone’开头的都不行,而同样是两千带投影的‘CGCS2000 / 3-degree Gauss-Kruger CM’系列就没事 这两个坐标系范围啥的都一样,我对比了下他俩的proj4
4528(CGCS2000 / 3-degree Gauss-Kruger zone 40)
+proj=tmerc +lat_0=0 +lon_0=120 +k=1 +x_0=40500000 +y_0=0 +ellps=GRS80 +units=m +no_defs
4549(CGCS2000 / 3-degree Gauss-Kruger CM 120E)
+proj=tmerc +lat_0=0 +lon_0=120 +k=1 +x_0=500000 +y_0=0 +ellps=GRS80 +units=m +no_defs
除了+x_0的值,其他都一毛一样,所以问题八成出在这个参数上
如何治标不治本
研究了下,4528(CGCS2000 / 3-degree Gauss-Kruger zone 40)的+x_0的值40500000,代表40带,偏移500000米,如果去掉前边代表带号的40,就和4549的完全一样了。 估计是这种带号+偏移量的赋值方式不被支持,所以在使用4528的proj4时地图空白。 那么一种治标不治本的解决方法就来了,直接使用4549代替4528,或者使用4528,但是移除‘+x_0=40500000’里代表带号的‘40’。
如果有更好的建议欢迎提出,也欢迎指出错误,毕竟当初学的东西基本忘光了,很多都是基于猜测。