vue2通过leaflet实现图片点位回显功能

需求:在图片上标点了,需要根据标记点在图片上进行回显功能,并且不会根据窗口大小导致标记点移位

1.效果

2.下载插件

用到的是leaflet插件:一个交互式地图 JavaScript 库,我下载是  "leaflet": "^1.9.4"

npm install leaflet

引入到项目

icon是自带的图标

import icon from 'leaflet/dist/images/marker-icon.png';
import * as L from 'leaflet';
import 'leaflet/dist/leaflet.css';

3.主要代码详解

图片加载后需要创建map对象,注意!!如果后端传的点数据是根据图片原有大小比如图片尺寸800*800,x:20,y:20,就是在800像素上的xy的值那么直接设置leftmap的unproject为图片本身的尺寸即可

​var south_west = that.leftMap.unproject([0, img_original_height], 1); //西南var north_east = that.leftMap.unproject([img_original_width, 0], 1);​

如果图片原尺寸为800*800,后端传来尺寸为400*400,x:10,y:10,需要设置如下代码

      var style = window.getComputedStyle(document.getElementById("roc_map"));var map_height = parseFloat(style.height);     var south_west = that.leftMap.unproject([0, map_height], 1); //西南var north_east = that.leftMap.unproject([img_original_width / this_ratio, 0],1);

创建点:draggable:是否拖拽L.marker上面的这些代码全部都是坐标转换的,就是为了应对原有尺寸和后端尺寸不对应的问题

        // 1. 获取旧图片尺寸(pointArr中保存的width/height)const oldWidth = obj_.width; // 例如 1036const oldHeight = obj_.height; // 例如 582// 3. 根据地理边界 this_bounds 计算实际的地理坐标const boundsWidth = this_bounds.getEast() - this_bounds.getWest();const boundsHeight = this_bounds.getNorth() - this_bounds.getSouth();const lng = this_bounds.getWest() + (boundsWidth / oldWidth) * obj_.x;const lat = this_bounds.getNorth() - (+boundsHeight / oldHeight) * obj_.y; // Y轴取反const DefaultIcon = L.icon({iconUrl: icon,iconAnchor: [10, 41]});// 4. 创建标记点(Leaflet的Y轴需要取反)const marker = L.marker([lat, lng], {draggable: false,title: obj_.name,icon: DefaultIcon}).addTo(that.leftMap);

创建点弹窗,弹窗样式自行设计

   const popup = L.popup().setContent('加载中...');marker.bindPopup(popup);

4.完整代码

