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

Vue项目中天地图动态标注的添加与删除实践

1. 天地图与Vue结合的基础准备在Vue项目中使用天地图API前需要先完成基础的环境配置。我推荐使用npm安装天地图JavaScript API的方式这样能更好地与现代前端工程化开发流程结合。首先在项目中执行npm install tdt-map安装完成后在main.js中全局引入天地图资源。这里有个小技巧建议把天地图密钥放在环境变量中管理import T from tdt-map import ../node_modules/tdt-map/dist/tdt.min.css Vue.prototype.$T T Vue.prototype.$tdtKey process.env.VUE_APP_TDT_KEY初始化地图组件时我习惯把地图实例挂载到Vue实例上方便全局调用。在组件mounted钩子中这样写mounted() { this.map new this.$T.Map(mapContainer, { center: new this.$T.LngLat(116.404, 39.915), zoom: 11, minZoom: 5, maxZoom: 18 }) }这里有个容易踩的坑天地图容器需要设置明确的高度。我建议在CSS中使用vh单位确保在不同设备上都能正常显示#mapContainer { width: 100%; height: 80vh; margin: 0; padding: 0; }2. 动态标注的创建与管理2.1 标注的批量创建实际项目中我们通常需要批量添加标注点。我封装了一个可复用的方法支持自定义图标和点击事件addMarkers(points, iconConfig, clickHandler) { const markers [] points.forEach(item { const marker new this.$T.Marker( new this.$T.LngLat(item.lng, item.lat), { icon: new this.$T.Icon({ iconUrl: iconConfig.url, iconSize: new this.$T.Point(iconConfig.width, iconConfig.height) }) } ) marker.customId item.id // 自定义标识 this.map.addOverLay(marker) if (clickHandler) { marker.addEventListener(click, () { clickHandler(item, marker) }) } markers.push(marker) }) return markers }使用时可以这样调用const hospitals this.addMarkers( [ {id: h1, lng: 116.404, lat: 39.915, name: 协和医院}, {id: h2, lng: 116.428, lat: 39.903, name: 301医院} ], { url: require(/assets/hospital.png), width: 32, height: 32 }, (item, marker) { this.showHospitalInfo(item) } )2.2 标注的自定义属性为了后续能精准控制特定标注我们需要给标注添加自定义属性。除了上面代码中的customId还可以扩展更多元数据marker.metaData { type: hospital, district: 海淀区, level: 三甲 }这样在后续操作时我们不仅能通过ID查找标注还能按类型、区域等属性进行筛选。3. 精准删除标注的实现方案3.1 基于标识的删除方法原始文章展示了通过遍历删除的方式这里我优化了一个更高效的版本removeMarkersByIds(ids) { const overlays this.map.getOverlays() overlays.forEach(overlay { if (overlay.customId ids.includes(overlay.customId)) { this.map.removeOverLay(overlay) } }) }这个方法支持批量删除调用时只需传入要删除的标注ID数组// 删除ID为h1和h2的标注 this.removeMarkersByIds([h1, h2])3.2 基于条件的动态筛选更灵活的做法是根据条件动态筛选要删除的标注removeMarkersByCondition(conditionFn) { const overlays this.map.getOverlays() overlays.forEach(overlay { if (conditionFn(overlay)) { this.map.removeOverLay(overlay) } }) }使用示例// 删除所有类型为医院的标注 this.removeMarkersByCondition( overlay overlay.metaData?.type hospital ) // 删除海淀区的三甲医院 this.removeMarkersByCondition( overlay overlay.metaData?.district 海淀区 overlay.metaData?.level 三甲 )4. 高级应用标注的状态管理4.1 使用Vuex管理标注状态在复杂项目中建议使用Vuex集中管理标注状态。首先定义store// store/modules/map.js const state { markers: [], visibleMarkerIds: [] } const mutations { ADD_MARKERS(state, markers) { state.markers [...state.markers, ...markers] }, TOGGLE_MARKERS(state, {ids, visible}) { if (visible) { state.visibleMarkerIds [...new Set([...state.visibleMarkerIds, ...ids])] } else { state.visibleMarkerIds state.visibleMarkerIds.filter(id !ids.includes(id)) } } }然后在组件中使用watch监听状态变化watch: { mapStore/visibleMarkerIds: { handler(newVal, oldVal) { // 找出需要新增的标注 const toAdd this.mapStore.markers.filter( m newVal.includes(m.customId) !oldVal.includes(m.customId) ) // 找出需要删除的标注 const toRemove oldVal.filter(id !newVal.includes(id)) // 执行更新 if (toAdd.length) this.addMarkers(toAdd) if (toRemove.length) this.removeMarkersByIds(toRemove) }, deep: true } }4.2 标注的动画效果为提升用户体验可以为标注添加显隐动画。这里实现一个淡入淡出效果async fadeMarker(marker, show true, duration 500) { const step 20 const delta 1 / (duration / step) if (show) { marker.setOpacity(0) this.map.addOverLay(marker) for (let op 0; op 1; op delta) { await new Promise(resolve setTimeout(resolve, step)) marker.setOpacity(op) } } else { for (let op 1; op 0; op - delta) { await new Promise(resolve setTimeout(resolve, step)) marker.setOpacity(op) } this.map.removeOverLay(marker) } }使用时可以这样调用// 淡入显示 this.fadeMarker(marker, true) // 淡出隐藏 this.fadeMarker(marker, false)5. 性能优化实践5.1 标注的聚类显示当地图缩放级别较小时可以使用标注聚类来提升性能。先安装聚类插件npm install tdt-map-cluster然后在项目中这样使用import MarkerCluster from tdt-map-cluster // 创建聚类实例 const cluster new MarkerCluster(this.map, { gridSize: 80, maxZoom: 15, styles: [{ url: require(/assets/cluster.png), size: new this.$T.Point(40, 40), textColor: #fff }] }) // 添加标注到聚类管理器 cluster.addMarkers(markers) // 需要删除时 cluster.removeMarkers(markersToRemove)5.2 可视区域优化当地图标注很多时可以只渲染可视区域内的标注updateVisibleMarkers() { const bounds this.map.getBounds() this.allMarkers.forEach(marker { const position marker.getLngLat() if (bounds.contains(position)) { if (!this.map.getOverlays().includes(marker)) { this.map.addOverLay(marker) } } else { this.map.removeOverLay(marker) } }) } // 监听地图移动事件 this.map.addEventListener(moveend, this.updateVisibleMarkers)6. 常见问题解决方案在实际开发中我遇到过几个典型问题值得分享。首先是天地图标注点击事件冒泡问题当地图上既有标注点击又有地图点击时会出现事件冲突。解决方案是marker.addEventListener(click, e { e.stopPropagation() // 处理标注点击逻辑 })其次是标注z-index的控制问题。天地图的标注默认是按添加顺序决定叠放层次如果需要手动控制// 将标注置顶 marker.setTop(true) // 设置具体z-index marker.setZIndex(100)还有一个常见问题是内存泄漏。在Vue组件销毁时务必清理所有标注和事件监听beforeDestroy() { // 移除所有标注 this.map.clearOverlays() // 移除事件监听 this.map.removeEventListener(moveend, this.updateVisibleMarkers) // 如果有聚类实例 if (this.cluster) { this.cluster.clearMarkers() } }7. 完整示例代码最后分享一个完整的Vue单文件组件示例实现了标注的增删改查template div div idmapContainer/div div classcontrol-panel button clickaddHospitalMarkers添加医院/button button clickremoveAllMarkers清除所有/button div v-formarker in markers :keymarker.id input typecheckbox v-modelmarker.visible changetoggleMarker(marker) {{ marker.name }} /div /div /div /template script export default { data() { return { map: null, markers: [ {id: h1, lng: 116.404, lat: 39.915, name: 协和医院, visible: true}, {id: h2, lng: 116.428, lat: 39.903, name: 301医院, visible: true} ], markerInstances: {} } }, mounted() { this.initMap() this.addHospitalMarkers() }, methods: { initMap() { this.map new this.$T.Map(mapContainer, { center: new this.$T.LngLat(116.404, 39.915), zoom: 12 }) }, addHospitalMarkers() { this.markers.forEach(item { if (item.visible !this.markerInstances[item.id]) { const marker new this.$T.Marker( new this.$T.LngLat(item.lng, item.lat), { icon: new this.$T.Icon({ iconUrl: require(/assets/hospital.png), iconSize: new this.$T.Point(32, 32) }) } ) marker.customId item.id this.map.addOverLay(marker) this.markerInstances[item.id] marker } }) }, toggleMarker(marker) { if (marker.visible) { this.addMarker(marker) } else { this.removeMarker(marker.id) } }, addMarker(markerData) { if (this.markerInstances[markerData.id]) return const marker new this.$T.Marker( new this.$T.LngLat(markerData.lng, markerData.lat), { icon: new this.$T.Icon({ iconUrl: require(/assets/hospital.png), iconSize: new this.$T.Point(32, 32) }) } ) marker.customId markerData.id this.map.addOverLay(marker) this.markerInstances[markerData.id] marker }, removeMarker(markerId) { if (!this.markerInstances[markerId]) return this.map.removeOverLay(this.markerInstances[markerId]) delete this.markerInstances[markerId] }, removeAllMarkers() { Object.values(this.markerInstances).forEach(marker { this.map.removeOverLay(marker) }) this.markerInstances {} this.markers.forEach(m m.visible false) } }, beforeDestroy() { this.map.clearOverlays() } } /script style #mapContainer { width: 100%; height: 80vh; } .control-panel { position: absolute; top: 20px; right: 20px; background: white; padding: 10px; z-index: 1000; } /style

