UNPKG

vue-maplibre-gl

Version:
85 lines (69 loc) 2.42 kB
import { Position, type PositionProp, PositionValues } from '@/components/controls/position.enum'; import { usePositionWatcher } from '@/composable/usePositionWatcher'; import { isInitializedSymbol, mapSymbol } from '@/types'; import type { ControlPosition, IControl } from 'maplibre-gl'; import { createCommentVNode, defineComponent, h, inject, nextTick, onBeforeUnmount, type PropType, ref, type Ref, type SlotsType, Teleport, watch } from 'vue'; export class CustomControl implements IControl { public static readonly CONTROL_CLASS = 'maplibregl-ctrl'; public static readonly CONTROL_GROUP_CLASS = 'maplibregl-ctrl-group'; public readonly container: HTMLDivElement; constructor(private isAdded: Ref<boolean>, noClasses: boolean) { this.container = document.createElement('div'); this.setClasses(noClasses); } getDefaultPosition(): ControlPosition { return Position.TOP_LEFT; } onAdd(): HTMLElement { nextTick(() => this.isAdded.value = true); return this.container; } onRemove(): void { this.isAdded.value = false; this.container.remove(); } setClasses(noClasses: boolean) { if (noClasses) { this.container.classList.remove(CustomControl.CONTROL_CLASS); this.container.classList.remove(CustomControl.CONTROL_GROUP_CLASS); } else { this.container.classList.add(CustomControl.CONTROL_CLASS); this.container.classList.add(CustomControl.CONTROL_GROUP_CLASS); } } } export default /*#__PURE__*/ defineComponent({ name : 'MglCustomControl', props: { position : { type : String as PropType<PositionProp>, validator: (v: Position) => { return PositionValues.indexOf(v) !== -1; } }, noClasses: { type : Boolean as PropType<boolean>, default: false } }, slots: Object as SlotsType<{ default: {} }>, setup(props, { slots }) { const map = inject(mapSymbol)!, isInitialized = inject(isInitializedSymbol)!, isAdded = ref(false), control = new CustomControl(isAdded, props.noClasses!); usePositionWatcher(() => props.position, map, control); watch(() => props.noClasses, v => control.setClasses(v!)); onBeforeUnmount(() => isInitialized.value && map.value?.removeControl(control)); return () => { if (!isAdded.value) { return createCommentVNode('custom-component'); } return h( Teleport as any, { to: control.container }, slots.default?.({}) ); }; } });