基于Openlayers3的地图轨迹及其优化

2023-11-02 00:10

本文主要是介绍基于Openlayers3的地图轨迹及其优化,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

一、背景
项目线上系统经常出现一个问题,当地图轨迹点较多后者出现跨度较大的跳跃点时,地图缩放轨迹计算会导致浏览器比较卡,非常影响用户体验,根本原因是因为地图轨迹在进行缩放时,会在前端重新计算轨迹箭头图层的位置信息,当看到计算入口代码时,发现计算比较暴力,计算时间复杂度太高,需要进行优化,通过网上查询,发现一个博主的做法能有效降低计算的时间复杂度(https://blog.csdn.net/freeland1/article/details/82113809),但实践后发现其存在一个问题,当存在两个点间来回的轨迹时,其做法只能显示一个方向的箭头,没有展示反向的箭头。

二、轨迹绘制及优化

组件地址
openlayershttps://openlayers.org/
rbushhttps://unpkg.com/rbush@2.0.1/rbush.min.js

注意:openlayers版本需v3.13.0及以上,低版本不支持不支持getCoordinateAt方法

附地图缩放时,轨迹箭头更新逻辑代码:

	/***地图缩放时,更新轨迹箭头*/updateTrackArrowStyle: function (geometry, lineWidth, lineColor, arrowIcon) {var _this = this;var trackLine = geometry;var zoom = window.map.getView().getZoom();var distance = 57*(19-zoom)*(19-zoom);//箭头间隔随地图层级变化var styles = [new ol.style.Style({stroke: new ol.style.Stroke({color: lineColor,width: lineWidth})})];var length = _this.getLineLength(trackLine);if(length < 2 * distance){if(length < distance){distance = length / 3;}else{distance = length / 4;}}//对segments建立btree索引var tree = rbush();//路段数var max_num = 1;var geomLength = 0;trackLine.forEachSegment(function(start, end) {var dx = end[0] - start[0];var dy = end[1] - start[1];var rotation = Math.atan2(dy, dx);var geom = new ol.geom.LineString([start,end]);var extent = geom.getExtent();geomLength += _this.getLineLength(geom);var min_num = max_num;max_num = parseInt(geomLength / distance);//计算每一段轨迹上箭头在整段轨迹中的索引var item = {minX: extent[0],minY: extent[1],maxX: extent[2],maxY: extent[3],geom: geom,min_num: min_num,max_num: max_num,rotation_o : null,rotation_n : null,rotation: rotation};tree.insert(item);});var recExtent = map.getView().calculateExtent(map.getSize());//箭头总数var arrowsNum = parseInt(length / distance);var isRepeat = true;for(var i = 1;i < arrowsNum;i++){var arrowIcon = arrowIcon;var arraw_coor = trackLine.getCoordinateAt(i*1.0/arrowsNum);var tol = 0.1;var arraw_coor_buffer = [arraw_coor[0]-tol,arraw_coor[1]-tol,arraw_coor[0]+tol,arraw_coor[1]+tol];//进行btree查询var treeSearch = tree.search({minX: arraw_coor_buffer[0],minY: arraw_coor_buffer[1],maxX: arraw_coor_buffer[2],maxY: arraw_coor_buffer[3]});var arrow_rotation;if(treeSearch.length == 1){isRepeat = true;arrow_rotation = treeSearch[0].rotation;}else if(treeSearch.length > 1){var results = treeSearch.filter(function(item){var _tol = 0.1;//消除精度误差的容差if(item.geom.intersectsExtent([arraw_coor[0]-_tol, arraw_coor[1]-_tol, arraw_coor[0]+_tol, arraw_coor[1]+_tol]))return true;})if(results.length > 0){for(var j = 0;j < results.length;j++){if(i >= results[j].min_num && i <= results[j].max_num){//判断箭头是否在该段轨迹上if(i == results[j].min_num + 1){if(!results[j].rotation_o){isRepeat = true;for(var k=0;k<results.length;k++){results[k].rotation_o = results[j].rotation;}}else if(results[j].rotation_o == results[j].rotation){isRepeat = false;}else if(!results[j].rotation_n){isRepeat = true;for(var k=0;k<results.length;k++){results[k].rotation_n = results[j].rotation;}}else if(results[j].rotation_n == results[j].rotation){isRepeat = false;}}arrow_rotation = results[j].rotation;break;}}}}if(isRepeat){//判断是否已显示,当轨迹来回次数比较多时,如果不去冲,会在轨迹上堆积很多箭头styles.push(new ol.style.Style({geometry: new ol.geom.Point(arraw_coor),image: new ol.style.Icon({src: arrowIcon,anchor: [0.75, 0.5],rotateWithView: false,rotation: -arrow_rotation})}));}}return styles;},/***计算轨迹长度*/getLineLength : function(line){var coordinates = line.getCoordinates();var length = 0;var sourceProj = map.getView().getProjection();for (var i = 0, ii = coordinates.length - 1; i < ii; ++i) {var c1 = ol.proj.transform(coordinates[i], sourceProj, 'EPSG:4326');var c2 = ol.proj.transform(coordinates[i + 1], sourceProj, 'EPSG:4326');length += new ol.Sphere(6378137).haversineDistance(c1, c2);}return (Math.round(length * 100) / 100);}

三、效果图
1、无来回点
在这里插入图片描述
2、有来回点
在这里插入图片描述

如果您有好的改进建议,还请留言,不吝赐教!

这篇关于基于Openlayers3的地图轨迹及其优化的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/326747

相关文章

SpringBoot3实现Gzip压缩优化的技术指南

《SpringBoot3实现Gzip压缩优化的技术指南》随着Web应用的用户量和数据量增加,网络带宽和页面加载速度逐渐成为瓶颈,为了减少数据传输量,提高用户体验,我们可以使用Gzip压缩HTTP响应,... 目录1、简述2、配置2.1 添加依赖2.2 配置 Gzip 压缩3、服务端应用4、前端应用4.1 N

Spring Boot + MyBatis Plus 高效开发实战从入门到进阶优化(推荐)

《SpringBoot+MyBatisPlus高效开发实战从入门到进阶优化(推荐)》本文将详细介绍SpringBoot+MyBatisPlus的完整开发流程,并深入剖析分页查询、批量操作、动... 目录Spring Boot + MyBATis Plus 高效开发实战:从入门到进阶优化1. MyBatis

MyBatis 动态 SQL 优化之标签的实战与技巧(常见用法)

《MyBatis动态SQL优化之标签的实战与技巧(常见用法)》本文通过详细的示例和实际应用场景,介绍了如何有效利用这些标签来优化MyBatis配置,提升开发效率,确保SQL的高效执行和安全性,感... 目录动态SQL详解一、动态SQL的核心概念1.1 什么是动态SQL?1.2 动态SQL的优点1.3 动态S

Python如何使用__slots__实现节省内存和性能优化

《Python如何使用__slots__实现节省内存和性能优化》你有想过,一个小小的__slots__能让你的Python类内存消耗直接减半吗,没错,今天咱们要聊的就是这个让人眼前一亮的技巧,感兴趣的... 目录背景:内存吃得满满的类__slots__:你的内存管理小助手举个大概的例子:看看效果如何?1.

一文详解SpringBoot响应压缩功能的配置与优化

《一文详解SpringBoot响应压缩功能的配置与优化》SpringBoot的响应压缩功能基于智能协商机制,需同时满足很多条件,本文主要为大家详细介绍了SpringBoot响应压缩功能的配置与优化,需... 目录一、核心工作机制1.1 自动协商触发条件1.2 压缩处理流程二、配置方案详解2.1 基础YAML

MySQL中慢SQL优化的不同方式介绍

《MySQL中慢SQL优化的不同方式介绍》慢SQL的优化,主要从两个方面考虑,SQL语句本身的优化,以及数据库设计的优化,下面小编就来给大家介绍一下有哪些方式可以优化慢SQL吧... 目录避免不必要的列分页优化索引优化JOIN 的优化排序优化UNION 优化慢 SQL 的优化,主要从两个方面考虑,SQL 语

MySQL中慢SQL优化方法的完整指南

《MySQL中慢SQL优化方法的完整指南》当数据库响应时间超过500ms时,系统将面临三大灾难链式反应,所以本文将为大家介绍一下MySQL中慢SQL优化的常用方法,有需要的小伙伴可以了解下... 目录一、慢SQL的致命影响二、精准定位问题SQL1. 启用慢查询日志2. 诊断黄金三件套三、六大核心优化方案方案

Redis中高并发读写性能的深度解析与优化

《Redis中高并发读写性能的深度解析与优化》Redis作为一款高性能的内存数据库,广泛应用于缓存、消息队列、实时统计等场景,本文将深入探讨Redis的读写并发能力,感兴趣的小伙伴可以了解下... 目录引言一、Redis 并发能力概述1.1 Redis 的读写性能1.2 影响 Redis 并发能力的因素二、

使用Folium在Python中进行地图可视化的操作指南

《使用Folium在Python中进行地图可视化的操作指南》在数据分析和可视化领域,地图可视化是一项非常重要的技能,它能够帮助我们更直观地理解和展示地理空间数据,Folium是一个基于Python的地... 目录引言一、Folium简介与安装1. Folium简介2. 安装Folium二、基础使用1. 创建

使用国内镜像源优化pip install下载的方法步骤

《使用国内镜像源优化pipinstall下载的方法步骤》在Python开发中,pip是一个不可或缺的工具,用于安装和管理Python包,然而,由于默认的PyPI服务器位于国外,国内用户在安装依赖时可... 目录引言1. 为什么需要国内镜像源?2. 常用的国内镜像源3. 临时使用国内镜像源4. 永久配置国内镜