相关文章:

Vue项目中天地图动态标注的添加与删除实践

1. 天地图与Vue结合的基础准备 在Vue项目中使用天地图API前,需要先完成基础的环境配置。我推荐使用npm安装天地图JavaScript API的方式,这样能更好地与现代前端工程化开发流程结合。首先在项目中执行: npm install tdt-map安装完成后&#xf…...

联邦卡尔曼滤波与分布式滤波在雷达多传感器轨迹估计中的性能对比与优化策略

1. 多传感器轨迹估计的技术挑战与需求 想象一下你正在指挥一个由多部雷达组成的防空系统,每部雷达都在追踪同一架飞机的轨迹。这些雷达分布在不同位置,有的在山顶,有的在海岸线,还有的在移动平台上。每部雷达都会产生带有噪声的测…...

从加权平均到多项式拟合:局部加权回归的进阶之路

1. 从加权平均到局部回归:理解核平滑的本质 我第一次接触核平滑方法时,被它优雅的数学形式深深吸引。想象你是一位气象学家,手头有一堆散乱的气温观测数据,想要绘制一条平滑的气温变化曲线。传统方法可能会对所有数据点一视同仁&a…...

K8s Kustomize介绍(Kubernetes官方声明式配置管理工具,通过叠加overlay方式定制资源)kubectl内置、Patch补丁机制、GitOps

