openlayers基本使用(街景+标注+绘制)

news/2025/10/11 8:12:41/文章来源:https://www.cnblogs.com/it774274680/p/19134185

卫星影像

<template><div class="app"><div class="map-container" ref="map_ref"></div></div>
</template><script>
import Map from "ol/Map.js";
import TileLayer from "ol/layer/Tile.js";
import View from "ol/View.js";
import XYZ from "ol/source/XYZ.js";export default {data() {return {};},mounted() {this.initMap();},methods: {initMap() {// const map = new Map({//   target: this.$refs.map_ref,//   layers: [//     new TileLayer({//       source: new XYZ({//         url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",//       }),//     }),//   ],//   view: new View({//     center: [0, 0],//     zoom: 2,//   }),// });// 创建卫星图层const satelliteLayer = new TileLayer({source: new XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",maxZoom: 18,}),opacity: 0.9,zIndex: 1,});// 创建街道图层作为备用const streetLayer = new TileLayer({source: new XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=7&x={x}&y={y}&z={z}",maxZoom: 18,}),zIndex: 0,visible: false,});const map = new Map({target: this.$refs.map_ref,layers: [satelliteLayer, streetLayer],view: new View({center: [0, 0],zoom: 2,}),});},},
};
</script><style lang="less" scoped>
.app {padding: 10px;
}
.map-container {height: calc(100vh - 50px);// background-color: orange;
}
</style>

增加标注

基础示例

<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="UTF-8" /><title>OpenLayers 街景与地名标注</title><!-- 引入 OpenLayers CSS --><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.css" /><!-- 引入 OpenLayers JavaScript --><script src="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.js"></script><style>#map {width: 100%;height: 800px;}</style></head><body><div id="map"></div><script>// 1.创建地图=============var map = new ol.Map({target: "map", // 地图渲染的目标 DOM 元素 IDlayers: [// 底图图层,这里使用 OpenStreetMapnew ol.layer.Tile({// source: new ol.source.OSM(),source: new ol.source.XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",}),}),],view: new ol.View({center: ol.proj.fromLonLat([108, 28]), // 地图初始中心点,这里以西南地区大致经纬度为例zoom: 8, // 初始缩放级别}),});// 2.1 加载地名 GeoJSON 数据=======================var vectorSource = new ol.source.Vector({url: "./places.json", // 地名数据文件路径format: new ol.format.GeoJSON(),});// 2.2 创建矢量图层,用于显示地名标注var vectorLayer = new ol.layer.Vector({source: vectorSource,style: function (feature) {// 为每个地名要素设置样式,包括点样式和文字标签var textStyle = new ol.style.Text({text: feature.get("name"), // 获取地名属性font: "12px Arial",fill: new ol.style.Fill({color: "#000",}),stroke: new ol.style.Stroke({color: "#fff",width: 2,}),offsetY: -15, // 文字相对于点的垂直偏移});var pointStyle = new ol.style.Style({image: new ol.style.Circle({radius: 5,fill: new ol.style.Fill({color: "#ff0000",}),}),text: textStyle,});return pointStyle;},});// 2.3 将地名标注图层添加到地图map.addLayer(vectorLayer);// 3. 给地图添加点击事件,模拟街景加载map.on("click", function (evt) {var coordinate = evt.coordinate;// 这里只是模拟,实际需根据点击位置获取街景资源并展示alert("点击位置经纬度:" + ol.proj.toLonLat(coordinate));// 实际项目中,可在此处调用街景库的 API 加载对应位置的街景});// 获取地图的缩放级别=================start// 获取地图视图对象const view = map.getView();// 监听change:resolution事件view.on("change:resolution", function () {const zoom = view.getZoom(); // 获取当前缩放级别console.log("zoom=========>", zoom);});// 获取地图的缩放级别=================end</script></body>
</html>

缩放到一定程度后再显示标注

效果图:

image

示例代码:

<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="UTF-8" /><title>OpenLayers 街景与地名标注</title><!-- 引入 OpenLayers CSS --><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.css" /><!-- 引入 OpenLayers JavaScript --><script src="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.js"></script><style>#map {width: 100%;height: 800px;}</style></head><body><div class="info">当前缩放级别: <span id="zoom-level">0</span><br />标注将在缩放级别 ≥ 8 时显示</div><div id="map"></div><script>// 1.创建地图=============var map = new ol.Map({target: "map", // 地图渲染的目标 DOM 元素 IDlayers: [// 底图图层,这里使用 OpenStreetMapnew ol.layer.Tile({// source: new ol.source.OSM(),source: new ol.source.XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",}),}),],view: new ol.View({center: ol.proj.fromLonLat([108, 28]), // 地图初始中心点,这里以西南地区大致经纬度为例zoom: 8, // 初始缩放级别}),});// 2.1 加载地名 GeoJSON 数据=======================var vectorSource = new ol.source.Vector({url: "./places.json", // 地名数据文件路径format: new ol.format.GeoJSON(),});// 2.2 创建矢量图层,用于显示地名标注var vectorLayer = new ol.layer.Vector({source: vectorSource,style: function (feature) {// 为每个地名要素设置样式,包括点样式和文字标签var textStyle = new ol.style.Text({text: feature.get("name"), // 获取地名属性font: "12px Arial",fill: new ol.style.Fill({color: "#000",}),stroke: new ol.style.Stroke({color: "#fff",width: 2,}),offsetY: -15, // 文字相对于点的垂直偏移});var pointStyle = new ol.style.Style({image: new ol.style.Circle({radius: 5,fill: new ol.style.Fill({color: "#ff0000",}),}),text: textStyle,});return pointStyle;},});// 2.3 将地名标注图层添加到地图map.addLayer(vectorLayer);// 3. 需求:获取地图的经纬度      (给地图添加点击事件)map.on("click", function (evt) {var coordinate = evt.coordinate;// 这里只是模拟,实际需根据点击位置获取街景资源并展示alert("点击位置经纬度:" + ol.proj.toLonLat(coordinate));// 实际项目中,可在此处调用街景库的 API 加载对应位置的街景});// 4. 需求:缩放到一定的程度后再显示标注图层============start// 缩放级别显示元素var zoomLevelElement = document.getElementById("zoom-level");// 控制标注显示的最小缩放级别var MIN_ZOOM_FOR_LABELS = 8;// 更新标注可见性的函数function updateLabelsVisibility() {var currentZoom = map.getView().getZoom();zoomLevelElement.textContent = currentZoom.toFixed(1);// 当缩放级别大于等于设定值时显示标注,否则隐藏vectorLayer.setVisible(currentZoom >= MIN_ZOOM_FOR_LABELS);}// 初始调用一次,设置初始状态updateLabelsVisibility();// 监听地图的移动结束事件(包括缩放和拖动)map.on("moveend", updateLabelsVisibility);// 4. 需求:缩放到一定的程度后再显示标注图层============end</script></body>
</html>

多边形绘制和标记

基础示例

效果图:

image

示例代码:

<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="UTF-8" /><title>OpenLayers 街景与地名标注</title><!-- 引入 OpenLayers CSS --><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.css" /><!-- 引入 OpenLayers JavaScript --><script src="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.js"></script><style>#map {width: 100%;height: 800px;}.info {/* position: absolute;top: 10px;left: 10px; */background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);/* max-width: 250px; */}/* 绘制工具 */.toolbar {/* position: absolute;top: 10px;right: 10px; */background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);}.toolbar button {/* display: block;width: 100%; */padding: 8px 12px;margin-bottom: 5px;background: #f5f5f5;border: 1px solid #ddd;border-radius: 3px;cursor: pointer;transition: all 0.2s;}.toolbar button:hover {background: #e0e0e0;}.toolbar button.active {background: #4285f4;color: white;border-color: #4285f4;}.status-panel {background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);max-height: 200px;overflow-y: auto;}.feature-count {color: #666;font-size: 14px;margin-bottom: 10px;}</style></head><body><div class="info">当前缩放级别: <span id="zoom-level">0</span><br />标注将在缩放级别 ≥ 8 时显示</div><div class="toolbar"><button id="draw-point">绘制点标记</button><button id="draw-line-string">绘制线</button><button id="draw-polygon">绘制多边形</button><button id="clear">清除所有绘制</button></div><div class="data-panel"><h4>绘制数据信息:</h4><pre id="data-display"></pre></div><!-- <div class="data-panel"><h4>绘制数据信息:</h4><pre id="latest-data"></pre><div class="history-list"><h5>历史绘制记录:</h5><ul id="history-data"></ul></div></div> --><div class="status-panel"><div class="feature-count">当前已绘制: <span id="count">0</span> 个要素</div><div><h4>最近绘制数据:</h4><pre id="last-feature-data"></pre></div></div><div id="map"></div><script>var map = new ol.Map({target: "map",layers: [// 底图图层,这里使用 OpenStreetMapnew ol.layer.Tile({// source: new ol.source.OSM(),source: new ol.source.XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",}),}),],view: new ol.View({center: ol.proj.fromLonLat([108, 28]),zoom: 8,}),});var vectorSource = new ol.source.Vector({url: "./places.json", // 地名数据文件路径format: new ol.format.GeoJSON(),});var vectorLayer = new ol.layer.Vector({source: vectorSource,style: function (feature) {var textStyle = new ol.style.Text({text: feature.get("name"), // 获取地名属性font: "12px Arial",fill: new ol.style.Fill({color: "#000",}),stroke: new ol.style.Stroke({color: "#fff",width: 2,}),offsetY: -15, // 文字相对于点的垂直偏移});var pointStyle = new ol.style.Style({image: new ol.style.Circle({radius: 5,fill: new ol.style.Fill({color: "#ff0000",}),}),text: textStyle,});return pointStyle;},});map.addLayer(vectorLayer);map.on("click", function (evt) {var coordinate = evt.coordinate;console.log("点击位置经纬度:" + ol.proj.toLonLat(coordinate));});var zoomLevelElement = document.getElementById("zoom-level");var MIN_ZOOM_FOR_LABELS = 8;function updateLabelsVisibility() {var currentZoom = map.getView().getZoom();zoomLevelElement.textContent = currentZoom.toFixed(1);vectorLayer.setVisible(currentZoom >= MIN_ZOOM_FOR_LABELS);}updateLabelsVisibility();map.on("moveend", updateLabelsVisibility);// 绘制// 绘制交互变量let draw;// 创建矢量数据源和图层const vector_source = new ol.source.Vector();// 创建矢量图层并关联数据源const vector_layer = new ol.layer.Vector({source: vector_source,style: new ol.style.Style({fill: new ol.style.Fill({ color: "rgba(0, 153, 255, 0.2)" }),stroke: new ol.style.Stroke({ color: "#0099ff", width: 2 }),image: new ol.style.Circle({radius: 6,fill: new ol.style.Fill({ color: "#0099ff" }),stroke: new ol.style.Stroke({ color: "white", width: 1 }),}),}),});map.addLayer(vector_layer);const dataDisplay = document.getElementById("data-display");const countElement = document.getElementById("count");const lastFeatureElement = document.getElementById("last-feature-data");// 更新要素计数显示function updateFeatureCount() {const count = vector_source.getFeatures().length;countElement.textContent = count;}// 激活绘制工具的函数function activateDraw(type, id) {// 移除现有的绘制交互if (draw) {map.removeInteraction(draw);}// 清除按钮的active状态document.querySelectorAll(".toolbar button").forEach((btn) => {btn.classList.remove("active");});// 如果不是清除操作,则激活相应的绘制工具if (type !== "clear") {document.getElementById(id).classList.add("active");// 创建新的绘制交互draw = new ol.interaction.Draw({// 绘制的内容会添加到这个数据源source: vector_source,type: type,});map.addInteraction(draw);// 监听绘制结束事件draw.on("drawend", function (event) {// 获取绘制的要素const feature = event.feature;// 获取几何图形const geometry = feature.getGeometry();// 根据几何类型处理数据let data, type;switch (geometry.getType()) {case "Point":type = "点";// OpenLayers 默认使用 Web Mercator 投影坐标(米为单位),转换为经纬度坐标(度为单位)const coords = ol.proj.toLonLat(geometry.getCoordinates());data = `坐标: [${coords[0].toFixed(6)}, ${coords[1].toFixed(6)}]`;break;case "LineString":type = "线";// 线的坐标数组const lineCoords = geometry.getCoordinates().map((coord) => ol.proj.toLonLat(coord)).map((coord) => `[${coord[0].toFixed(6)}, ${coord[1].toFixed(6)}]`);data = `路径点: [\n  ${lineCoords.join(",\n  ")}\n]`;break;case "Polygon":type = "多边形";// 多边形的坐标数组(外层数组是多边形环,取第一个环)const polygonCoords = geometry.getCoordinates()[0].map((coord) => ol.proj.toLonLat(coord)).map((coord) => `[${coord[0].toFixed(6)}, ${coord[1].toFixed(6)}]`);data = `顶点: [\n  ${polygonCoords.join(",\n  ")}\n]`;break;}// 显示数据dataDisplay.textContent = `绘制了${type}:\n${data}\n\n历史数据可通过vectorSource获取`;lastFeatureElement.textContent = data;// 更新要素计数// 确保添加完成后再更新计数setTimeout(() => {updateFeatureCount();}, 200);});}}// 绑定按钮事件document.getElementById("draw-point").addEventListener("click", () => {activateDraw("Point", "draw-point");});document.getElementById("draw-line-string").addEventListener("click", () => {activateDraw("LineString", "draw-line-string");});document.getElementById("draw-polygon").addEventListener("click", () => {activateDraw("Polygon", "draw-polygon");});document.getElementById("clear").addEventListener("click", () => {// 清除所有绘制的要素vector_source.clear();// 移除绘制交互if (draw) {map.removeInteraction(draw);draw = null;}// 清除按钮的active状态document.querySelectorAll(".toolbar button").forEach((btn) => {btn.classList.remove("active");dataDisplay.textContent = "所有绘制已清除";// 更新显示lastFeatureElement.textContent = "所有要素已清除";updateFeatureCount();});});</script></body>
</html>

增加信息窗

效果图:

image

示例代码:

<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="UTF-8" /><title>OpenLayers 街景与地名标注</title><!-- 引入 OpenLayers CSS --><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.css" /><!-- 引入 OpenLayers JavaScript --><script src="https://cdn.jsdelivr.net/npm/ol@7.5.1/dist/ol.js"></script><style>#map {width: 100%;height: 800px;}.info {/* position: absolute;top: 10px;left: 10px; */background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);/* max-width: 250px; */}/* 绘制工具 */.toolbar {/* position: absolute;top: 10px;right: 10px; */background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);}.toolbar button {/* display: block;width: 100%; */padding: 8px 12px;margin-bottom: 5px;background: #f5f5f5;border: 1px solid #ddd;border-radius: 3px;cursor: pointer;transition: all 0.2s;}.toolbar button:hover {background: #e0e0e0;}.toolbar button.active {background: #4285f4;color: white;border-color: #4285f4;}.status-panel {background: white;padding: 10px;border-radius: 5px;box-shadow: 0 1px 5px rgba(0, 0, 0, 0.2);max-height: 200px;overflow-y: auto;}.feature-count {color: #666;font-size: 14px;margin-bottom: 10px;}/* 信息弹窗样式 */.popup {position: absolute;background-color: white;padding: 10px;border: 1px solid #ccc;border-radius: 5px;box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);pointer-events: auto;display: none;}.popup-content {min-width: 200px;}.popup-closer {position: absolute;top: 5px;right: 5px;cursor: pointer;font-size: 16px;}</style></head><body><div class="info">当前缩放级别: <span id="zoom-level">0</span><br />标注将在缩放级别 ≥ 8 时显示</div><div class="toolbar"><button id="draw-point">绘制点标记</button><button id="draw-line-string">绘制线</button><button id="draw-polygon">绘制多边形</button><button id="clear">清除所有绘制</button><button id="save">保存</button></div><div class="data-panel"><h4>绘制数据信息:</h4><pre id="data-display"></pre></div><!-- <div class="data-panel"><h4>绘制数据信息:</h4><pre id="latest-data"></pre><div class="history-list"><h5>历史绘制记录:</h5><ul id="history-data"></ul></div></div> --><div class="status-panel"><div class="feature-count">当前已绘制: <span id="count">0</span> 个要素</div><div><h4>最近绘制数据:</h4><pre id="last-feature-data"></pre></div></div><!-- 信息弹窗 --><div id="popup" class="popup"><a href="#" class="popup-closer" onclick="hidePopup()">&times;</a><div id="popup-content" class="popup-content"></div></div><div id="map"></div><script>var map = new ol.Map({target: "map",layers: [// 底图图层,这里使用 OpenStreetMapnew ol.layer.Tile({// source: new ol.source.OSM(),source: new ol.source.XYZ({url: "https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}",}),}),],view: new ol.View({center: ol.proj.fromLonLat([108, 28]),zoom: 8,}),});var vectorSource = new ol.source.Vector({url: "./places.json", // 地名数据文件路径format: new ol.format.GeoJSON(),});var vectorLayer = new ol.layer.Vector({source: vectorSource,style: function (feature) {var textStyle = new ol.style.Text({text: feature.get("name"), // 获取地名属性font: "12px Arial",fill: new ol.style.Fill({color: "#000",}),stroke: new ol.style.Stroke({color: "#fff",width: 2,}),offsetY: -15, // 文字相对于点的垂直偏移});var pointStyle = new ol.style.Style({image: new ol.style.Circle({radius: 5,fill: new ol.style.Fill({color: "#ff0000",}),}),text: textStyle,});return pointStyle;},});map.addLayer(vectorLayer);map.on("click", function (evt) {var coordinate = evt.coordinate;console.log("点击位置经纬度:" + ol.proj.toLonLat(coordinate));// 检查点击位置是否有要素map.forEachFeatureAtPixel(evt.pixel, function (feature) {// 核心过滤逻辑:排除临时要素(只有带 isFinished: true 的才是正式要素)// 如果点击的是多边形// if (feature.get("isFinished") && feature.getGeometry() instanceof ol.geom.Polygon) {//   showPopup(evt.coordinate, feature);//   return true; // 停止遍历// }if (feature.get("isFinished")) {showPopup(evt.coordinate, feature);return true; // 停止遍历}});});var zoomLevelElement = document.getElementById("zoom-level");var MIN_ZOOM_FOR_LABELS = 8;function updateLabelsVisibility() {var currentZoom = map.getView().getZoom();zoomLevelElement.textContent = currentZoom.toFixed(1);vectorLayer.setVisible(currentZoom >= MIN_ZOOM_FOR_LABELS);}updateLabelsVisibility();map.on("moveend", updateLabelsVisibility);// 绘制// 绘制交互变量let draw;// 创建矢量数据源和图层const vector_source = new ol.source.Vector();// 创建矢量图层并关联数据源const vector_layer = new ol.layer.Vector({source: vector_source,style: new ol.style.Style({fill: new ol.style.Fill({ color: "rgba(0, 153, 255, 0.2)" }),stroke: new ol.style.Stroke({ color: "#0099ff", width: 2 }),image: new ol.style.Circle({radius: 6,fill: new ol.style.Fill({ color: "#0099ff" }),stroke: new ol.style.Stroke({ color: "white", width: 1 }),}),}),});map.addLayer(vector_layer);const dataDisplay = document.getElementById("data-display");const countElement = document.getElementById("count");const lastFeatureElement = document.getElementById("last-feature-data");const saveElement = document.getElementById("save");// 更新要素计数显示function updateFeatureCount() {const count = vector_source.getFeatures().length;countElement.textContent = count;}// 计算多边形面积(平方米)function calculateArea(geometry) {const area = geometry.getArea();// 转换为平方米(如果需要)return Math.round(area) + " 平方米";}// 激活绘制工具的函数function activateDraw(type, id) {// 移除现有的绘制交互if (draw) {map.removeInteraction(draw);}// 清除按钮的active状态document.querySelectorAll(".toolbar button").forEach((btn) => {btn.classList.remove("active");});// 如果不是清除操作,则激活相应的绘制工具if (type !== "clear") {document.getElementById(id).classList.add("active");// 创建新的绘制交互draw = new ol.interaction.Draw({// 绘制的内容会添加到这个数据源source: vector_source,type: type,});map.addInteraction(draw);// 监听绘制结束事件draw.on("drawend", function (event) {// event.stopPropagation();draw.setActive(false);// 获取绘制的要素const feature = event.feature;// 获取几何图形const geometry = feature.getGeometry();// 给正式要素添加标识(用于后续弹窗过滤)feature.set("isFinished", true);// 添加其他属性(如面积)// 多边形// feature.set("area", Math.round(geometry.getArea()) + " 平方米");// feature.set("name", "多边形" + vector_source.getFeatures().length);feature.set("test_data", {name: "zs",age: 36,friend: ["kobe", "lili"],});// 根据几何类型处理数据let data, type;switch (geometry.getType()) {case "Point":type = "点";// OpenLayers 默认使用 Web Mercator 投影坐标(米为单位),转换为经纬度坐标(度为单位)const coords = ol.proj.toLonLat(geometry.getCoordinates());data = `坐标: [${coords[0].toFixed(6)}, ${coords[1].toFixed(6)}]`;break;case "LineString":type = "线";// 线的坐标数组const lineCoords = geometry.getCoordinates().map((coord) => ol.proj.toLonLat(coord)).map((coord) => `[${coord[0].toFixed(6)}, ${coord[1].toFixed(6)}]`);data = `路径点: [\n  ${lineCoords.join(",\n  ")}\n]`;break;case "Polygon":type = "多边形";// 多边形的坐标数组(外层数组是多边形环,取第一个环)const polygonCoords = geometry.getCoordinates()[0].map((coord) => ol.proj.toLonLat(coord)).map((coord) => `[${coord[0].toFixed(6)}, ${coord[1].toFixed(6)}]`);data = `顶点: [\n  ${polygonCoords.join(",\n  ")}\n]`;break;}// 显示数据dataDisplay.textContent = `绘制了${type}:\n${data}\n\n历史数据可通过vectorSource获取`;lastFeatureElement.textContent = data;// 更新要素计数// 确保添加完成后再更新计数setTimeout(() => {updateFeatureCount();}, 200);});}}// 绑定按钮事件document.getElementById("draw-point").addEventListener("click", () => {activateDraw("Point", "draw-point");});document.getElementById("draw-line-string").addEventListener("click", () => {activateDraw("LineString", "draw-line-string");});document.getElementById("draw-polygon").addEventListener("click", () => {activateDraw("Polygon", "draw-polygon");});document.getElementById("clear").addEventListener("click", () => {// 清除所有绘制的要素vector_source.clear();// 移除绘制交互if (draw) {map.removeInteraction(draw);draw = null;}// 清除按钮的active状态document.querySelectorAll(".toolbar button").forEach((btn) => {btn.classList.remove("active");dataDisplay.textContent = "所有绘制已清除";// 更新显示lastFeatureElement.textContent = "所有要素已清除";updateFeatureCount();});});document.getElementById("save").addEventListener("click", () => {if (draw) {map.removeInteraction(draw);}});// 显示弹窗function showPopup(coordinate, feature) {const popup = document.getElementById("popup");const popupContent = document.getElementById("popup-content");// 设置弹窗内容// 示例:多边形// popupContent.innerHTML = `//         <h3>${feature.get("name")}</h3>//         <p>面积: ${feature.get("area")}</p>//         <p>ID: ${feature.getId()}</p>//     `;const test_data = feature.get("test_data");popupContent.innerHTML = `<h1>测试数据</h1><h3>姓名:${test_data.name}</h3><h3>年龄:${test_data.age}</h3><h3>朋友:${JSON.stringify(test_data.friend)}</h3>`;console.log("dddddd==>", feature.get("test_data"));// 设置弹窗位置const overlay = new ol.Overlay({element: popup,positioning: "bottom-center",stopEvent: false,offset: [0, -10],});map.addOverlay(overlay);overlay.setPosition(coordinate);// 显示弹窗popup.style.display = "block";}// 隐藏弹窗function hidePopup() {const popup = document.getElementById("popup");popup.style.display = "none";}// 鼠标悬停时改变光标样式map.on("pointermove", function (e) {const pixel = map.getEventPixel(e.originalEvent);const hit = map.hasFeatureAtPixel(pixel);map.getTargetElement().style.cursor = hit ? "pointer" : "";});</script></body>
</html>

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

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

相关文章

VMware ESXi 9.0.1.0 macOS Unlocker OEM BIOS 2.7 AQC 网卡特殊定制版

VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 AQC 网卡特殊定制版VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 AQC 网卡特殊定制版 VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 集…

推荐系统三大技术挑战解析

本文深入探讨推荐系统面临的三大技术挑战:有向图中的非对称推荐关系处理、目标标签随时间变化的模型训练策略,以及利用预测不确定性提升模型准确性的创新方法。在今年的ACM推荐系统会议上,某机构国际新兴商店部门应…

VMware ESXi 9.0.1.0 macOS Unlocker OEM BIOS 2.7 ConnectX-3 网卡特殊定制版

VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 ConnectX-3 网卡特殊定制版VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 ConnectX-3 网卡特殊定制版 VMware ESXi 9.0.1.0 macOS Unlocker & O…

VMware ESXi 9.0.1.0 macOS Unlocker OEM BIOS 2.7 NVMe 驱动特殊定制版

VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 NVMe 驱动特殊定制版VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 NVMe 驱动特殊定制版 VMware ESXi 9.0.1.0 macOS Unlocker & OEM BIOS 2.7 …

博客SEO优化实战:从入门到精通 - 教程

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

读技术之外:社会联结中的人工智能06分类

读技术之外:社会联结中的人工智能06分类1. 分类 1.1. 塞缪尔莫顿1.1.1. Samuel Morton1.1.1.1. 美国颅骨学家1.1.1.2. 医生和自然历史学家1.1.1.3. 费城自然科学院的成员1.1.2. 通过比较头骨的物理特征,来“客观地”…

中文二字词词语接龙的最长最短路径

结论:长度13个词。有3种起始字,6种结束字,共18条路径。 具体规则:取 mapull/chinese-dictionary,去除含有非中文字符或非二字的词语为词典。不允许出现重复尾字,字形一样即可接龙。 方便起见,我们约定省去重复的…

【GitHub每日速递 251011】无需注册!本地开源AI应用构建器Dyad,跨平台速下载!

原文: https://mp.weixin.qq.com/s/3cKyqVciKXCUmUgKKKLYjw 全网数百平台通吃!ytDownloader 多系统适用无广告高速下载神器来袭 ytDownloader 是一个支持从数百个网站下载视频和音频的桌面应用。简单讲,它是一个能帮…

SignTool 使用 SafeNet eToken 硬证书进行代码签名

现在软件代码签名已经不能用 pfx 软证书了,需要搭配 FIPS140-2 Level2、Common Criteria EAL4级以上或者同等认证级别的硬件,如 USB 令牌、硬件安全模块 HSM 等才能完成签名根据CA/B联盟国际标准要求,从 2022 年 11…

计算机网络技术全面解析:从基础架构到未来趋势

本文深入解析计算机网络的核心概念,涵盖网络类型、拓扑结构、关键组件及通信协议,同时探讨网络优势、风险挑战与未来发展趋势,为理解现代网络技术提供全面指南。什么是计算机网络? 计算机网络是指在信息系统中通过…

高增长行业碳减排技术路径解析

本文探讨了高增长经济部门实现碳减排的技术路径,包括可再生能源应用、电动交通转型、物流系统优化等关键技术领域,分析了清洁能源基础设施和零排放车辆等技术挑战与解决方案。高增长经济部门碳减排的技术路径 应对气…

css_01_自适应grid布局

网格布局根据宽度自动分配列数和列宽 主要是在设置 grid-template-columns 时设置repeat的第一个参数是 auto-fill或auto-fit第二个参数使用minmax和min进行配合让宽度使用最小值 注:希望grid中单元格宽度固定就使用 …

css01_自适应grid布局

网格布局根据宽度自动分配列数和列宽 主要是在设置 grid-template-columns 时设置repeat的第一个参数是 auto-fill或auto-fit第二个参数使用minmax和min进行配合让宽度使用最小值 注:希望grid中单元格宽度固定就使用 …

Software Foundations Vol.I : 更多基本策略(Tactics)

Software Foundations Vol.I : 更多基本策略(Tactics)本章主要内容包括:如何在“向前证明”和“向后证明”两种风格中使用辅助引理; 如何对数据构造子进行论证,特别是,如何利用它们单射且不交的事实; 如何增强归纳…

Ai元人文:算力的涅槃——当“悟空之眼”照见AI决策的下一纪元

让我们以相同的硬件为舞台,展开一场关于“模拟悟空决策”范式与传统大模型之间,那场关乎效率与智慧本质的深刻对话。 在这场人工智能的竞赛中,我们常被一种叙事所主导:更大的模型、更多的数据、更强的算力。这是一…

关于微信公众号/服务号自动回消息问题(python)

天呐!!!!!真的忙活了好久,终于在将近凌晨两点的时候解决了问题。进入正题。是的,没有错,如果你怀疑微信那边给的示例有问题那是对的,至少其给的示例在python3上有问题(我测试是如此哈, python3.9),需要改动一…

10.10 闲话

Alexander Hamilton.《会魔法的老人》 我从出生就是一个自闭小孩 容易被别人一句话给轻易伤害 所以 我在唱台上 不断的摆弄我的肢体 为了阻挡光线 和我眼神里的荒诞 独自在电影院里 观看一部杰作 野火在我的心底燃烧 梦…

Python 中的函数签名:详解与实例

Python 中的函数签名:详解与实例 函数签名(Function Signature)在 Python 中是对函数调用接口的结构化描述,它定义了函数接收参数的方式、类型提示以及返回值信息。Python 的函数签名具有灵活性,不强制参数类型,…

基于AXI模块的视频流传输(上板移植篇)

先发泄一下,终于!!!国庆!一个国庆,你知道我怎么过的吗!!! 首先我是拿官方例程,但是还是依旧跑不通,检查一下,发现以下几个问题,并且我是怎么处理的: 1、首先上板失败,可能由于只是粗略配置了一下管脚没配…

装饰器工厂与类装饰器:进阶装饰器技术解析

装饰器工厂与类装饰器:进阶装饰器技术解析 装饰器是Python中强大的元编程工具,除多种进阶形式。其中装饰器工厂(Decorator Factory)和类装饰器(Class Decorator)是两种重要变体,分别解决“带参数的装饰器”和“…