diff --git a/modules/rmaps/components/folk-map-viewer.ts b/modules/rmaps/components/folk-map-viewer.ts index 47dfc04..8112591 100644 --- a/modules/rmaps/components/folk-map-viewer.ts +++ b/modules/rmaps/components/folk-map-viewer.ts @@ -31,6 +31,19 @@ const DARK_STYLE = { layers: [{ id: "carto", type: "raster", source: "carto" }], }; +const LIGHT_STYLE = { + version: 8, + sources: { + carto: { + type: "raster", + tiles: ["https://basemaps.cartocdn.com/rastertiles/voyager/{z}/{x}/{y}@2x.png"], + tileSize: 256, + attribution: '© CARTO © OSM', + }, + }, + layers: [{ id: "carto", type: "raster", source: "carto" }], +}; + const PARTICIPANT_COLORS = ["#ef4444", "#f59e0b", "#22c55e", "#3b82f6", "#8b5cf6", "#ec4899", "#14b8a6", "#f97316"]; const EMOJIS = ["\u{1F9ED}", "\u{1F30D}", "\u{1F680}", "\u{1F308}", "\u{2B50}", "\u{1F525}", "\u{1F33F}", "\u{1F30A}", "\u{26A1}", "\u{1F48E}"]; @@ -74,6 +87,13 @@ class FolkMapViewer extends HTMLElement { private watchId: number | null = null; private pushManager: MapPushManager | null = null; private thumbnailTimer: ReturnType | null = null; + private _themeObserver: MutationObserver | null = null; + + private isDarkTheme(): boolean { + const theme = document.documentElement.getAttribute("data-theme"); + if (theme) return theme === "dark"; + return window.matchMedia("(prefers-color-scheme: dark)").matches; + } constructor() { super(); @@ -99,6 +119,10 @@ class FolkMapViewer extends HTMLElement { disconnectedCallback() { this.leaveRoom(); + if (this._themeObserver) { + this._themeObserver.disconnect(); + this._themeObserver = null; + } } // ─── User profile ──────────────────────────────────────────── @@ -139,6 +163,10 @@ class FolkMapViewer extends HTMLElement { this.view = "map"; this.room = "cosmolocal-providers"; this.syncStatus = "connected"; + // Re-render demo on theme change + this._themeObserver = new MutationObserver(() => this.renderDemo()); + this._themeObserver.observe(document.documentElement, { attributes: true, attributeFilter: ["data-theme"] }); + this.providers = [ { name: "Radiant Hall Press", city: "Pittsburgh", country: "USA", @@ -195,6 +223,18 @@ class FolkMapViewer extends HTMLElement { private renderDemo() { const W = 900; const H = 460; + const dark = this.isDarkTheme(); + + // Theme-aware SVG colors (can't use CSS vars in SVG fill/stroke) + const oceanStop1 = dark ? "#0f1b33" : "#d4e5f7"; + const oceanStop2 = dark ? "#060d1a" : "#e8f0f8"; + const pinStroke = dark ? "#0f172a" : "#f5f5f0"; + const continentFill = dark ? "#162236" : "#c8d8c0"; + const continentStroke = dark ? "#1e3050" : "#a0b898"; + const graticuleLine = dark ? "#1a2744" : "#c0d0e0"; + const graticuleStrong = dark ? "#1e3050" : "#a8b8c8"; + const cityColor = dark ? "#64748b" : "#6b7280"; + const coordColor = dark ? "#4a5568" : "#6b7280"; const px = (lng: number) => ((lng + 180) / 360) * W; const py = (lat: number) => ((90 - lat) / 180) * H; @@ -253,10 +293,10 @@ class FolkMapViewer extends HTMLElement { ${isSelected ? `` : ""} - + ${this.esc(p.name)} - ${this.esc(p.city)}, ${this.esc(p.country)} + ${this.esc(p.city)}, ${this.esc(p.country)} `; }).join(""); @@ -266,8 +306,8 @@ class FolkMapViewer extends HTMLElement {
- ${this.esc(p.name)} - ${this.esc(p.city)}, ${this.esc(p.country)} + ${this.esc(p.name)} + ${this.esc(p.city)}, ${this.esc(p.country)}
`).join(""); @@ -281,16 +321,16 @@ class FolkMapViewer extends HTMLElement {
-
${this.esc(sp.name)}
-
${this.esc(sp.city)}, ${this.esc(sp.country)}
+
${this.esc(sp.name)}
+
${this.esc(sp.city)}, ${this.esc(sp.country)}
-

${this.esc(sp.desc)}

+

${this.esc(sp.desc)}

${sp.specialties.map(s => `${this.esc(s)}`).join("")}
-
+
${sp.lat.toFixed(4)}\u00B0N, ${Math.abs(sp.lng).toFixed(4)}\u00B0${sp.lng >= 0 ? "E" : "W"}
@@ -301,15 +341,15 @@ class FolkMapViewer extends HTMLElement { this.shadow.innerHTML = `