文章目录 Kustomize 入门与实践指南:Kubernetes 原生配置管理利器一、什么是 Kustomize?二、为什么需要 Kustomize?三、核心概念1. Base(基础配置)2. Overlay(覆盖层)3. kustomization.yaml&…...

PCB接地设计

接地模拟小信号地和功率地必须分开。原则上功率地在顶层挨在一起放置(图8的左图),如果分割PGND而通过过孔在背面或内层连接的话(图8的右图),受过孔的寄生电阻和寄生电感的影响,可能会出现损耗增…...

三菱FX5U Socket通信避坑指南:被动模式下的5个常见错误与稳定连接秘诀

三菱FX5U Socket通信避坑指南:被动模式下的5个常见错误与稳定连接秘诀 在工业自动化领域,稳定可靠的通信是生产线持续运行的生命线。三菱FX5U系列PLC凭借其强大的以太网Socket通信能力,成为众多工程师的首选。然而,在实际应用中&a…...

新服务器上线优化调整

1. 写入到系统配置 重新登录终端生效配置&#xff0c;只对使用二进制启动的进程生效&#xff0c;对于使用systemd管理的进程不生效&#xff0c;已经运行的进程不生效。 cat >> /etc/security/limits.conf << EOF # 限制用户能打开的进程数 * soft nproc 1000000 * …...

