当前位置: 首页 > news >正文

openlayers利用已知的三个经纬度的坐标点 , 绘制一个贝塞尔曲线

以下是使用OpenLayers根据三个经纬度点绘制贝塞尔曲线的完整实现方案。贝塞尔曲线通过控制点生成平滑曲线,特别适合绘制地图上的弧线、路径等。

实现思路

  1. 贝塞尔曲线原理:使用三个点(起点、控制点、终点)生成二阶贝塞尔曲线。
  2. 坐标转换:将WGS 84经纬度点转换为Web Mercator投影(EPSG:3857)以在地图上正确显示。
  3. 曲线计算:通过贝塞尔公式计算曲线上的多个点,形成近似曲线。
  4. 地图渲染:使用OpenLayers的LineString几何对象绘制曲线。

代码实现

<!DOCTYPE html>
<html lang="zh-CN">
<head><meta charset="UTF-8"><title>OpenLayers贝塞尔曲线绘制</title><script src="https://cdn.jsdelivr.net/npm/ol@7.3.0/dist/ol.js"></script><link href="https://cdn.jsdelivr.net/npm/ol@7.3.0/ol.css" rel="stylesheet"><style>.map {width: 100%;height: 400px;}</style>
</head>
<body><div id="map" class="map"></div><script>// 1. 定义三个经纬度点(起点、控制点、终点)const startPoint = [116.3, 39.9]; // 北京(起点)const controlPoint = [110.0, 30.5]; // 控制点(黄海海域)const endPoint = [121.4, 31.2]; // 上海(终点)// 2. 经纬度转Web Mercator投影const transformPoints = (points) => {return points.map(point => ol.proj.transform(point, 'EPSG:4326', 'EPSG:3857'));};// 3. 计算二阶贝塞尔曲线上的点function calculateBezierPoints(start, control, end, segments = 50) {const points = [];for (let t = 0; t <= 1; t += 1 / segments) {// 二阶贝塞尔公式: B(t) = (1-t)²P0 + 2(1-t)tP1 + t²P2const x = Math.pow(1 - t, 2) * start[0] + 2 * (1 - t) * t * control[0] + Math.pow(t, 2) * end[0];const y = Math.pow(1 - t, 2) * start[1] + 2 * (1 - t) * t * control[1] + Math.pow(t, 2) * end[1];points.push([x, y]);}return points;}// 4. 转换坐标并计算贝塞尔曲线const [startMerc, controlMerc, endMerc] = transformPoints([startPoint, controlPoint, endPoint]);const bezierPoints = calculateBezierPoints(startMerc, controlMerc, endMerc, 100);// 5. 创建地图const map = new ol.Map({target: 'map',layers: [new ol.layer.Tile({source: new ol.source.OSM()  // 使用OpenStreetMap作为底图})],view: new ol.View({center: ol.proj.transform([118, 35], 'EPSG:4326', 'EPSG:3857'),zoom: 5})});// 6. 创建贝塞尔曲线要素const bezierCurve = new ol.geom.LineString(bezierPoints);const feature = new ol.Feature({geometry: bezierCurve,name: '贝塞尔曲线'});// 7. 设置曲线样式feature.setStyle(new ol.style.Style({stroke: new ol.style.Stroke({color: 'rgba(255, 0, 0, 0.8)',  // 红色半透明width: 3,lineDash: [10, 5]  // 虚线样式})}));// 8. 添加曲线到地图const vectorSource = new ol.source.Vector({features: [feature]});const vectorLayer = new ol.layer.Vector({source: vectorSource});map.addLayer(vectorLayer);// 9. 添加起点、控制点和终点标记const addMarker = (coord, label) => {const marker = new ol.Feature({geometry: new ol.geom.Point(coord),name: label});marker.setStyle(new ol.style.Style({image: new ol.style.Circle({radius: 6,fill: new ol.style.Fill({ color: 'blue' }),stroke: new ol.style.Stroke({ color: 'white', width: 2 })}),text: new ol.style.Text({text: label,font: '14px Arial',fill: new ol.style.Fill({ color: 'black' }),stroke: new ol.style.Stroke({ color: 'white', width: 2 }),offsetY: -10})}));vectorSource.addFeature(marker);};addMarker(startMerc, '起点');addMarker(controlMerc, '控制点');addMarker(endMerc, '终点');</script>
</body>
</html>

核心代码解析

  1. 贝塞尔曲线计算

    • 使用二阶贝塞尔公式:( B(t) = (1-t)^2P_0 + 2(1-t)tP_1 + t^2P_2 )
    • 通过参数t从0到1的变化,计算曲线上的多个点,segments参数控制精度
  2. 坐标转换

    • 使用ol.proj.transform()将WGS 84经纬度转换为Web Mercator坐标
    • 确保所有点在同一投影系统下计算
  3. 地图渲染

    • 使用LineString几何对象表示曲线
    • 通过Style设置曲线样式(颜色、宽度、虚线等)
    • 添加标记点显示起点、控制点和终点

效果展示

在这里插入图片描述

(注:实际运行时会显示OpenStreetMap底图和红色贝塞尔曲线)

相关文章:

  • JDBC执行sql过程
  • Unity.UGUI DrawCall合批笔记
  • onGAU:简化的生成式 AI UI界面,一个非常简单的 AI 图像生成器 UI 界面,使用 Dear PyGui 和 Diffusers 构建。
  • 移动零--双指针
  • 【Java ee初阶】网络原理
  • P1725 琪露诺
  • 代码随想录第41天:图论2(岛屿系列)
  • PPT图表怎么制作?说5款自己使用过的PPT图表制作工具
  • 遗传算法组卷系统实现(Java版)
  • Web 架构之容灾方案深度解析
  • ThinkPad T440P如何从U盘安装Ubuntu24.04系统
  • Cadence学习笔记之---导入PCB板框、网表
  • 贪心算法专题(Part2)
  • 简述Web和HTTP
  • 机器学习 day02
  • 【OpenCV】imread函数的简单分析
  • 计算机网络基础科普
  • 学习黑客了解Python3的“HTTPServer“
  • 社区商城分销合作合规承诺书
  • MacOS 用brew 安装、配置、启动Redis
  • 王毅同印度国家安全顾问多瓦尔通电话
  • 这座古村,藏着多少赣韵风华
  • 花2万多在海底捞办婚礼,连锁餐企要抢酒楼的婚宴生意?
  • 保证断电、碰撞等事故中车门系统能够开启!隐藏式门把手将迎来强制性国家标准
  • 98年服装“厂二代”:关税压力下,我仍相信中国供应链|湃客Talk
  • 外交部答澎湃:美方攻击抹黑中加关系与合作的卑劣图谋不会得逞