1.用canvas画一张地球贴图
1.地球geojson
js复制代码npm i @surbowl/world-geo-json-zh
2.画出地球贴图
众所周知,经度范围
[-180,180]
,纬度范围[-90,90]
那么显而易见,经度是维度的两倍长度,所以画出的canvas也是2:1
的图片,为了方便计算我这里将经纬度分别放大十倍画图,即宽度360*10
,高度180*10
1.canvas样式设置
let canvas = document.createElement('canvas'); canvas.width = 3600; canvas.height = 1800; let ctx = canvas.getContext('2d'); //背景颜色 ctx.fillStyle = that.bg; ctx.rect(0, 0, canvas.width, canvas.height); ctx.fill(); //设置地图样式 ctx.strokeStyle = that.borderColor;//描边颜色 ctx.lineWidth = that.borderWidth;//描边线宽 ctx.fillStyle = that.fillColor;//填充颜色 if (that.blurWidth) { ctx.shadowBlur = that.blurWidth;//边界模糊范围 ctx.shadowColor = that.blurColor;//边界模糊颜色 }
2.遍历geojson画区块
geojson
格式中features
数组里面每个geometry
包含了区块形状的坐标,对其进行遍历,分别画出区块就行
fetch('../node_modules/@surbowl/world-geo-json-zh/world.zh.json') .then((res) => res.json()) .then((geojson) => { console.log(geojson); geojson.features.forEach((a) => { if (a.geometry.type == 'MultiPolygon') {//多个区块组成 a.geometry.coordinates.forEach((b) => { b.forEach((c) => { drawRegion(ctx, c); }); }); } else {//单个区块 a.geometry.coordinates.forEach((c) => { drawRegion(ctx, c); }); } }); document.body.appendChild(canvas); });
画区块: 对每一组坐标点进行遍历,第一个点用moveTo
,后面的点全用lineTo
,为了保证每个区块形状都是独立的闭合形状,记得开始要用beginPath
,结束要用closePath
注意:
在canvas中坐标是以左上角的原点开始的,所以经纬度在canvas坐标是不适用的,需要转换,因为canvas的y轴正方向与纬度的方向是相反的,所以纬度需要取负值。
-lat
而经纬度有正负值,为了保证所有坐标都落在canvas可视范围内,要将坐标全部向canvas正轴方向偏移,经度偏移180度,纬度偏移90度,即
lng+180
,-lat+90
function drawRegion(ctx, c, geoInfo) { ctx.beginPath(); c.forEach((item, i) => {//转换经纬度坐标为canvas坐标点 let pos = [(item[0] + 180)*10, (-item[1] + 90)*10]; if (i == 0) { ctx.moveTo(pos[0], pos[1]); } else { ctx.lineTo(pos[0], pos[1]); } }); ctx.closePath(); ctx.fill(); ctx.stroke(); }
3.使用canvas画地球贴图
var that = { bg: '#000080',//背景色 borderColor: '#1E90FF',//描边颜色 blurColor: '#1E90FF',//边界模糊颜色 borderWidth: 1,//描边宽度 blurWidth: 5,//边界模糊范围 fillColor: 'rgb(30 ,144 ,255,0.3)',//区块填充颜色 };
原文链接:
此处为隐藏内容,请评论后查看隐藏内容,谢谢!
发表评论
2023-11-04 15:21:23回复