Android音频开发避坑指南:搞懂AudioTrack的MODE_STATIC与MODE_STATIC内存模型差异

Android音频开发深度解析&#xff1a;AudioTrack的MODE_STATIC与MODE_STREAM内存模型实战对比 在移动端音频应用开发中&#xff0c;性能优化始终是工程师们需要直面的挑战。当你在开发一款高要求的音乐播放器或游戏音效系统时&#xff0c;是否遇到过音频播放延迟、内存占用异常…...

HFSS实战指南:从零到一完成矩形贴片微带天线参数化调优

1. HFSS与微带天线设计基础 刚接触HFSS时&#xff0c;我也曾被它复杂的界面吓到过。但用熟后发现&#xff0c;这简直就是射频工程师的"瑞士军刀"。就拿最常见的矩形贴片微带天线来说&#xff0c;用HFSS做参数化调优&#xff0c;效率比手工计算高太多了。先说说这个天…...

科学计算器统计功能实战:从基础操作到概率论应用

1. 科学计算器统计功能入门指南 第一次接触科学计算器的统计功能时&#xff0c;我被那一排排按键搞得晕头转向。记得大学概率论课上&#xff0c;教授突然说"现在请大家用计算器计算这组数据的标准差"&#xff0c;整个教室顿时响起此起彼伏的按键声和叹气声。如果你也…...

科研利器t-SNE降维实战:从特征可视化到深度学习模型诊断,一文掌握核心技巧!

1. 为什么t-SNE是科研可视化神器 第一次看到t-SNE生成的彩色散点图时&#xff0c;我正盯着屏幕上那团像星云般聚集的数据点发呆。那是我处理了三个月的基因表达数据&#xff0c;在PCA降维后依然像打翻的颜料盘&#xff0c;而t-SNE只用了几行代码就让不同癌症亚型自动分成了泾渭…...

Eye-in-Hand还是Eye-to-Hand?机器人视觉抓取中九点标定的选择与实战避坑

Eye-in-Hand还是Eye-to-Hand&#xff1f;机器人视觉抓取中九点标定的工程化选择 在自动化生产线调试现场&#xff0c;机械臂工程师小李盯着屏幕上飘忽不定的定位误差发愁——同样的九点标定流程&#xff0c;上周测试时精度还能控制在0.3mm以内&#xff0c;今天却突然漂移超过1m…...

保姆级教程:在Deepin/UOS上用DTK(Qt5)开发你的第一个桌面应用

零基础实战&#xff1a;在Deepin/UOS上使用DTK开发桌面应用全指南 从零开始搭建DTK开发环境 Deepin操作系统自带的DTK&#xff08;Deepin Tool Kit&#xff09;是一套基于Qt5的深度定制UI组件库&#xff0c;能让开发者快速构建符合Deepin/UOS统一风格的应用程序。对于刚接触这个…...

如何让8大网盘下载速度提升300%?解锁LinkSwift的下载新体验

