diff --git a/src/leaflet/control/ChatControl.ts b/src/leaflet/control/ChatControl.ts index 10720bc..ff94791 100644 --- a/src/leaflet/control/ChatControl.ts +++ b/src/leaflet/control/ChatControl.ts @@ -21,6 +21,9 @@ import {watch} from "@vue/runtime-core"; import "@/assets/icons/chat.svg"; +/** + * Leaflet map control providing a chat button which opens the chatbox on click + */ export class ChatControl extends Control { declare options: ControlOptions diff --git a/src/leaflet/control/ClockControl.ts b/src/leaflet/control/ClockControl.ts index 8068fd5..4fc1f8a 100644 --- a/src/leaflet/control/ClockControl.ts +++ b/src/leaflet/control/ClockControl.ts @@ -37,6 +37,9 @@ export interface ClockControlOptions extends ControlOptions { showWeather: boolean; } +/** + * Leaflet map control providing a clock which can display the current in-game time of day and weather + */ export class ClockControl extends Control { declare options: ClockControlOptions; declare _container?: HTMLElement; diff --git a/src/leaflet/control/CoordinatesControl.ts b/src/leaflet/control/CoordinatesControl.ts index 0ce732b..a5300c1 100644 --- a/src/leaflet/control/CoordinatesControl.ts +++ b/src/leaflet/control/CoordinatesControl.ts @@ -30,6 +30,9 @@ export interface CoordinatesControlOptions extends ControlOptions { label: string; } +/** + * Leaflet map control which displays in-game block coordinates when hovering over or tapping the map + */ export class CoordinatesControl extends Control { declare options: CoordinatesControlOptions; declare _map ?: Map; diff --git a/src/leaflet/control/LinkControl.ts b/src/leaflet/control/LinkControl.ts index 16d84d0..d2434ec 100644 --- a/src/leaflet/control/LinkControl.ts +++ b/src/leaflet/control/LinkControl.ts @@ -24,6 +24,9 @@ import { toClipboard } from '@soerenmartius/vue3-clipboard'; import {notify} from "@kyvg/vue3-notification"; import {computed} from "@vue/runtime-core"; +/** + * Leaflet map control providing a button for copying a link for the current map view to the clipboard + */ export class LinkControl extends Control { declare options: ControlOptions diff --git a/src/leaflet/control/LiveAtlasLayerControl.ts b/src/leaflet/control/LiveAtlasLayerControl.ts index 2fdde01..b9880ae 100644 --- a/src/leaflet/control/LiveAtlasLayerControl.ts +++ b/src/leaflet/control/LiveAtlasLayerControl.ts @@ -30,6 +30,10 @@ import LayersOptions = Control.LayersOptions; const store = useStore(); +/** + * Extension of leaflet's standard {@link Control.Layers} + * Sorts layers by position, adds additional keyboard navigation, adjusts to viewport size and tracks expanded state in vuex + */ export class LiveAtlasLayerControl extends Control.Layers { declare _map ?: LeafletMap; declare _overlaysList?: HTMLElement; diff --git a/src/leaflet/control/LoadingControl.ts b/src/leaflet/control/LoadingControl.ts index 491453c..f91e81f 100644 --- a/src/leaflet/control/LoadingControl.ts +++ b/src/leaflet/control/LoadingControl.ts @@ -37,6 +37,9 @@ export interface LoadingControlOptions extends ControlOptions { delayIndicator?: number; } +/** + * Leaflet map control which displays a loading spinner when any tiles are loading + */ export class LoadingControl extends Control { declare options: LoadingControlOptions; diff --git a/src/leaflet/control/LoginControl.ts b/src/leaflet/control/LoginControl.ts index 2cd0d7f..fab0843 100644 --- a/src/leaflet/control/LoginControl.ts +++ b/src/leaflet/control/LoginControl.ts @@ -26,6 +26,9 @@ import {ActionTypes} from "@/store/action-types"; import {notify} from "@kyvg/vue3-notification"; import LiveAtlasLeafletMap from "@/leaflet/LiveAtlasLeafletMap"; +/** + * Leaflet map control providing a login/logout button which opens the login modal/logs out on click + */ export class LoginControl extends Control { declare _map: LiveAtlasLeafletMap; declare options: ControlOptions; diff --git a/src/leaflet/control/LogoControl.ts b/src/leaflet/control/LogoControl.ts index ed98619..0c0a05e 100644 --- a/src/leaflet/control/LogoControl.ts +++ b/src/leaflet/control/LogoControl.ts @@ -25,6 +25,10 @@ export interface LogoControlOptions extends ControlOptions { text: string; } +/** + * Leaflet map control which displays an arbitrary image or text with an optional link + * Intended for use for dynmap logo components + */ export class LogoControl extends Control { declare options: LogoControlOptions; diff --git a/src/util.ts b/src/util.ts index b8d5d0d..d12fed5 100644 --- a/src/util.ts +++ b/src/util.ts @@ -22,7 +22,7 @@ import { LiveAtlasDimension, LiveAtlasGlobalMessageConfig, LiveAtlasLocation, - LiveAtlasMessageConfig, + LiveAtlasMessageConfig, LiveAtlasParsedUrl, } from "@/index"; import {notify} from "@kyvg/vue3-notification"; import {globalMessages, serverMessages} from "../messages"; @@ -34,6 +34,11 @@ export const titleColoursRegex = /ยง[0-9a-f]/ig; export const netherWorldNameRegex = /[_\s]?nether([\s_]|$)/i; export const endWorldNameRegex = /(^|[_\s])end([\s_]|$)/i; +/** + * Calculates 24 hour time of day and the current day from the given server time + * @param {number} serverTime Server time in ticks + * @returns The equivalent 24 hour time, current day and whether it is currently day or night + */ export const getMinecraftTime = (serverTime: number) => { const day = serverTime >= 0 && serverTime < 13700; @@ -51,14 +56,26 @@ export const getMinecraftTime = (serverTime: number) => { }; } -export const parseUrl = (url: URL) => { +/** + * Parses the given {@link URL} into a {@link LiveAtlasParsedUrl}, if the URL matches any known URL formats + * @param {URL} url The URL to parse + * @returns {LiveAtlasParsedUrl | null} A LiveAtlasParsedUrl if the provided URL matched any known URL formats, + * otherwise null + */ +export const parseUrl = (url: URL): LiveAtlasParsedUrl | null => { const query = new URLSearchParams(url.search), hash = url.hash.replace('#', ''); return hash ? parseMapHash(hash) : parseMapSearchParams(query); } -export const parseMapHash = (hash: string) => { +/** + * Parses the given hash into a {@link LiveAtlasParsedUrl}, if the hash matches the LiveAtlas URL hash format + * @param {string} hash The hash to parse + * @returns {LiveAtlasParsedUrl | null} A LiveAtlasParsedUrl if the provided hash matched the LiveAtlas URL + * hash format, otherwise null + */ +export const parseMapHash = (hash: string): LiveAtlasParsedUrl | null => { const parts = hash.replace('#', '').split(';'); const world = parts[0] || undefined, @@ -81,7 +98,13 @@ export const parseMapHash = (hash: string) => { }); } -export const parseMapSearchParams = (query: URLSearchParams) => { +/** + * Parses the given {@link URLSearchParams} into a {@link LiveAtlasParsedUrl}, if it matches any known query string formats + * @param {URLSearchParams} query The URLSearchParams to parse + * @returns {LiveAtlasParsedUrl | null} A LiveAtlasParsedUrl if the provided hash matched the LiveAtlas URL + * hash format, otherwise null + */ +export const parseMapSearchParams = (query: URLSearchParams): LiveAtlasParsedUrl | null => { const world = query.get('worldname') /* Dynmap */ || query.get('world') /* Pl3xmap */ || undefined, map = query.has('worldname') ? query.get('mapname') || undefined : undefined, //Dynmap only location = [ @@ -104,6 +127,15 @@ export const parseMapSearchParams = (query: URLSearchParams) => { }); } +/** + * Validates the given {@link LiveAtlasParsedUrl} to ensure all required properties are present and have valid values + * @param {LiveAtlasParsedUrl} parsed The parsed URL to validate + * @return {LiveAtlasParsedUrl | null} The parsed URL, possibly modified to ensure validity, or null if it is invalid + * and cannot be fixed + * @see {@link parseMapSearchParams} + * @see {@link parseMapHash} + * @private + */ const validateParsedUrl = (parsed: any) => { if(typeof parsed.zoom !== 'undefined' && (isNaN(parsed.zoom) || parsed.zoom < 0 || !isFinite(parsed.zoom))) { parsed.zoom = undefined; @@ -116,6 +148,14 @@ const validateParsedUrl = (parsed: any) => { return parsed; } +/** + * Generates a LiveAtlas formatted URL hash representing the given {@link LiveAtlasMapDefinition}map, {@link Coordinate} + * location and zoom level + * @param {LiveAtlasMapDefinition} map The map + * @param {Coordinate} location The location + * @param {number} zoom The zoom level + * @return {string} The URL hash (including the #), or an empty string if a valid hash cannot be constructed + */ export const getUrlForLocation = (map: LiveAtlasMapDefinition, location: Coordinate, zoom: number): string => { const x = Math.round(location.x), y = Math.round(location.y), @@ -129,6 +169,10 @@ export const getUrlForLocation = (map: LiveAtlasMapDefinition, location: Coordin return `#${map.world.name};${map.name};${locationString};${zoom}`; } +/** + * Focuses the first html element which matches the given selector, if any + * @param {string} selector The selector string + */ export const focus = (selector: string) => { const element = document.querySelector(selector); @@ -139,31 +183,74 @@ export const focus = (selector: string) => { const decodeTextarea = document.createElement('textarea'); +/** + * Decodes HTML entities in the given string using a