Vue leaflet 的使用代码示范

96 min read
<template>
  <!-- 组件模板部分包含一个显示地图的div元素 -->
  <div id="site-plan-map" style="height: 100vh; width: 100vw"></div>
</template>

<script>
import {map, imageOverlay, LatLng, CRS, LatLngBounds, geoJSON} from "leaflet";
import "leaflet/dist/leaflet.css"; // 导入Leaflet样式文件
import jsonData from "./geo.json"; // 导入包含地图要素的GeoJSON文件

export default {
  name: "SitePlanMap", // 组件名称
  mounted() {
    this.initMap(); // 在组件挂载后初始化地图
  },
  // add props onClick
  props: {
    onClickPoint: { // onClickPoint prop,用于接受点击事件处理函数
      type: Function,
      default: () => {},
    },
  },
  methods: {
    async getImageDimensions(url) { // 获取图片宽高的函数
      const img = new Image();
      return new Promise((resolve, reject) => {
        img.onload = () => resolve({
          width: img.width,
          height: img.height
        });
        img.onerror = reject;
        img.src = url;
      });
    },
    getBounds(w, h) { // 计算地图边界的函数
      let x;
      let y;

      if (w / 2 >= h) {
        x = 180;

        y = h * (x / w);
      } else if (h > w || w / 2 < h) {
        y = 90;

        x = w * (y / h);
      }

      let c1 = new LatLng(-y, -x);
      let c2 = new LatLng(y, x);

      return new LatLngBounds(c1, c2);
    },
    addListeners(layer) { // 为每个GeoJSON要素添加事件监听器
      layer.on("click", () => {
        if (layer.feature.properties.name) {
          this.$emit("onClickPoint", layer.feature.properties.name);
        }
      });
    },
    initMap() { // 初始化地图的函数
      const mapConfig = {
        crs: CRS.Simple, // 地图坐标系类型
        minZoom: 0, // 最小缩放级别
        attributionControl: false, // 是否显示地图版权信息
      };
      const mapInstance = map("site-plan-map", mapConfig); // 创建地图实例

      const geomanControlConfig = { // 设置地图绘制控件的配置项
        drawMarker: false,
        drawCircleMarker: false,
        drawPolyline: false,
        drawCircle: false,
        drawText: false,
      };
      mapInstance.pm.addControls(geomanControlConfig); // 将绘制控件添加到地图中

      const imageUrl = "./bg.png"; // 背景图片的URL
      this.getImageDimensions(imageUrl).then((dimensions) => { // 获取背景图片的宽高
        const bounds = this.getBounds(dimensions.width || 0, dimensions.height); // 计算地图边界
        mapInstance.setMaxBounds(bounds); // 设置地图最大边界
        mapInstance.fitBounds(bounds); // 将地图缩放至合适的大小
        mapInstance.on("pm:create", ({layer}) => {
      layer.setStyle({color: "#3388ff"}); // 设置新创建的图层的样式
    });
    const mapOverlay = imageOverlay(imageUrl, bounds); // 创建地图叠加层
    mapOverlay.addTo(mapInstance); // 添加叠加层到地图上
    mapInstance.panTo(new LatLng(0, 0)); // 将地图视图移动到中心点

    let importedGeoJSON = geoJSON(jsonData, { // 创建包含地图要素的GeoJSON图层
      onEachFeature: (feature, layer) => {
        this.addListeners(layer); // 为每个要素添加事件监听器
      },
    });
    importedGeoJSON.addTo(mapInstance); // 添加GeoJSON图层到地图上
  	});
		},
	},
};
</script>

标识

const getMarkerColor = (data) => {
  if (data.value1 > 10) {
    return "red";
  } else if (data.value2 < 5) {
    return "blue";
  } else {
    return "green";
  }
};

import { marker, Icon } from "leaflet";

const createCustomMarker = (latLng, data) => {
  const markerColor = getMarkerColor(data);
  const customIcon = new Icon({
    iconUrl: `https://cdn.jsdelivr.net/gh/pointhi/leaflet-color-markers/img/marker-icon-2x-${markerColor}.png`,
    shadowUrl: "https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.7.1/images/marker-shadow.png",
    iconSize: [25, 41],
    iconAnchor: [12, 41],
    popupAnchor: [1, -34],
    shadowSize: [41, 41],
  });

  return marker(latLng, { icon: customIcon });
};


使用

const myData = {
  value1: 15,
  value2: 3,
};

const myLatLng = new LatLng(51.505, -0.09);
const myMarker = createCustomMarker(myLatLng, myData);
myMarker.addTo(mapInstance);