You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
leaflet-components/src/components/leaflet-tile-layer-wms.ts

60 lines
2.1 KiB
TypeScript

import { CRS, TileLayer, type WMSOptions, type WMSParams } from 'leaflet';
import { bool, str, type PropDef } from '../core/props.ts';
import { tileLayerProps, urlProp } from '../core/shared-props.ts';
import {
WithProps,
type LeafletAddEventListener,
type LeafletRemoveEventListener,
} from '../core/with-props.ts';
import type { TileLayerEvents } from '../core/event-types.ts';
// WMS request parameters have no individual setters -- they're merged into the
// query string through setParams().
function param<T>(key: keyof WMSParams): (obj: TileLayer.WMS, value: T) => void {
return (obj, value) => {
obj.setParams({ [key]: value } as unknown as WMSParams);
};
}
// `crs` takes a CRS instance, not a primitive, so it's looked up by name from
// Leaflet's built-in set rather than decoded like a plain value. Constructor-
// only, like the rest of tileLayerProps -- Leaflet has no setter for it.
const NAMED_CRS = {
EPSG3857: CRS.EPSG3857,
EPSG4326: CRS.EPSG4326,
EPSG3395: CRS.EPSG3395,
Simple: CRS.Simple,
};
type CrsName = keyof typeof NAMED_CRS;
const crsProp: PropDef<CRS> = {
default: CRS.EPSG3857,
decode: (raw) => NAMED_CRS[raw as CrsName] ?? CRS.EPSG3857,
encode: (value) =>
value === CRS.EPSG3857
? null
: ((Object.keys(NAMED_CRS) as CrsName[]).find((name) => NAMED_CRS[name] === value) ?? null),
};
export class LeafletTileLayerWMS extends WithProps({
url: urlProp,
...tileLayerProps,
layers: str('', { set: param('layers') }),
styles: str('', { set: param('styles') }),
format: str('image/jpeg', { set: param('format') }),
transparent: bool(false, { set: param('transparent') }),
version: str('1.1.1', { set: param('version') }),
uppercase: bool(),
crs: crsProp,
}) {
declare readonly leafletObject?: TileLayer.WMS;
declare addEventListener: LeafletAddEventListener<TileLayerEvents>;
declare removeEventListener: LeafletRemoveEventListener<TileLayerEvents>;
createLeafletObject(options: WMSOptions): TileLayer.WMS {
return new TileLayer.WMS(this.url, options);
}
}
customElements.define('leaflet-tile-layer-wms', LeafletTileLayerWMS);