Refactor popup handling

- Merge label and popupContent properties for vector layers, as only one is ever used
- Move common vector methods to separate file and remove duplicates
- Rename isHTML properties to be clearer
This commit is contained in:
James Lyne 2021-07-28 17:49:38 +01:00
parent 2a216dd4e8
commit d04226e3ec
7 changed files with 72 additions and 92 deletions

5
src/index.d.ts vendored
View File

@ -196,7 +196,7 @@ interface LiveAtlasMarker {
dimensions: PointTuple;
icon: string;
label: string;
isHTML: boolean;
isLabelHTML: boolean;
location: Coordinate;
minZoom?: number;
maxZoom?: number;
@ -205,11 +205,10 @@ interface LiveAtlasMarker {
interface LiveAtlasPath {
style: PathOptions;
label: string;
isHTML: boolean;
minZoom?: number;
maxZoom?: number;
popupContent?: string;
isPopupHTML: boolean;
}
interface LiveAtlasArea extends LiveAtlasPath {

View File

@ -280,6 +280,7 @@ export default class DynmapMapProvider extends MapProvider {
private static buildMarker(marker: any): LiveAtlasMarker {
return {
label: marker.label || '',
isLabelHTML: marker.markup || false,
location: {
x: marker.x || 0,
y: marker.y || 0,
@ -287,7 +288,6 @@ export default class DynmapMapProvider extends MapProvider {
},
dimensions: marker.dim ? marker.dim.split('x') : [16, 16],
icon: marker.icon || "default",
isHTML: marker.markup || false,
minZoom: typeof marker.minzoom !== 'undefined' && marker.minzoom > -1 ? marker.minzoom : undefined,
maxZoom: typeof marker.maxzoom !== 'undefined' && marker.maxzoom > -1 ? marker.maxzoom : undefined,
popupContent: marker.desc || undefined,
@ -323,12 +323,12 @@ export default class DynmapMapProvider extends MapProvider {
fillOpacity: area.fillopacity || 0,
},
outline: !opacity,
label: area.label || '',
isHTML: area.markup || false,
points: getPoints(x, y, z, !opacity),
minZoom: typeof area.minzoom !== 'undefined' && area.minzoom > -1 ? area.minzoom : undefined,
maxZoom: typeof area.maxzoom !== 'undefined' && area.maxzoom > -1 ? area.maxzoom : undefined,
popupContent: area.desc || undefined,
isPopupHTML: area.desc ? true : area.markup || false,
popupContent: area.desc || area.label || undefined,
});
}
@ -353,12 +353,12 @@ export default class DynmapMapProvider extends MapProvider {
opacity: line.opacity || 1,
weight: line.weight || 1,
},
label: line.label || '',
isHTML: line.markup || false,
points: getLinePoints(line.x || [0, 0], line.y || [0, 0], line.z || [0, 0]),
minZoom: typeof line.minzoom !== 'undefined' && line.minzoom > -1 ? line.minzoom : undefined,
maxZoom: typeof line.maxzoom !== 'undefined' && line.maxzoom > -1 ? line.maxzoom : undefined,
popupContent: line.desc || undefined,
isPopupHTML: line.desc ? true : line.markup || false,
popupContent: line.desc || line.label || undefined,
});
}
@ -391,12 +391,11 @@ export default class DynmapMapProvider extends MapProvider {
opacity: circle.opacity || 1,
weight: circle.weight || 1,
},
label: circle.label || '',
isHTML: circle.markup || false,
minZoom: typeof circle.minzoom !== 'undefined' && circle.minzoom > -1 ? circle.minzoom : undefined,
maxZoom: typeof circle.maxzoom !== 'undefined' && circle.maxzoom > -1 ? circle.maxzoom : undefined,
popupContent: circle.desc || undefined,
isPopupHTML: circle.desc ? true : circle.markup || false,
popupContent: circle.desc || circle.label || undefined,
});
}

View File

