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.pswp.cn/diannao/83289.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/83289.shtml
英文地址,請注明出處:http://en.pswp.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等…