<!--* @Description:* @Author: 请叫我欧皇!* @Date: 2025-04-28 14:58:23* @FilePath: \vue-secondMenu-test-master\src\page\test4\zongti\02.leftjs.vue
-->
<template><div class="leaflet-box"><div id="roc_map" class="map"></div></div>
</template><script>
import icon from 'leaflet/dist/images/marker-icon.png';
import * as L from 'leaflet';
import 'leaflet/dist/leaflet.css';
export default {data() {return {pointArr: [{x: 80,y: 50,name: '测试111',group: ['测试111'],point_id: 1,sn: '123456789',width: 800,height: 572},{x: 200,y: 0,name: '测试222',group: ['测试222'],point_id: 2,sn: '123456789',width: 800,height: 572},{x: 200,y: 200,name: '测试333',group: ['测试222'],point_id: 3,sn: '123456789',width: 800,height: 572}],leftMap: null};},mounted() {this.initLeaflet();},methods: {initLeaflet() {let that = this;let pointArr = this.pointArr;var mark_map = {};var this_img = new Image();let imgs = 'https://fuss10.elemecdn.com/e/5d/4a731a90594a4af544c0c25941171jpeg.jpeg';// this_img.src = "../images/01.jpg";this_img.src = imgs;this_img.onload = function () {var img_original_width = this_img.width,img_original_height = this_img.height;// 在初始化地图前检查是否已存在地图实例if (that.leftMap) {that.leftMap.remove(); // 移除旧地图that.leftMap = null;}that.leftMap = new L.Map('roc_map', {minZoom: 1,maxZoom: 4,center: [0, 0],zoom: 1,crs: L.CRS.Simple,zoomControl: false,attributionControl: false// zoomControl: false, // 禁用默认的缩放控件});var south_west = that.leftMap.unproject([0, img_original_height], 1); //西南var north_east = that.leftMap.unproject([img_original_width, 0], 1);var this_bounds = new L.LatLngBounds(south_west, north_east);L.imageOverlay(imgs, this_bounds).addTo(that.leftMap);that.leftMap.fitBounds(this_bounds);init_p();//   init_grid_2();function init_p() {for (var i = 0; i < pointArr.length; i++) {let obj_ = pointArr[i];// 1. 获取旧图片尺寸(pointArr中保存的width/height)const oldWidth = obj_.width; // 例如 1036const oldHeight = obj_.height; // 例如 582// 3. 根据地理边界 this_bounds 计算实际的地理坐标const boundsWidth = this_bounds.getEast() - this_bounds.getWest();const boundsHeight = this_bounds.getNorth() - this_bounds.getSouth();const lng = this_bounds.getWest() + (boundsWidth / oldWidth) * obj_.x;const lat = this_bounds.getNorth() - (+boundsHeight / oldHeight) * obj_.y; // Y轴取反const DefaultIcon = L.icon({iconUrl: icon,iconAnchor: [10, 41]});// 4. 创建标记点(Leaflet的Y轴需要取反)const marker = L.marker([lat, lng], {draggable: false,title: obj_.name,icon: DefaultIcon}).addTo(that.leftMap);const popup = L.popup().setContent('加载中...');marker.bindPopup(popup);// 最新监测时间:2025-12-23 00:00:00 累计变化量X:1234.45mm 累计变化量Y:12345.567mm// .bindPopup(that.getBindPopup(obj_))marker.on('click', async function (e) {that.sendPointInfo = { ...obj_ };// Show loading messagemarker.bindPopup("<div style='width:260px;height:150px;font-size:12px' class='popup'>加载中...</div>").openPopup();try {const popupContent = `<div style='width:260px;height:150px;font-size:13px' class='popup'><div class="title">点编号:${obj_.name}</div><ul><li>sn:${obj_.sn}</li></ul></div>`;popup.setContent(popupContent);//                             }} catch (error) {popup.setContent('请求数据时出错');}});mark_map[obj_.point_id] = marker;}}};}}
};
</script><style lang="scss" scoped>
.leaflet-box {width: 100%;height: 800px;.map {width: 50%;height: 70%;margin: 40px;}
}
</style>

文章到此结束,希望对你有所帮助~

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/web/84965.shtml
繁体地址,请注明出处:http://hk.pswp.cn/web/84965.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

OmniDocBench:一键评测PDF解析算法

绝大多数文档格式都能无损转换至PDF&#xff0c;解决了PDF解析&#xff0c;也就相当于解决了绝大多数文档的解析。所以&#xff0c;PDF解析算法是文档服务的基石技术。 PDF解析算法目前有两类技术路线 pipeline方法&#xff0c;整合layout analysis, OCR, formula/table reco…

[按键精灵安卓/ios脚本插件开发] 遍历获取LuaAuxLib函数库命令辅助工具

LuaAuxLib库 LuaAuxLib是按键精灵所有内置命令所在的库文件&#xff0c;有多种方式来获取LuaAuxLib库下的函数命令&#xff0c;例如反编译按键精灵手机端库文件等。这里咱们来介绍一种浅显易懂的方式来获取&#xff0c;直接for循环遍历获取函数名。 ScanLuaAuxLib 我们写一个自…

深度学习和计算机视觉的关系的理解

深度学习和计算机视觉的关系 深度学习作为人工智能的重要分支&#xff0c;近年来在计算机视觉领域取得了革命性突破。计算机视觉的核心任务包括图像分类、目标检测、语义分割等&#xff0c;而深度学习通过神经网络模型自动学习图像特征&#xff0c;极大提升了这些任务的准确率…

springboot开发项目 SLF4J+Logback日志框架集成【最终篇】

在这篇文章之前&#xff0c;实际对于 springboot和SLF4JLogback日志框架的使用 我已经分享过3篇关于springboot 日志的文章了。为什么会在写这篇最终篇&#xff0c;因为 前3篇分享的关于springBoot框架日志的配置方案&#xff0c; 发现了一个问题&#xff1a;只有项目启动的时候…

phpstudy无法启动apache,80端口被占用,完美解决

phpstudy无法启动apache&#xff0c;80端口被占用&#xff0c;完美解决 解决方法一(最推荐) 依次点击网站-管理-修改 将端口由80改为81&#xff0c;再点击确认后即可重新启动apache。 需要注意的是&#xff0c;网站的访问由127.0.0.1变为127.0.0.1:81。默认是80的端口所以可以不…

Loggers 配置解析(log4j.xml)

Loggers 配置解析 我们通过下面的例子来理解 log4j 的 Loggers 配置是如何决定日志输出规则的。 <Loggers><!-- 根Logger&#xff1a;全局配置 --><Root level"debug"><AppenderRef ref"consoleAppender" level"info"/&g…

Java 大视界 -- Java 大数据在智能政务舆情监测与引导中的情感分析与话题挖掘技术(272)

&#x1f496;亲爱的朋友们&#xff0c;热烈欢迎来到 青云交的博客&#xff01;能与诸位在此相逢&#xff0c;我倍感荣幸。在这飞速更迭的时代&#xff0c;我们都渴望一方心灵净土&#xff0c;而 我的博客 正是这样温暖的所在。这里为你呈上趣味与实用兼具的知识&#xff0c;也…

[NocoDB] 在局域网中调整Float类型显示精度的部署经验

在单位局域网环境中,NocoDB有效地连接MySQL数据库和前端服务,做为中间件很方便。然而,在实际应用中,我们也会遇到一些较为隐藏的设置问题,比如此次经历的 float 显示精度不匹配问题。 问题环境 实际数据库:MySQL,表中有 float 类型的数据 原始数据来源:Excel表格 数据转…

Dockerfile 常见指令详解

Dockerfile 是一个文本文件&#xff0c;包含了一系列用于构建 Docker 镜像的指令。以下是 Dockerfile 中常见指令的详细解释&#xff1a; 基础指令 1. FROM 指定基础镜像&#xff0c;必须为第一条指令&#xff08;注释除外&#xff09;。 FROM ubuntu:20.04 FROM python:3.…

InnoDB Cluster 与 NDB Cluster 对比及部署指南

InnoDB Cluster 与 NDB Cluster 对比及部署指南 一、核心区别对比 特性InnoDB ClusterNDB Cluster存储引擎InnoDBNDB (内存优先)架构设计基于Group Replication分布式架构(数据节点管理节点SQL节点)一致性模型最终一致性/强一致性强一致性数据持久化磁盘存储为主内存存储为主…

PySide环境配置及工具使用

文章目录 [toc]1 概述1.1 PySide 能做什么&#xff1f;1.2 PySide 的优点1.3 PySide 的缺点1.4 示例代码&#xff08;简单窗口&#xff09; 2 环境准备2.1 安装必要软件2.2 修改 pip 源 3 PySide23.1 环境要求3.2 配置PySide23.3 工具配置 4 PySide64.1 环境4.2 配置PySide64.3…

数据标注师学习内容

目录 文本标注词性标注实体标注 图像标注语音标注 文本标注 词性标注 第一篇 第二篇 实体标注 点击这里 关系标注 事件标注 意图标注 关键词标注 分类标注 问答标注 对话标注 图像标注 拉框标注 关键点标注 2D标注 3D标注 线标注 目标跟踪标注 OCR标注 图像分类标注 语音…

【linux】文件与目录命令 - rsync

文章目录 1. 基本用法2. 常用参数3. 用法举例4. 注意事项 rsync 命令用于快速同步文件和目录&#xff0c;可用于本地和远程传输&#xff0c;支持增量同步、压缩、权限保留等特性。 1. 基本用法 语法&#xff1a; rsync [选项] 源 目标功能&#xff1a; 高效增量同步&#xff…

互联网大厂Java求职面试:电商系统高并发设计

互联网大厂Java求职面试&#xff1a;电商系统高并发设计 文章内容 面试官&#xff08;技术总监&#xff09;与郑薪苦的对话 面试官&#xff1a; “郑薪苦&#xff0c;欢迎来到我们的面试。今天我们会围绕一个非常热门的话题——电商系统的高并发设计进行深入探讨。你之前在某…

Nginx跨云反向代理排错:解密配置参数的“陷阱”

前言&#xff1a;在当今的云计算环境中&#xff0c;跨云平台的应用部署变得越来越常见。为了验证跨云平台反向代理的可行性&#xff0c;我们进行了一次测试。本次测试将后端程序部署在阿里云服务器&#xff0c;同时使用在腾讯云注册的已备案国内域名。我们在腾讯云控制台将域名…

股票账户的管理和交易

中国证券登记结算有限责任公司&#xff08;简称“中国结算”&#xff09;确实是负责股票的账户管理&#xff08;开户、销户&#xff09;和登记、存管、清算、交收等后台业务的中央机构。它确保了股票所有权的准确记录和交易后资金与证券的最终转移。 而股票的交易业务&#xff…

Arcgis地理配准变换方法说明

零阶多项式 - 将使用零阶多项式来平移数据。 当已对数据进行地理配准但通过微小的平移可以更好的排列数据时&#xff0c;通常使用该多项式。 执行零阶多项式平移只需要一个连接线。相似性多项式 - 将使用一阶变换&#xff0c;尝试保持原始栅格的形状。 RMS 错误会高于其他多项式…

深入理解 C++ volatile 与 atomic:五大用法解析 + 六大高频考点

一、volatile volatile是C中一个非常重要的关键字。volatile关键字告诉编译器&#xff0c;被修饰的变量可能会在程序控制之外被改变&#xff0c;因此编译器不能对该变量的访问进行优化。什么意思呢&#xff1f;现代处理器架构中&#xff0c;有寄存器&#xff0c;L1缓存&#x…

跨主机管理Docker容器化应用的操作与技巧

哈喽&#xff0c;大家好&#xff0c;我是左手python&#xff01; 环境准备与 Docker 安装 在开始跨主机管理 Docker 容器化应用之前&#xff0c;需要确保所有主机上都安装了 Docker 引擎&#xff0c;并且这些主机之间可以通过 SSH 协议进行通信。本节将详细介绍环境准备和 Doc…

编程实践:sigmastar330 调用IVE图像处理加速

说明:本专栏文章有两种解锁方案 1:付费订阅,畅享所有文章 2:免费获取,点击下方链接,关注,自动获取免费链接 https://free-img.400040.xyz/4/2025/04/29/6810a50b7ac8b.jpg 主题:利用IVE进行图像处理加速 Sigmastar 支持的硬件操作,基本都在:mi_ive.h 文件中,本文…