@ -21,14 +21,15 @@ import {LatLngExpression} from "leaflet";
import LiveAtlasPolyline from "@/leaflet/vector/LiveAtlasPolyline";
import LiveAtlasPolygon from "@/leaflet/vector/LiveAtlasPolygon";
import {Coordinate, LiveAtlasArea} from "@/index";
import {arePointsEqual, createPopup, isStyleEqual} from "@/util/paths";
export const createArea = (options: LiveAtlasArea, converter: Function): LiveAtlasPolyline | LiveAtlasPolygon => {
const outline = !options.style.fillOpacity || (options.style.fillOpacity <= 0),
points = options.points.map(projectPointsMapCallback, converter) as LatLngExpression[] | LatLngExpression[][],
area = outline ? new LiveAtlasPolyline(points, options) : new LiveAtlasPolygon(points, options);
if (options.label) {
area.bindPopup(() => createPopup(options));
if (options.popupContent) {
area.bindPopup(() => createPopup(options, 'AreaPopup'));
}
return area;
@ -57,7 +58,7 @@ export const updateArea = (area: LiveAtlasPolyline | LiveAtlasPolygon | undefine
area.closePopup();
area.unbindPopup();
area.bindPopup(() => createPopup(options));
area.bindPopup(() => createPopup(options, 'AreaPopup'));
if(dirty) {
area.redraw();
@ -66,35 +67,6 @@ export const updateArea = (area: LiveAtlasPolyline | LiveAtlasPolygon | undefine
return area;
};
const arePointsEqual = (oldPoints: any, newPoints: any) => {
return JSON.stringify(oldPoints) === JSON.stringify(newPoints);
}
const isStyleEqual = (oldStyle: any, newStyle: any) => {
return oldStyle && newStyle
&& (oldStyle.color === newStyle.color)
&& (oldStyle.weight === newStyle.weight)
&& (oldStyle.opacity === newStyle.opacity)
&& (oldStyle.fillColor === newStyle.fillColor)
&& (oldStyle.fillOpacity === newStyle.fillOpacity)
}
export const createPopup = (options: LiveAtlasArea): HTMLElement => {
const popup = document.createElement('span');
if (options.popupContent) {
popup.classList.add('AreaPopup');
popup.insertAdjacentHTML('afterbegin', options.popupContent);
} else if (options.isHTML) {
popup.classList.add('AreaPopup');
popup.insertAdjacentHTML('afterbegin', options.label);
} else {
popup.textContent = options.label;
}
return popup;
};
const projectPointsMapCallback = function(this: Function, point: Coordinate | Coordinate[] | Coordinate[][]): LatLngExpression | LatLngExpression[] {
if(Array.isArray(point)) {
return point.map(projectPointsMapCallback, this) as LatLngExpression[];

View File

@ -21,14 +21,15 @@ import {LatLngExpression} from "leaflet";
import LiveAtlasPolyline from "@/leaflet/vector/LiveAtlasPolyline";
import LiveAtlasPolygon from "@/leaflet/vector/LiveAtlasPolygon";
import {LiveAtlasCircle} from "@/index";
import {createPopup} from "@/util/paths";
export const createCircle = (options: LiveAtlasCircle, converter: Function): LiveAtlasPolyline | LiveAtlasPolygon => {
const outline = !options.style.fillOpacity || (options.style.fillOpacity <= 0),
points = getCirclePoints(options, converter, outline),
circle = outline ? new LiveAtlasPolyline(points, options) : new LiveAtlasPolygon(points, options);
if(options.label) {
circle.bindPopup(() => createPopup(options));
if(options.popupContent) {
circle.bindPopup(() => createPopup(options, 'CirclePopup'));
}
return circle;
@ -43,7 +44,7 @@ export const updateCircle = (circle: LiveAtlasPolyline | LiveAtlasPolygon | unde
circle.closePopup();
circle.unbindPopup();
circle.bindPopup(() => createPopup(options));
circle.bindPopup(() => createPopup(options, 'CirclePopup'));
circle.setStyle(options.style);
circle.setLatLngs(getCirclePoints(options, converter, outline));
circle.redraw();
@ -51,22 +52,6 @@ export const updateCircle = (circle: LiveAtlasPolyline | LiveAtlasPolygon | unde
return circle;
}
export const createPopup = (options: LiveAtlasCircle) => {
const popup = document.createElement('span');
if (options.popupContent) {
popup.classList.add('CirclePopup');
popup.insertAdjacentHTML('afterbegin', options.popupContent);
} else if (options.isHTML) {
popup.classList.add('CirclePopup');
popup.insertAdjacentHTML('afterbegin', options.label);
} else {
popup.textContent = options.label;
}
return popup;
}
export const getCirclePoints = (options: LiveAtlasCircle, converter: Function, outline: boolean): LatLngExpression[] => {
const points = [];

View File

@ -20,13 +20,14 @@
import LiveAtlasPolyline from "@/leaflet/vector/LiveAtlasPolyline";
import {Coordinate, LiveAtlasLine} from "@/index";
import {LatLngExpression} from "leaflet";
import {createPopup} from "@/util/paths";
export const createLine = (options: LiveAtlasLine, converter: Function): LiveAtlasPolyline => {
const points = options.points.map(projectPointsMapCallback, converter),
line = new LiveAtlasPolyline(points, options);
if(options.label) {
line.bindPopup(() => createPopup(options));
if(options.popupContent) {
line.bindPopup(() => createPopup(options, 'LinePopup'));
}
return line;
@ -39,7 +40,7 @@ export const updateLine = (line: LiveAtlasPolyline | undefined, options: LiveAtl
line.closePopup();
line.unbindPopup();
line.bindPopup(() => createPopup(options));
line.bindPopup(() => createPopup(options, 'LinePopup'));
line.setStyle(options.style);
line.setLatLngs(options.points.map(projectPointsMapCallback, converter));
line.redraw();
@ -56,22 +57,6 @@ const projectPointsMapCallback = function(point: Coordinate): LatLngExpression {
}
};
export const createPopup = (options: LiveAtlasLine) => {
const popup = document.createElement('span');
if (options.popupContent) {
popup.classList.add('LinePopup');
popup.insertAdjacentHTML('afterbegin', options.popupContent);
} else if (options.isHTML) {
popup.classList.add('LinePopup');
popup.insertAdjacentHTML('afterbegin', options.label);
} else {
popup.textContent = options.label;
}
return popup;
}
export const getLinePoints = (x: number[], y: number[], z: number[]): Coordinate[] => {
const points = [];

View File

@ -28,7 +28,7 @@ export const createMarker = (options: LiveAtlasMarker, converter: Function): Mar
icon: options.icon,
label: options.label,
iconSize: options.dimensions,
isHtml: options.isHTML,
isHtml: options.isLabelHTML,
}),
maxZoom: options.maxZoom,
minZoom: options.minZoom,
@ -65,7 +65,7 @@ export const updateMarker = (marker: Marker | undefined, options: LiveAtlasMarke
icon: options.icon,
label: options.label,
iconSize: options.dimensions,
isHtml: options.isHTML,
isHtml: options.isLabelHTML,
});
}
}
@ -80,17 +80,12 @@ export const updateMarker = (marker: Marker | undefined, options: LiveAtlasMarke
return marker;
};
export const createPopup = (options: LiveAtlasMarker) => {
const createPopup = (options: LiveAtlasMarker) => {
const popup = document.createElement('span');
if (options.popupContent) {
popup.classList.add('MarkerPopup');
popup.insertAdjacentHTML('afterbegin', options.popupContent);
} else if (options.isHTML) {
popup.classList.add('MarkerPopup');
popup.insertAdjacentHTML('afterbegin', options.label);
} else {
popup.textContent = options.label;
}
return popup;

45
src/util/paths.ts Normal file
View File

@ -0,0 +1,45 @@
/*
* Copyright 2021 James Lyne
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import {LatLngExpression, PathOptions} from "leaflet";
import {LiveAtlasPath} from "@/index";
export const arePointsEqual = (oldPoints: LatLngExpression | LatLngExpression[] | LatLngExpression[][] | LatLngExpression[][][],
newPoints: LatLngExpression | LatLngExpression[] | LatLngExpression[][] | LatLngExpression[][][]) => {
return JSON.stringify(oldPoints) === JSON.stringify(newPoints);
}
export const isStyleEqual = (oldStyle: PathOptions, newStyle: PathOptions) => {
return oldStyle && newStyle
&& (oldStyle.color === newStyle.color)
&& (oldStyle.weight === newStyle.weight)
&& (oldStyle.opacity === newStyle.opacity)
&& (oldStyle.fillColor === newStyle.fillColor)
&& (oldStyle.fillOpacity === newStyle.fillOpacity)
}
export const createPopup = (options: LiveAtlasPath, className: string): HTMLElement => {
const popup = document.createElement('span');
if(options.isPopupHTML) {
popup.classList.add(className);
popup.insertAdjacentHTML('afterbegin', options.popupContent as string);
} else {
popup.textContent = options.popupContent as string;
}
return popup;
};