React中使用openLayer画地图

OpenLayers(简称ol)是一个‌开源的WebGIS前端开发库‌,基于JavaScript实现,主要用于在网页中嵌入动态二维地图。 

官方网站: https://openlayers.org

中文官网: https://openlayers.vip

大家可以去参考学习一些api等内容

 下面我们做一个类似效果,首先我只要某个区域,并将这个区域用颜色来覆盖,用边框来画出来。并在这个区域内加一些我自己的坐标点,这些坐标点根据类型不同使用不同颜色的图片来表示,点击这些点,弹出一个popup列表框,显示相关数据信息。

 全部代码如下:

一、引入相关组件:(里面几个图片用来显示不同的点)

import React,{ useState ,useEffect,useRef} from 'react';
import { Button } from 'antd';
import Map from 'ol/Map.js';
import View from 'ol/View.js';
import TileLayer from 'ol/layer/Tile.js';
import {fromLonLat} from 'ol/proj';
import XYZ from 'ol/source/XYZ.js';
import VectorLayer from 'ol/layer/Vector.js';
import VectorSource from 'ol/source/Vector.js';
import GeoJSON from 'ol/format/GeoJSON.js';
import Style from 'ol/style/Style.js';
import Fill from 'ol/style/Fill.js';
import Stroke from 'ol/style/Stroke.js';
import Icon from 'ol/style/Icon.js';
import Feature from 'ol/Feature.js';
import Polygon from 'ol/geom/Polygon.js';
import Point from 'ol/geom/Point.js';
import Overlay from 'ol/Overlay.js';
import 'ol/ol.css';
import yellow from '../../assets/yellow.png';
import blue from '../../assets/blue.png';
import green from '../../assets/green.png';
import close from '../../assets/map-close.png';

第二步、创建所需视图和图层

view:是视图,也就是我们看到的整个区域。可以设置中心坐标,坐标系,缩放等内容。

layers是图层,其中layer一个是底图(类似地图大致轮廓)、layer2一个是标注(带有地理位置名称)、VectorLayer2是我选中的所在区域,因为我想让这个区域在地图上显示不一样,比如让某区域加个颜色,加个边框等等。

const view=new View({center:fromLonLat([122.356879,41.734601]),zoom:10,minZoom:8,maxZoom:12})const layer=new TileLayer({ source: new XYZ({url:"http://t5.tianditu.gov.cn/vec_w/wmts?SERVICE=WMTS&REQUEST=GetTile&VERSION=1.0.0&LAYER=vec&STYLE=default&TILEMATRIXSET=w&FORMAT=tiles&TILEMATRIX={z}&TILEROW={y}&TILECOL={x}&tk=528881a2c3d647268c04ab43dc46bd51"})})const layer2=new TileLayer({ source: new XYZ({url:"http://t3.tianditu.com/DataServer?T=cva_w&tk=faf4cf166d31edcaba5de523eae8084f&x={x}&y={y}&l={z}"})})const VectorSource2=new VectorSource({ url:"https://geo.datav.aliyun.com/areas_v3/bound/210726.json",format:new GeoJSON()})const VectorLayer2=new VectorLayer({source:VectorSource2,style:new Style({fill:new Fill({color:"rgba(0,96,255,0.2)"}),stroke:new Stroke({color:'#0060ff',width:3})}),})

 三、自定义坐标点,可以看到在我这个地图中,有些多黄色蓝色绿色的坐标点,这些坐标点是我自定义的,我想点击这些坐标点提示这些坐标点内的数据。

