feat(geomap): load markers at startup

This commit is contained in:
Elian Doran 2025-01-20 23:27:32 +02:00
parent a3f257f3c5
commit f76b454d5a
No known key found for this signature in database
2 changed files with 29 additions and 7 deletions

View File

@ -16,12 +16,15 @@ const TPL = `\
<div class="geo-map-container"></div> <div class="geo-map-container"></div>
</div>` </div>`
export type Leaflet = typeof import("leaflet");
export type InitCallback = ((L: Leaflet) => void);
export default class GeoMapWidget extends NoteContextAwareWidget { export default class GeoMapWidget extends NoteContextAwareWidget {
map?: Map; map?: Map;
private initCallback?: () => void; private initCallback?: InitCallback;
constructor(widgetMode: "type", initCallback?: () => void) { constructor(widgetMode: "type", initCallback?: InitCallback) {
super(); super();
this.initCallback = initCallback; this.initCallback = initCallback;
} }
@ -41,7 +44,7 @@ export default class GeoMapWidget extends NoteContextAwareWidget {
this.map = map; this.map = map;
if (this.initCallback) { if (this.initCallback) {
this.initCallback(); this.initCallback(L);
} }
L.tileLayer('https://tile.openstreetmap.org/{z}/{x}/{y}.png', { L.tileLayer('https://tile.openstreetmap.org/{z}/{x}/{y}.png', {

View File

@ -1,6 +1,6 @@
import type { LatLng, LeafletMouseEvent } from "leaflet"; import type { LatLng, LeafletMouseEvent } from "leaflet";
import type FNote from "../../entities/fnote.js"; import type FNote from "../../entities/fnote.js";
import GeoMapWidget from "../geo_map.js"; import GeoMapWidget, { type InitCallback, type Leaflet } from "../geo_map.js";
import TypeWidget from "./type_widget.js" import TypeWidget from "./type_widget.js"
import server from "../../services/server.js"; import server from "../../services/server.js";
import toastService from "../../services/toast.js"; import toastService from "../../services/toast.js";
@ -51,7 +51,7 @@ export default class GeoMapTypeWidget extends TypeWidget {
constructor() { constructor() {
super(); super();
this.geoMapWidget = new GeoMapWidget("type", () => this.#onMapInitialized()); this.geoMapWidget = new GeoMapWidget("type", (L: Leaflet) => this.#onMapInitialized(L));
this.child(this.geoMapWidget); this.child(this.geoMapWidget);
} }
@ -63,23 +63,42 @@ export default class GeoMapTypeWidget extends TypeWidget {
super.doRender(); super.doRender();
} }
async #onMapInitialized() { async #onMapInitialized(L: Leaflet) {
const map = this.geoMapWidget.map; const map = this.geoMapWidget.map;
if (!map) { if (!map) {
throw new Error("Unable to load map."); throw new Error("Unable to load map.");
} }
const blob = await this.note?.getBlob(); if (!this.note) {
return;
}
const blob = await this.note.getBlob();
let parsedContent: MapData = {}; let parsedContent: MapData = {};
if (blob) { if (blob) {
parsedContent = JSON.parse(blob.content); parsedContent = JSON.parse(blob.content);
} }
// Restore viewport position & zoom
const center = parsedContent.view?.center ?? [51.505, -0.09]; const center = parsedContent.view?.center ?? [51.505, -0.09];
const zoom = parsedContent.view?.zoom ?? 13; const zoom = parsedContent.view?.zoom ?? 13;
map.setView(center, zoom); map.setView(center, zoom);
// Restore markers.
const childNotes = await this.note.getChildNotes();
for (const childNote of childNotes) {
const latLng = childNote.getAttributeValue("label", LOCATION_ATTRIBUTE);
if (!latLng) {
continue;
}
const [ lat, lng ] = latLng.split(",", 2).map((el) => parseFloat(el));
L.marker(L.latLng(lat, lng))
.addTo(map)
.bindPopup(childNote.title);
}
const updateFn = () => this.spacedUpdate.scheduleUpdate(); const updateFn = () => this.spacedUpdate.scheduleUpdate();
map.on("moveend", updateFn); map.on("moveend", updateFn);
map.on("zoomend", updateFn); map.on("zoomend", updateFn);