Vue3 + 高德地图实现围栏绘制与线路渲染(含 GeoJSON 支持)

在项目中,往往需要通过地图进行区域围栏绘制、线路渲染 等功能,用于数据可视化、行为监控、地理标注等业务场景。本文将基于 Vue 3 + 高德地图 JSAPI 实现一个完整的地图功能模块,包括:

  • 地图初始化与 GeoJSON 加载

  • 绘制围栏(可编辑)

  • 渲染多边形遮罩层

  • 动态加载中心线、左/右边界线等结构化线路

📌 适用于城市交通可视化、车辆轨迹管控、地图交互平台等项目。


🧩一、技术栈与依赖

  • Vue 3 Composition API

  • 高德地图 JSAPI v2.0

  • 支持 Element Plus 按钮交互(仅 UI)

  • 加载本地 GeoJSON 线路数据


🗺️二、地图初始化与基础设置

我们首先使用 @amap/amap-jsapi-loader 来加载高德地图 JS:

复制代码
AMapLoader.load({
  key: "你的高德Key",
  version: "2.0",
  plugins: [
    "AMap.MouseTool", "AMap.Polygon", "AMap.PolyEditor", 
    "AMap.OverlayGroup", "AMap.DistrictSearch", ...
  ],
}).then((AMap) => {
  map = new AMap.Map("container", {
    zoom: 15.5,
    center: [113.50099365, 23.04139783],
    mapStyle: "amap://styles/darkblue", // 暗色背景,突出图层
    WebGLParams: { preserveDrawingBuffer: true },
  });

  pointsGroup = new AMap.OverlayGroup();
  map.add(pointsGroup);

  drawGeoJsonLines(); // 加载线路
  drawDist(map);      // 加载遮罩层
});

🧱三、GeoJSON 数据线路渲染

使用一个本地 outlines.json 文件进行数据加载。我们通过 drawGeoJsonFeature 方法解析每一个 feature:

复制代码
const drawGeoJsonFeature = (feature) => {
  const { geometry, properties } = feature;

  // 多边形区域显示为透明遮罩
  const polygon = new AMap.Polygon({
    path: geometry.coordinates?.[0]?.map(([lng, lat]) => [lng, lat]),
    strokeColor: "#fff",
    strokeOpacity: 0.1,
    fillOpacity: 0.01,
  });
  polygon.setMap(map);
  overlays.push(polygon);

  // 渲染每一类线(如中心线、左右边界线)
  Object.entries(lineStyleMap).forEach(([key, color]) => {
    const lineData = properties[key];
    if (!lineData?.geometry?.length) return;

    const path = lineData.geometry.map(p => [p.lng, p.lat]);
    const polyline = new AMap.Polyline({ path, strokeColor: color });
    polyline.setMap(map);
    overlays.push(polyline);
  });
};

centerLineleftBoundaryLinerightBoundaryLine 等结构都封装在 GeoJSON 的 properties 属性中,便于扩展。


🖌️四、围栏绘制与编辑功能

地图点击按钮可开启手绘模式,利用高德的 MouseTool 工具类进行绘制:

复制代码
const drawFence = () => {
  let mouseTool = new AMap.MouseTool(map);
  mouseTool.polygon({
    strokeColor: "#FEB80A",
    strokeWeight: 6,
    fillOpacity: 0.2,
  });

  mouseTool.on("draw", (event) => {
    mouseTool.close(true);
    const path = event.obj.getPath().map((p) => [p.lng, p.lat]);
    blockDrawFence({ path, flag: "2" });
  });
};

用户绘制完成后,可进入编辑模式,并监听结束编辑事件:

复制代码
blockEditor = new AMap.PolyEditor(map, polygonLayer);
blockEditor.on("end", (event) => {
  emit("fence-update", event.target._opts.path); // 实时更新路径
});

🧱五、遮罩层区域绘制