如何让8大网盘下载速度提升300%&#xff1f;解锁LinkSwift的下载新体验 【免费下载链接】Online-disk-direct-link-download-assistant 一个基于 JavaScript 的网盘文件下载地址获取工具。基于【网盘直链下载助手】修改 &#xff0c;支持 百度网盘 / 阿里云盘 / 中国移动云盘 /…...

51单片机核心板PCB设计避坑指南:嘉立创EDA专业版实战(附免费打样尺寸秘诀)

51单片机核心板PCB设计避坑指南&#xff1a;嘉立创EDA专业版实战解析 第一次用嘉立创EDA专业版画51单片机核心板时&#xff0c;我盯着DRC检查列表里密密麻麻的警告发愣——明明跟着教程一步步操作&#xff0c;为什么还会出现这么多潜在问题&#xff1f;后来才发现&#xff0c;…...

SpeedAI科研小助手:论文查重降AIGC率一站式通关神器

一、论文人共同焦虑&#xff1a;重复率飙红、AI率超标&#xff0c;踩坑踩麻了 凌晨两点的实验室、宿舍书桌前&#xff0c;你盯着查重报告上刺眼的60%重复率&#xff0c;再看AIGC检测结果里98%的疑似度&#xff0c;只觉得毕业答辩的门槛好像瞬间高了好几倍。 是不是也踩过这些坑…...

STM32 TIM定时器PWM实战:从呼吸灯到舵机控制,一个定时器搞定三个项目

STM32 TIM定时器PWM实战&#xff1a;从呼吸灯到舵机控制&#xff0c;一个定时器搞定三个项目 在嵌入式开发中&#xff0c;PWM&#xff08;脉冲宽度调制&#xff09;技术就像一把瑞士军刀&#xff0c;它能让你用简单的数字信号控制各种模拟设备。想象一下&#xff0c;你手头只有…...

让你的10美元鼠标秒变苹果触控板!Mac Mouse Fix终极使用指南

让你的10美元鼠标秒变苹果触控板&#xff01;Mac Mouse Fix终极使用指南 【免费下载链接】mac-mouse-fix Mac Mouse Fix - Make Your $10 Mouse Better Than an Apple Trackpad! 项目地址: https://gitcode.com/GitHub_Trending/ma/mac-mouse-fix 还在为macOS上的鼠标体…...

【最后72小时解锁权限】:2026奇点大会AI对话机器人Benchmark基准测试平台访问密钥(含OpenChatBench v3.1、C-DialEval 2026、中文司法对话挑战集)

第一章&#xff1a;2026奇点智能技术大会&#xff1a;AI对话机器人 2026奇点智能技术大会(https://ml-summit.org) 本届大会聚焦于对话式AI的范式跃迁——从任务导向型助手迈向具备持续记忆、跨轮次意图推理与多模态语境感知的“共生智能体”。核心展示平台基于开源框架Conve…...

【AI隐私计算新范式】:联邦学习+差分隐私+可信执行环境(TEE)三位一体架构实测报告

第一章&#xff1a;生成式AI应用数据隐私保护 2026奇点智能技术大会(https://ml-summit.org) 生成式AI在内容创作、代码生成、客服对话等场景中爆发式落地&#xff0c;但其训练与推理过程常涉及敏感用户数据的输入、缓存与输出&#xff0c;引发隐私泄露、数据残留和模型反演等…...

计算机视觉 --- 图像去噪与增强:模糊算法的艺术与科学

1. 图像模糊的双面魔法&#xff1a;降噪与特征增强 第一次接触图像模糊技术时&#xff0c;我和大多数人一样疑惑&#xff1a;把图片变模糊有什么用&#xff1f;直到在医疗影像项目里看到CT扫描图上那些雪花点般的噪声&#xff0c;才明白这个看似简单的操作背后藏着多少门道。想…...

C#实现ModbusRTU详解【六】—— NModbus4报文读写

