前言
日常操作中,切换图层的时候我们需要更换图例,官网中是有legend(图例)的widget工具的,但是样式或者布局上满足不了设计需求,因此有时我们还是需要自定义legend的。
图层添加到地图map.add的时候就要为新添加的layer(图层)添加一个监听,监听layer的visible,visible变化就相应的控制图例的visible。
我们需要了解watchUtils的使用,才能很好的监听图层变化。
实现
/**
* @描述: 图层图例
* @作者: 花姐夫
* @创建时间: 2022-04-26 10:17:13
*/
<template>
<div id="legend">
<div v-for="legendSrc,layerId in visibleLayers" :key="layerId">
<img :src="legendSrc"/>
</div>
</div>
</template>
<script lang="ts">
import { Component, Emit, Vue } from 'vue-property-decorator';
@Component({ name: 'LayersControlWidget' })
export default class LayersControlWidget extends Vue {
activeView;
// 可见的图层
visibleLayers = {};
// 图层监听handle的集合
watchHandleList = {};
init(activeView: any) {
this.activeView = activeView;
if (activeView) {
// 监听每个图层被添加的时候
activeView.on('layerview-create', ({ layer }) => {
if (layer?.legend) {
// 将这个监听添加到集合里面,方便后面移除
this.watchHandleList[layer.id] = layer.watch('visible', (newVal, oldVal, propertyName, target) => {
const { id, legend } = target;
// 如果现在是要可见的就添加到可见图层数组里面
if (newVal) {
if (!Object.values(this.visibleLayers).includes(legend)) {
this.visibleLayers = { ...this.visibleLayers, [id]: legend };
}
} else { // 如果现在不是要可见的就从可见图层数组里面移除
delete this.visibleLayers[id];
this.visibleLayers = { ...this.visibleLayers };
}
console.log('可见图层:', this.visibleLayers);
});
const { id, legend, visible } = layer;
// 如果现在是要可见的就添加到可见图层数组里面
if (visible) {
if (!Object.values(this.visibleLayers).includes(legend)) {
this.visibleLayers = { ...this.visibleLayers, [id]: legend };
}
} else { // 如果现在不是要可见的就从可见图层数组里面移除
delete this.visibleLayers[id];
this.visibleLayers = { ...this.visibleLayers };
}
console.log('watchHandleList添加:', this.watchHandleList);
}
});
// 监听每个图层被删除的时候
activeView.on('layerview-destroy', ({ layer }) => {
// 移除该图层的监听
if (this.watchHandleList?.[layer.id]) {
this.watchHandleList[layer.id].remove();
delete this.watchHandleList[layer.id];
console.log('watchHandleList移除:', this.watchHandleList);
}
if (this.visibleLayers?.[layer?.id]) {
delete this.visibleLayers[layer.id];
this.visibleLayers = { ...this.visibleLayers };
}
});
}
}
// 加载完成
@Emit('success')
emitSuccess() {
return true;
}
}
</script>
<style scoped lang="less">
#legend {
position: absolute;
right: 40%;
bottom: 15px;
min-width: 600px;
text-align: right;
}
</style>
注意:图层移除的时候也要将该图层的watch移除