为确保围栏和线路都只在我们指定的区域显示,我们绘制一个包含全国的"外包围"大矩形作为遮罩外框:

复制代码
const drawDist = (map) => {
  let outer = [
    new AMap.LngLat(-360, 90), new AMap.LngLat(-360, -90),
    new AMap.LngLat(360, -90), new AMap.LngLat(360, 90),
  ];
  let pathArray = [outer, JSON.parse(props.fences)];

  let polygon = new AMap.Polygon({
    strokeColor: "#00eeff",
    fillColor: "#71B3ff",
    fillOpacity: 0.5,
  });

  polygon.setPath(pathArray);
  map.add(polygon);
};

📌 注意:遮罩图层要最晚渲染,并使用较高的 fillOpacity,可防止路线图层"盖住"遮罩图层。


🎮六、交互 UI 与地图控制面板

复制代码
<el-button v-if="editPoints[0] == ''" @click="drawFence">标记角点</el-button>
<el-button v-else @click="editBlockDrawFence">编辑围栏</el-button>
<el-button v-else @click="editBlockCloseDrawFence">结束编辑</el-button>

可通过按钮实现"开始绘制 - 编辑围栏 - 结束编辑"三段式操作,符合用户思维流。


🧠七、层级问题及修复建议

问题:线路在遮罩层上方

此问题常见于:

  • 多边形 Polygon 图层未设置 zIndex,默认图层排序不一致;

  • 线路渲染顺序早于遮罩层;

  • 遮罩层 fillOpacity 太小。

✅解决方案:

复制代码
const polygon = new AMap.Polygon({
  path: coords,
  strokeColor: "#fff",
  fillColor: "#fff",
  fillOpacity: 0.9,  // 不透明
  zIndex: 1000,       // 提升层级
});

确保遮罩层 zIndex 高于线路图层(线路建议设为 zIndex: 10 ~ 100)。


✅总结

本组件可作为地图绘制交互模块的通用模板,具备以下优势:

  • ✅ 支持任意 GeoJSON 线路绘制(中心线、边界线)

  • ✅ 支持区域围栏绘制与编辑

  • ✅ 可灵活接入业务平台,适用于智慧城市、交通监控等项目

  • ✅ 支持遮罩层绘制,限制展示区域


📦项目扩展建议

  • 🚀支持多围栏绘制

  • 📊集成围栏属性统计与数据绑定

  • 📍支持围栏内点位聚合或热力图渲染

  • 🌍兼容 Mapbox 或 Cesium 等其他地图平台


如果你对这个项目感兴趣,可以点赞+收藏+关注我,后续我将推出 Vue3 + Mapbox 实现 3D 车辆轨迹回放 的实战教程。

相关推荐
拾光拾趣录13 分钟前
Element Plus表格表头动态刷新难题:零闪动更新方案
前端·vue.js·element
空の鱼1 小时前
js与vue基础学习
javascript·vue.js·学习
鱼樱前端1 小时前
2025前端SSR框架之十分钟快速上手Nuxt3搭建项目
前端·vue.js
HYI2 小时前
naive-ui n-data-table 使用踩坑总结
vue.js
JosieBook3 小时前
【前端】Vue 3 页面开发标准框架解析:基于实战案例的完整指南
前端·javascript·vue.js
薄荷椰果抹茶3 小时前
前端技术之---应用国际化(vue-i18n)
前端·javascript·vue.js
墨苒孤3 小时前
【Vue】tailwindcss + ant-design-vue + vue-cropper 图片裁剪功能(解决遇到的坑)
vue.js·vue-croppper
结城3 小时前
使用位运算优化 Vue.js 应用:高效状态管理技巧
vue.js
初出茅庐的3 小时前
uniapp - AI 聊天页面布局的实现
前端·vue.js·uni-app
晴殇i4 小时前
Vue i18n插件:实现Web应用多语言切换的
前端·javascript·vue.js