高德地图API自用记录
功能需求:
需求:高德地图,加载点位信息,点击marker弹出信息窗口,右上角模糊搜索选择,自动切换marker以及信息窗口。 添加行政区边界,边界外添加透明灰背景。
- 首先,初始化地图,引入高德的web api js
<script src="https://webapi.amap.com/maps?v=2.0&key=你的Key"></script>
<script src="//webapi.amap.com/ui/1.1/main.js?v=1.1.1"></script>
2. 初始化地图,获取行政区域坐标和所需拿到的标记点的坐标
<template>
<div class="search-box">
<el-select v-model="searchValue" style="width: 200px" @change="onSearch" filterable clearable placeholder="请输入桥梁名称">
<el-option
v-for="item in mapData"
:key="item.id"
:label="item.bridgeName"
:value="item.id" />
</el-select>
</div>
<div>
<div id="map" ref="mapContainer" style="width: 100%; height: 800px;"></div>
</div>
</template>
<style>
.search-box {
position: absolute;
top: 16px;
right: 20px;
display: flex;
gap: 10px;
}
</style>
const mapData = ref<any>([]);
const mapContainer = ref(null); // 新增DOM容器引用
const map = ref<AMap.Map>(); // 保持地图实例专用
const searchValue = ref('');
const markersMap = ref<Record<string, AMap.Marker>>({});
const infoWindowsMap = ref<Record<string, any>>({}); // 新增infoWindow存储
const isSelectInfoMap = ref<any>();
const getMapInfo = () => {
DashboardApi.getMapInfo().then((res: any) => {
mapData.value = res;
initMap();
})
}
const initMap = () => {
map.value = markRaw(new AMap.Map('map', {
center: [121.5879052,29.83087043], // 宁波市鄞州区的经纬度
zoom: 14, // 缩放级别
}));
fetchDistrictBoundary();
};
const fetchDistrictBoundary = () => {
const url = `https://restapi.amap.com/v3/config/district?key=你的Key&keywords=鄞州区&subdistrict=3&extensions=all`;
fetch(url)
.then(response => response.json())
.then(data => {
if (data.status === '1') {
const district = data.districts[0];
const boundary = parseBoundary(district.polyline);
drawPolygon(boundary);
addMarkers();
}
})
.catch(error => {
console.error('Error fetching district boundary:', error);
});
};
// 解析坐标数据
const parseBoundary = (polyline: string) => {
return polyline.split(';').map(point => {
const [lng, lat] = point.split(',').map(Number);
return [lng, lat];
});
};
3.为行政区域画出边界线和外部区域的阴影
const drawPolygon = (boundary) => {
const worldBounds = [
[0, 90], // 左上角坐标
[180, 90], // 右上角
[180, -90], // 右下角
[0, -90], // 左下角
[0, 90] // 闭合路径
];
// 1. 绘制外部灰色背景
const outerBoundary = new AMap.Polygon({
path: [worldBounds, boundary],
strokeColor: '#D3D3D3', // 灰色边界
strokeOpacity: 0, // 透明的边界
strokeWeight: 0, // 无边界宽度
fillColor: '#D3D3D3', // 灰色填充
fillOpacity: 0.7, // 灰色背景透明度
fillRule: 'evenodd'
});
outerBoundary.setMap(map.value);
// 2. 绘制鄞州区的蓝色边界
const innerBoundary = new AMap.Polygon({
path: boundary,
strokeColor: '#318ec9', // 蓝色边界
strokeOpacity: 0.8, // 边界透明度
strokeWeight: 4, // 边界宽度
fillColor: 'transparent', // 内部不填充颜色
fillOpacity: 0, // 不填充
});
innerBoundary.setMap(map.value);
};
4.对地图添加标记的点位,自定义marker点击后的样式并添加点击监听
const addMarkers = () => {
const data = mapData.value;
// 加载 AMapUI 的 SimpleInfoWindow 组件
data.forEach((item: any) => {
const marker = new AMap.Marker({
position: [item.longitude, item.latitude],
title: item.bridgeName,
});
// 为每个标记创建独立的信息窗体
const infoWindow = new AMap.InfoWindow({
content: `
<div class="my-desc">
<strong>${item.bridgeName}</strong>
<p>道路名称:${item.roadName || '--'}</p>
<p>桥梁类型:${item.bridgeType || '--'}</p>
<p>桥长:${item.totalLength || '--'}</p>
<p>桥宽:${item.totalWidth || '--'}</p>
<p>级别:${item.technicalConditionGrade || '--'}</p>
<p>管养单位:${item.maintenanceCompany || '--'}</p>
<p>荷载等级:${item.designLoad || '--'}</p>
</div>
`,
offset: new AMap.Pixel(0, -31) // 调整信息窗体的偏移量
});
// 存储marker和infoWindow
markersMap.value[item.id] = marker;
infoWindowsMap.value[item.id] = infoWindow;
// 点击标记时打开信息窗体
marker.on('click', () => {
infoWindow.open(map.value!, marker.getPosition());
});
marker.setMap(map.value!);
});
};
5.地图组件外部card添加一个搜索组件,可以模糊搜索筛选已拿到的marker点位,并且打开正确的信息窗体
const onSearch = (item) => {
console.log(map.value)
const marker = markersMap.value[item];
const data = mapData.value.find((e: any) => e.id === item);
// 关闭之前的信息窗
if (isSelectInfoMap.value) {
isSelectInfoMap.value.close();
}
isSelectInfoMap.value = infoWindowsMap.value[item];
// 打开信息窗并记录当前窗口
infoWindowsMap.value[item].open(map.value!, marker.getPosition());
};
···