1. 为什么需要直接操作ModbusRTU底层报文 在工业自动化项目中&#xff0c;ModbusRTU协议因其简单可靠被广泛应用。NModbus4库提供了ReadCoils、WriteSingleRegister等高层API&#xff0c;确实能快速实现基础功能。但实际开发中&#xff0c;我遇到过三种必须操作底层报文的典型场…...

PowerDNS+MySQL实战:5步搞定内网DNS高可用部署(附避坑指南)

PowerDNSMySQL企业级内网DNS高可用架构设计与实战 当企业内网规模突破千台设备时&#xff0c;"ping不通服务器"这类基础问题往往成为IT团队的噩梦。传统hosts文件维护早已力不从心&#xff0c;而公有云DNS服务又无法满足内网隔离需求。这正是我们三年前遇到的困境——…...

如何快速搭建Windows C/C++开发环境:MinGW-w64终极配置指南

如何快速搭建Windows C/C开发环境&#xff1a;MinGW-w64终极配置指南 【免费下载链接】mingw-w64 (Unofficial) Mirror of mingw-w64-code 项目地址: https://gitcode.com/gh_mirrors/mi/mingw-w64 你是否想在Windows系统上开启专业的C/C编程之旅&#xff0c;但又苦于找…...

给信用卡大小的电脑装上大脑:用OpenClaw把可乐派变成Al智能体

一张信用卡大小的电脑&#xff0c;接上 AI 后能做什么&#xff1f;能管理日程、整理邮件、在飞书上和你聊天——还能用自然语言控制你家里的灯、门锁、传感器。这不是云端那个飘渺的AI&#xff0c;而是长在你桌上的&#xff0c;真实连接着物理世界的智能体。今天分享一下我是怎…...

如何撰写符合Sensors期刊投稿要求的高质量技术论文

1. 从摘要到结论&#xff1a;Sensors论文写作全流程指南 写一篇符合Sensors期刊要求的论文&#xff0c;就像给一位严谨的科学家讲故事。我投过三次稿&#xff0c;前两次都被打回来修改&#xff0c;第三次才摸清门道。最容易被拒稿的环节往往出现在摘要、图表和实验方法部分。 …...

STM32+W25Q256实战:ThreadX LevelX移植避坑指南(附完整工程)

STM32W25Q256实战&#xff1a;ThreadX LevelX移植避坑指南&#xff08;附完整工程&#xff09; 在嵌入式系统中&#xff0c;NorFlash因其非易失性、快速读取和随机访问特性&#xff0c;成为存储关键数据的理想选择。然而&#xff0c;频繁的擦写操作会导致存储单元磨损&#xff…...

博士论文盲审前夜,我靠这7个细节检查清单拿到了全A(附避坑指南)

博士论文盲审前夜&#xff1a;7个细节检查清单与全A避坑指南 凌晨三点的实验室&#xff0c;键盘敲击声在空旷的走廊回响。这是张明博士论文提交前的最后一夜&#xff0c;他的目光反复游移在屏幕上那篇凝聚五年心血的文档与墙上的倒计时之间。像大多数面临盲审的博士生一样&…...

用VSCode玩转AX620A:从交叉编译到在线调试的完整开发体验

用VSCode玩转AX620A&#xff1a;从交叉编译到在线调试的完整开发体验 在嵌入式开发领域&#xff0c;图形化工具链的成熟让开发效率大幅提升。AX620A作为一款面向边缘计算的高性能AI芯片&#xff0c;其开发环境搭建往往需要处理交叉编译、远程调试等复杂环节。本文将带你用VSCo…...

别再只盯着NOERROR了!用Wireshark实战分析DNS应答码(RCODE),从SERVFAIL到REFUSED的排错指南

从SERVFAIL到REFUSED&#xff1a;用Wireshark解码DNS故障的实战指南 当用户报告"网站打不开"时&#xff0c;80%的运维工程师会立即检查网络连通性&#xff0c;却忽略了DNS这个隐形杀手。上周我就遇到一个典型案例&#xff1a;某电商平台突然出现区域性访问故障&#…...