const yellowsource=new VectorSource({})const yellowlayer=new VectorLayer({source:yellowsource})const yellowpoints=[fromLonLat([122.486629,41.570355]),fromLonLat([122.498091,41.617429]),fromLonLat([121.992578,41.906638]),fromLonLat([122.550649,41.678931]),fromLonLat([121.936423,41.875015])]yellowpoints.forEach(function(coords){let yellowfeature = new Feature({geometry: new Point(coords),});yellowfeature.setStyle(new Style({image:new Icon({src:yellow,})}))yellowsource.addFeature(yellowfeature); })const bluesource=new VectorSource({})const bluelayer=new VectorLayer({source:bluesource})const bluepoints=[fromLonLat([122.561534,41.783343]),fromLonLat([122.459847,41.849685]),fromLonLat([121.846006,41.83962]),fromLonLat([122.457756,41.856836]),fromLonLat([122.132125,42.002747])]bluepoints.forEach(function(coords){let bluefeature = new Feature({geometry: new Point(coords),});bluefeature.setStyle(new Style({image:new Icon({src:blue,})}))bluesource.addFeature(bluefeature); })const greensource=new VectorSource({})const greenlayer=new VectorLayer({source:greensource})const greenpoints=[fromLonLat([122.428214,42.093392]),fromLonLat([122.06593,41.971059]),fromLonLat([122.039448,41.644037]),fromLonLat([122.194422,42.033781]),fromLonLat([122.46685,42.04159])]greenpoints.forEach(function(coords){let greenfeature = new Feature({geometry: new Point(coords),});greenfeature.setStyle(new Style({image:new Icon({src:green,})}))greensource.addFeature(greenfeature); })

 四、将数据绑定到地图中,并在地图里面添加点击事件,并且只有限制,只有点击到我自定义的坐标上时候,才显示相关内容。

 useEffect(()=>{map=new Map({target:"map",view:view,layers:[layer,layer2,VectorLayer2,yellowlayer,bluelayer,greenlayer]})popup=new Overlay({element:document.getElementById("popup"),})map.addOverlay(popup)map.on("click",function(e){let pixel=e.pixel;let features=map.getFeaturesAtPixel(pixel);if(features.length>=2){var geometry = features[0].getGeometry().getCoordinates();var geometry2 = features[1].getGeometry().getCoordinates();popup.setPosition(geometry);map.addOverlay(popup);}        })},[])

 五、点击关闭按钮隐藏卡片

 function _closeOverlay(){console.log('删除overlay')popup.setPosition(undefined);// map.removeOverlay(popup);}

 六、全部代码如下

import React,{ useState ,useEffect,useRef} from 'react';
import { Button } from 'antd';
import Map from 'ol/Map.js';
import View from 'ol/View.js';
import TileLayer from 'ol/layer/Tile.js';
import {fromLonLat} from 'ol/proj';
import XYZ from 'ol/source/XYZ.js';
import VectorLayer from 'ol/layer/Vector.js';
import VectorSource from 'ol/source/Vector.js';
import GeoJSON from 'ol/format/GeoJSON.js';
import Style from 'ol/style/Style.js';
import Fill from 'ol/style/Fill.js';
import Stroke from 'ol/style/Stroke.js';
import Icon from 'ol/style/Icon.js';
import Feature from 'ol/Feature.js';
import Polygon from 'ol/geom/Polygon.js';
import Point from 'ol/geom/Point.js';
import Overlay from 'ol/Overlay.js';
import 'ol/ol.css';
import yellow from '../../assets/yellow.png';
import blue from '../../assets/blue.png';
import green from '../../assets/green.png';
import close from '../../assets/map-close.png';let map=null;
let popup=null;
function GisMapView() {const [count, setCount] = useState(0)const [center,setCenter]=useState(0)const mapDiv = useRef(null);const view=new View({center:fromLonLat([122.356879,41.734601]),zoom:10,minZoom:8,maxZoom:12})const layer=new TileLayer({ source: new XYZ({url:"http://t5.tianditu.gov.cn/vec_w/wmts?SERVICE=WMTS&REQUEST=GetTile&VERSION=1.0.0&LAYER=vec&STYLE=default&TILEMATRIXSET=w&FORMAT=tiles&TILEMATRIX={z}&TILEROW={y}&TILECOL={x}&tk=528881a2c3d647268c04ab43dc46bd51"})})const layer2=new TileLayer({ source: new XYZ({url:"http://t3.tianditu.com/DataServer?T=cva_w&tk=faf4cf166d31edcaba5de523eae8084f&x={x}&y={y}&l={z}"})})const VectorSource2=new VectorSource({ url:"https://geo.datav.aliyun.com/areas_v3/bound/210726.json",format:new GeoJSON()})const VectorLayer2=new VectorLayer({source:VectorSource2,style:new Style({fill:new Fill({color:"rgba(0,96,255,0.2)"}),stroke:new Stroke({color:'#0060ff',width:3})}),})const yellowsource=new VectorSource({})const yellowlayer=new VectorLayer({source:yellowsource})const yellowpoints=[fromLonLat([122.486629,41.570355]),fromLonLat([122.498091,41.617429]),fromLonLat([121.992578,41.906638]),fromLonLat([122.550649,41.678931]),fromLonLat([121.936423,41.875015])]yellowpoints.forEach(function(coords){let yellowfeature = new Feature({geometry: new Point(coords),});yellowfeature.setStyle(new Style({image:new Icon({src:yellow,})}))yellowsource.addFeature(yellowfeature); })const bluesource=new VectorSource({})const bluelayer=new VectorLayer({source:bluesource})const bluepoints=[fromLonLat([122.561534,41.783343]),fromLonLat([122.459847,41.849685]),fromLonLat([121.846006,41.83962]),fromLonLat([122.457756,41.856836]),fromLonLat([122.132125,42.002747])]bluepoints.forEach(function(coords){let bluefeature = new Feature({geometry: new Point(coords),});bluefeature.setStyle(new Style({image:new Icon({src:blue,})}))bluesource.addFeature(bluefeature); })const greensource=new VectorSource({})const greenlayer=new VectorLayer({source:greensource})const greenpoints=[fromLonLat([122.428214,42.093392]),fromLonLat([122.06593,41.971059]),fromLonLat([122.039448,41.644037]),fromLonLat([122.194422,42.033781]),fromLonLat([122.46685,42.04159])]greenpoints.forEach(function(coords){let greenfeature = new Feature({geometry: new Point(coords),});greenfeature.setStyle(new Style({image:new Icon({src:green,})}))greensource.addFeature(greenfeature); })useEffect(()=>{map=new Map({target:"map",view:view,layers:[layer,layer2,VectorLayer2,yellowlayer,bluelayer,greenlayer]})popup=new Overlay({element:document.getElementById("popup"),})map.addOverlay(popup)map.on("click",function(e){let pixel=e.pixel;let features=map.getFeaturesAtPixel(pixel);if(features.length>=2){var geometry = features[0].getGeometry().getCoordinates();var geometry2 = features[1].getGeometry().getCoordinates();popup.setPosition(geometry);map.addOverlay(popup);}        })},[])function _closeOverlay(){console.log('删除overlay')popup.setPosition(undefined);// map.removeOverlay(popup);}return (<><div id="map" ref={mapDiv} style={{width: "100%",height: "98vh"}}><div id="popup"><div className="popup_header"><div className="popup_header_left"><img className="popup_header_left_img" src={green}/><div className="popup_header_left_name">红光二</div></div><img id="popup-closer" className="popup_header_rigth" src={close} onClick={_closeOverlay}/></div><div className="popup_content"><div className="popup_content_item"><div className="popup_content_item_name">液位</div><div className="popup_content_item_content"><div className="popup_content_item_content_count">1.3</div><div className="popup_content_item_content_unit">m</div></div></div><div className="popup_content_item"><div className="popup_content_item_name">排水流量</div><div className="popup_content_item_content"><div className="popup_content_item_content_count">1.3</div><div className="popup_content_item_content_unit">m</div></div></div><div className="popup_content_item"><div className="popup_content_item_name">排水站状态</div><div className="popup_content_item_content"><div className="popup_content_item_content_states">正常</div></div></div><div className="popup_content_item"><div className="popup_content_item_name">采集时间</div><div className="popup_content_item_content"><div className="popup_content_item_content_unit">05-01 10:00:00</div></div></div></div></div><div className="map_side_menu"><div className="map_side_menu_item"><img className="map_side_menu_item_img" src={green}/><div className="map_side_menu_item_content"><div className="map_side_menu_item_content_name">排水站</div><div className="map_side_menu_item_content_count">50个</div></div></div><div className="map_side_menu_item"><img className="map_side_menu_item_img" src={yellow}/><div className="map_side_menu_item_content"><div className="map_side_menu_item_content_name">液位计</div><div className="map_side_menu_item_content_count">50个</div></div></div><div className="map_side_menu_item"><img className="map_side_menu_item_img" src={blue}/><div className="map_side_menu_item_content"><div className="map_side_menu_item_content_name">视频监控</div><div className="map_side_menu_item_content_count">50个</div></div></div></div></div></>)
}export default GisMapView

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

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

相关文章

WHAT - 缓存命中 Cache Hit 和缓存未命中 Cache Miss

文章目录 一、什么是缓存命中&#xff1f;二、前端开发要知道哪些缓存机制&#xff08;以及命中条件&#xff09;&#xff1f;1. 浏览器缓存&#xff08;主要针对静态资源&#xff09;常见的缓存位置关键 HTTP 头字段&#xff08;决定命中与否&#xff09; 2. 前端应用层缓存&a…

10 个可靠的 Android 文件传输应用程序

Android 文件传输是 Android 用户的常见需求。我们经常需要将文件从一台 Android 设备传输到 PC 或 Mac。但我们怎样才能做到这一点呢&#xff1f;俗话说&#xff0c;工欲善其事&#xff0c;必先利其器。因此&#xff0c;首先了解 10 个锋利的 Android 文件传输应用程序&#x…

AlphaEvolve:LLM驱动的算法进化革命与科学发现新范式

AlphaEvolve&#xff1a;LLM驱动的算法进化革命与科学发现新范式 本文聚焦Google DeepMind最新发布的AlphaEvolve&#xff0c;探讨其如何通过LLM与进化算法的结合&#xff0c;在数学难题突破、计算基础设施优化等领域实现革命性进展。从48次乘法优化44矩阵相乘到数据中心资源利…

Java大师成长计划之第24天:Spring生态与微服务架构之分布式配置与API网关

&#x1f4e2; 友情提示&#xff1a; 本文由银河易创AI&#xff08;https://ai.eaigx.com&#xff09;平台gpt-4-turbo模型辅助创作完成&#xff0c;旨在提供灵感参考与技术分享&#xff0c;文中关键数据、代码与结论建议通过官方渠道验证。 在微服务架构中&#xff0c;如何管理…

eSwitch manager 简介

eSwitch manager 的定义和作用 eSwitch manager 通常指的是能够配置和管理 eSwitch&#xff08;嵌入式交换机&#xff09;的实体或接口。在 NVIDIA/Mellanox 的网络架构中&#xff0c;Physical Function&#xff08;PF&#xff09;在 switchdev 模式下充当 eSwitch manager&am…

最新开源 TEN VAD 与 Turn Detection 让 Voice Agent 对话更拟人 | 社区来稿

关键词&#xff1a;对话式 AI | 语音智能体 | Voice Agent | VAD | 轮次检测 | 声网 | TEN GPT-4o 所展示对话式 AI 的新高度&#xff0c;正一步步把我们在电影《Her》中看到的 AI 语音体验变成现实。AI 的语音交互正在变得更丰富、更流畅、更易用&#xff0c;成为构建多模态智…

AI实践用例---日程规划(通用日程管理文件ICS)灵感踩坑日常

我是一位践行独立开发者之路的菜鸟开发者。 由于执行力较差,常常有很多想法但是很多时候没有去践行。 所以我有了让大模型为我生成日程安排的想法,这确实可以,很简单。只需要将你的想法告诉ai就行了。 例如: 发给AI的提示词: 我想你帮我对,嗯,未来的一年做一个嗯,大…

大疆无人机​​DRC 链路

在大疆上云API中&#xff0c;​​DRC 链路​​通常指 ​​Device-Cloud Remote Control Link&#xff08;设备-云端远程控制链路&#xff09;​​&#xff0c;它是无人机&#xff08;或设备&#xff09;与云端服务之间建立的​​实时控制与数据传输通道​​&#xff0c;用于实现…

tomcat一闪而过,按任意键继续以及控制台中文乱码问题

问题描述 今天在打开tomcat,启动startup.bat程序时 tomcat直接闪退,后面查找资料后发现,可以通过编辑startup.bat文件内容,在最后一行加入pause即可让程序不会因为异常而终止退出 这样方便查看tomcat所爆出的错误: 然后,我明确看到我的tomcat启动程序显示如下的内容,没有明确…

中大型水闸安全监测系统解决方案

一、方案概述 中大型水闸作为水利工程的重要组成部分&#xff0c;承担着调节水位、控制水流、防洪排涝等多重功能&#xff0c;在防洪减灾、水资源配置、生态环境改善等方面发挥着巨大作用。然而&#xff0c;由于历史原因&#xff0c;许多水闸存在建设标准偏低、质量较差、配套设…

轨迹误差评估完整流程总结(使用 evo 工具)

roslaunch .launch rosbag play your_dataset.bag -r 2.0 ✅ 第二步&#xff1a;录制估计轨迹 bash 复制编辑 rosbag record -O traj_only.bag /aft_mapped_to_init 运行一段时间后 CtrlC 停止&#xff0c;生成 traj_only.bag 第三步&#xff1a;提取估计轨迹和真值轨迹为…

Linux任务管理与守护进程

目录 任务管理 jobs&#xff0c;fg&#xff0c;bg 进程组概念 任务概念 守护进程 守护进程的概念 守护进程的查看 守护进程的创建 ​编辑模拟实现daemon函数 任务管理 每当有一个用户登录Linux时&#xff0c;系统就会创建一个会话&#xff08;session&#xff09; 任何…

Json rpc 2.0比起传统Json在通信中的优势

JSON-RPC 2.0 相较于直接使用传统 JSON 进行通信&#xff0c;在协议规范性、开发效率、通信性能等方面具有显著优势。以下是核心差异点及技术价值分析&#xff1a; 一、结构化通信协议&#xff0c;降低开发成本 传统 JSON 通信需要开发者自定义数据结构和处理逻辑&#xff0c;…

机器学习与人工智能:NLP分词与文本相似度分析

DIY AI & ML NLP — Tokenization & Text Similarity by Jacob Ingle in Data Science Collective 本文所使用的数据是在 Creative Commons license 下提供的。尽管我们已尽力确保信息的准确性和完整性&#xff0c;但我们不对数据的完整性或可靠性做任何保证。数据的使…

RK3568平台OpenHarmony系统移植可行性评估

https://docs.openharmony.cn/pages/v5.0/zh-cn/device-dev/quick-start/quickstart-appendix-compiledform.md 官方给的标准系统就是RK3568, 所以肯定可以, 关于硬件加速部分 看了鸿蒙RK3568开发板的GPU编译配置,只能说能用 https://docs.openharmony.cn/pages/v4.1/zh-cn/…

论文浅尝 | HOLMES:面向大语言模型多跳问答的超关系知识图谱方法(ACL2024)

笔记整理&#xff1a;李晓彤&#xff0c;浙江大学硕士&#xff0c;研究方向为大语言模型 论文链接&#xff1a;https://arxiv.org/pdf/2406.06027 发表会议&#xff1a;ACL 2024 1. 动机 多跳问答&#xff08;Multi-Hop Question Answering, MHQA&#xff09;技术近年来在自然语…

机器学习中的特征工程:解锁模型性能的关键

在机器学习领域&#xff0c;模型的性能往往取决于数据的质量和特征的有效性。尽管深度学习模型在某些任务中能够自动提取特征&#xff0c;但在大多数传统机器学习任务中&#xff0c;特征工程仍然是提升模型性能的关键环节。本文将深入探讨特征工程的重要性、常用方法以及在实际…

Kotlin与Java的融合趋势:从互操作到云原生实践

在2025年的软件开发领域&#xff0c;Kotlin和Java作为JVM生态的支柱语言&#xff0c;展现出强大的协同能力。Kotlin以其简洁的语法和现代特性迅速崛起&#xff0c;而Java凭借其成熟生态和稳定性依然占据主导地位。通过两者的融合&#xff0c;我们的实时聊天系统将开发效率提升了…

Python生成器:高效处理大数据的秘密武器

生成器概述 生成器是 Python 中的一种特殊迭代器&#xff0c;通过普通函数的语法实现&#xff0c;但使用 yield 语句返回数据。生成器自动实现了 __iter__() 和 __next__() 方法&#xff0c;因此可以直接用于迭代。生成器的核心特点是延迟计算&#xff08;lazy evaluation&…

Flask框架入门与实践

Flask框架入门与实践 Flask是一个轻量级的Python Web框架&#xff0c;以其简洁、灵活和易于上手的特点深受开发者喜爱。本文将带您深入了解Flask的核心概念、基本用法以及实际应用。 什么是Flask&#xff1f; Flask是由Armin Ronacher于2010年开发的微型Web框架。与Django等…