Take main
Some checks are pending
Deploy to GitHub Pages / build (push) Waiting to run
Deploy to GitHub Pages / deploy (push) Blocked by required conditions

This commit is contained in:
doxa-maps-88655c70 2026-09-25 08:27:09 +00:00
commit afe04bc835
98 changed files with 1199 additions and 668 deletions

View file

@ -85,3 +85,41 @@ export async function serveThisTree(dir) {
}
return null
}
/**
* The same check, as a one-liner a gate can put right after it resolves its base URL.
*
* ★ EXIT 75, NOT 1. A gate pointed at another worktree's server has NOT MEASURED this build — it
* has not found a defect in it. flock uses 75 for the same idea (EX_TEMPFAIL) and the wave runner
* already reports 75 as ⊘ rather than ✗, so one code means "not measured" everywhere in this repo.
* Exiting 1 here would turn a mis-pointed probe into a red product gate, which is the failure this
* whole family of checks exists to prevent.
*
* @param {string} base origin (or any URL on it) that should serve public/
* @param {string} repo absolute path to the repo root
* @param {string} label the gate's own name, for the message
*/
export async function requireThisTree(base, repo, label) {
let origin = String(base || '')
// A gate that loads file:// URLs is reading THIS checkout by construction — there is no server to
// be wrong about, so the guard stays silent rather than inventing a precondition.
if (!/^https?:/i.test(origin)) return { ok: true, why: 'not an http target' }
// ★ ONLY LOCAL SERVERS. The defect this guards is several worktrees sharing one machine's ports.
// A gate aimed at a DEPLOYED site (verify-map-paint defaults to the live host) is asking a
// different question on purpose — "does production match what we built" is a deploy check, not a
// mis-pointed probe — and enforcing local identity there would make it permanently unmeasured.
// MEASURED while rolling this out: that gate reported NOT MEASURED against the live site, which
// is the guard being wrong rather than the gate.
try {
const host = new URL(origin).hostname
if (!/^(localhost|127\.|0\.0\.0\.0$|\[?::1\]?$)/.test(host)) return { ok: true, why: 'remote target, not a worktree port' }
} catch { /* unparseable — fall through to the content check */ }
try { origin = new URL(origin).origin } catch { /* already an origin, or unusable — pass through */ }
const verdict = await servesThisTree(origin, repo)
if (/DIFFERENT build/.test(verdict.why)) {
console.log(`${label}: NOT MEASURED — ${verdict.why}`)
console.log(' Point this gate at a server for THIS checkout (bun run serve) and re-run.')
process.exit(75)
}
return verdict
}

View file

@ -27,8 +27,19 @@
//
// Usage: node internal/check-aria-labels-localized.mjs <leafUrl> [locales]
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const URL_ = process.argv[2] || process.env.ARIA_URL
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(URL_, ROOT, 'ARIA-LABELS-LOCALIZED')
if (!URL_) {
console.log('ARIA-LABELS-LOCALIZED: SKIP — no leaf url given.')
console.log(' Pass one, or set ARIA_URL. Serve the TREE ROOT (public/) and point at a leaf,')

View file

@ -13,8 +13,19 @@
// Usage: node internal/check-card-deck.mjs [lang] [stock]
// PACKET_ORIGIN (default http://127.0.0.1:4898) · PACKET_API · PACKET_ISO3
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const ORIGIN = process.env.PACKET_ORIGIN || 'http://127.0.0.1:4898'
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(ORIGIN, ROOT, 'CARD-DECK')
const API = process.env.PACKET_API || 'https://pray.doxa.life'
const ISO3 = process.env.PACKET_ISO3 || 'LAO'
const LANG = process.argv[2] || 'en'

View file

@ -17,8 +17,17 @@ import { chromium } from 'playwright'
import { readFileSync, existsSync } from 'node:fs'
import { resolve, dirname, join } from 'node:path'
import { fileURLToPath } from 'node:url'
import { requireThisTree } from './_serves-this-tree.mjs'
const URL_ = process.argv[2]
const ROOT = resolve(dirname(fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(URL_, ROOT, 'DECK-CLICK')
if (!URL_) { console.error('usage: check-deck-click.mjs <wallUrl> [stock] [expectedPage]'); process.exit(2) }
const STOCK = process.argv[3] || ''
const EXPECT_PAGE = process.argv[4] || (STOCK === 'pokerLandscape' ? '3.5in 2.5in' : '2.5in 3.5in')

View file

@ -34,8 +34,19 @@
* exactly where the old probe passed, which is the property that makes it worth having.
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const BASE = process.env.BASE || 'http://127.0.0.1:4173/doxa-maps'
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(BASE, ROOT, 'FIXED-ANCHORING')
const TK = process.env.MAPBOX_TOKEN ? `?tk=${process.env.MAPBOX_TOKEN}` : ''
const DEEP = `(sel)=>{const out=[],seen=new Set();const w=(r)=>{if(!r||seen.has(r))return;seen.add(r);try{out.push(...r.querySelectorAll(sel))}catch(e){};for(const el of r.querySelectorAll('*'))if(el.shadowRoot)w(el.shadowRoot)};w(document);return out}`

View file

@ -29,11 +29,20 @@ import { chromium } from 'playwright'
import { serveReaped } from './_serve-reaped.mjs'
import { resolve, dirname } from 'node:path'
import { fileURLToPath } from 'node:url'
import { requireThisTree } from './_serves-this-tree.mjs'
const HERE = dirname(fileURLToPath(import.meta.url))
const PUBLIC = resolve(HERE, '../public')
const PORT = Number(process.env.PORT || 5399)
const BASE = process.env.BASE_URL || `http://127.0.0.1:${PORT}`
const ROOT = resolve(dirname(fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(BASE, ROOT, 'GOSPEL-COMPOSED-FILTERS')
const PATHNAME = '/doxa-maps/gospel-resources/gospel-dashboard/index.html'
let srv = null

View file

@ -32,11 +32,21 @@ import { chromium } from 'playwright'
import { readFileSync, existsSync } from 'node:fs'
import { join, dirname } from 'node:path'
import { fileURLToPath } from 'node:url'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
const REPO = join(dirname(fileURLToPath(import.meta.url)), '..')
const LOCALES = join(REPO, 'library/i18n/locales')
const URL_ = process.argv[2] || process.env.LEGEND_URL
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(URL_, ROOT, 'LEGEND-INFO-LOCALIZED')
if (!URL_) {
console.log('LEGEND-INFO-LOCALIZED: SKIP — no leaf url given.')
console.log(' Pass one, or set LEGEND_URL. Serve the TREE ROOT (public/doxa-maps) and point')

View file

@ -24,9 +24,20 @@
* actually removed before release, the race was not staged and it exits 2, not 0.
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const i = process.argv.indexOf('--url')
const BASE = (i > -1 ? process.argv[i + 1] : '').replace(/#.*$/, '')
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(BASE, ROOT, 'MAP-UNMOUNT-MID-INIT')
if (!BASE) { console.error('check-map-unmount-mid-init: pass --url <studio page>'); process.exit(2) }
// Production map plugins that go through useMapInstance, opened by their studio key.

View file

@ -13,8 +13,19 @@
//
// Usage: node internal/check-mfe-two-tab.mjs <url> [expectedTabCount]
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const URL = process.argv[2]
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(URL, ROOT, 'MFE-TWO-TAB')
if (!URL) { console.error('usage: check-mfe-two-tab.mjs <url> [tabs]'); process.exit(2) }
const WANT_TABS = Number(process.argv[3] || 2)

View file

@ -37,10 +37,18 @@ import { readFileSync, existsSync } from 'node:fs'
import { resolve, dirname, join } from 'node:path'
import { fileURLToPath } from 'node:url'
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
const ROOT = resolve(dirname(fileURLToPath(import.meta.url)), '..')
const MANIFEST = join(ROOT, 'public', 'doxa-maps', 'manifest.json')
const BASE = process.env.BASE || 'http://127.0.0.1:4173/doxa-maps/'
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees of this repo run on one machine and
// a default port belongs to whichever server started first — measured 2026-09-24, :4173 was another
// worktree's, and browser gates reported confidently on a build nobody here had touched. Exit 75
// (EX_TEMPFAIL) rather than 1: pointing at the wrong tree is a precondition, not a product defect,
// and the wave runner already reports 75 as ⊘ instead of ✗.
await requireThisTree(BASE, ROOT, 'NAV-REACHABLE-MOBILE')
// 414x896 = iPhone-class portrait, comfortably inside the layout's 760px breakpoint.
const VIEWPORT = { width: Number(process.env.W || 414), height: Number(process.env.H || 896) }

View file

@ -25,8 +25,19 @@
//
// Usage: node internal/check-poster-degrades-honestly.mjs <wallUrl> [zoneId]
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const WALL = process.argv[2] || process.env.POSTER_WALL_URL
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(WALL, ROOT, 'POSTER-DEGRADES-HONESTLY')
if (!WALL) {
console.log('POSTER-DEGRADES: SKIP — no wall url given.')
console.log(' Serve the TREE ROOT (public/<name>), not public/, or assetsBase resolves')

View file

@ -24,12 +24,23 @@
//
// Usage: node internal/check-poster-print-fallback.mjs <wallUrl> [zoneId]
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
// SKIP, never fail, when the preconditions are absent. This gate needs a SERVED tree
// that carries posters/<id>.html (posterSources:true or bundlePosters:true). The
// default tree ships neither, and a clean checkout has no server at all — failing the
// build on that would only teach people to disable the gate. It says what is missing.
const WALL = process.argv[2] || process.env.POSTER_WALL_URL
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(WALL, ROOT, 'POSTER-PRINT-FALLBACK')
if (!WALL) {
console.log('POSTER-PRINT-FALLBACK: SKIP — no wall url given.')
console.log(' Pass one, or set POSTER_WALL_URL. Needs a tree built with posterSources:true')

View file

@ -17,8 +17,19 @@
// Usage: node internal/check-poster-raster.mjs [zoneId]
// PACKET_ORIGIN (default http://127.0.0.1:4898)
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const ORIGIN = process.env.PACKET_ORIGIN || 'http://127.0.0.1:4898'
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(ORIGIN, ROOT, 'POSTER-RASTER')
const ZONE = process.argv[2] || 'laos'
const HTML = `${ORIGIN}/library/scripts/posters/out/posters/${ZONE}.html`

View file

@ -14,8 +14,19 @@
// Usage: node internal/check-print-geometry.mjs
// PACKET_ORIGIN (default http://127.0.0.1:4898) — a static server over the repo root
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const ORIGIN = process.env.PACKET_ORIGIN || 'http://127.0.0.1:4898'
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(ORIGIN, ROOT, 'PRINT-GEOMETRY')
const API = process.env.PACKET_API || 'https://pray.doxa.life'
const ISO3 = process.env.PACKET_ISO3 || 'LAO'

View file

@ -72,6 +72,11 @@ const LINKED_KNOWN = {
'upg-100: "Show on map" does not select the zone on the map': 'upg100-plugin (upg-100-mfe.vue:143 re-dispatch doxa:select-zone)',
}
const MAPBOX_KNOWN = {
// pplr-data-maps (new Experimental bundle, exp-shepherd) loads the Mapbox GEOCODER script even when
// the host asked for maplibre: the only api.mapbox.com request in the whole keyless gallery, both
// modes, measured 2026-09-25 while that tab was open. Routed via dx-shepherd; delete this entry in
// the owner's fix commit so the gate enforces zero again.
'https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-geocoder/v5.0.0/mapbox-gl-geocoder.min.js': 'exp-shepherd (pplr-data-maps loads the Mapbox geocoder under maplibre)',
// EMPTY ON PURPOSE. The one entry here — my-upg-100-list/upg-100-list.vue:1464 pinning
// mapbox-gl.css v3.3.0 regardless of engine — was fixed and the exemption deleted in the SAME
// COMMIT as the fix, so main never had a window where the gate red-flagged its own known bug and

View file

@ -44,8 +44,19 @@
* Exit: 0 all pass · 1 any fail · 2 dev server unreachable (a precondition, not a defect).
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const BASE = (process.env.DEV_URL || 'http://localhost:5173').replace(/\/+$/, '')
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees of this repo run on one machine and
// a default port belongs to whichever server started first — measured 2026-09-24, :4173 was another
// worktree's, and browser gates reported confidently on a build nobody here had touched. Exit 75
// (EX_TEMPFAIL) rather than 1: pointing at the wrong tree is a precondition, not a product defect,
// and the wave runner already reports 75 as ⊘ instead of ✗.
await requireThisTree(BASE, ROOT, 'SCRIM-COVERS-VIEWPORT')
const SELF_TEST = process.argv.includes('--self-test')
const VW = 1280, VH = 900

View file

@ -83,6 +83,21 @@ const MARKERS = [
landed: 'studio, 2026-09-25',
why: 'a map whose pane unmounts mid-initialise no longer throws "reading getRootNode" (check-map-unmount-mid-init)',
},
{
// The RTL text plugin now installs for MapLibre too, from useMapInstance at the moment an engine
// exists (a bundle entry runs before a lazily-injected MapLibre). The built marker is the keyless
// jsDelivr URL, a string literal that survives minification. staleRe is initializeMap's own error
// message: a bundle that compiles initializeMap WITHOUT the URL is stale; a bundle that compiles
// neither is not affected (it never boots a map).
id: 'rtl-text-maplibre',
component: 'library/composables/useMapInstance.js',
sourceRe: /installRtlTextPlugin\(gl\)/,
builtRe: /cdn\.jsdelivr\.net\/npm\/@mapbox\/mapbox-gl-rtl-text/,
staleRe: /GL JS script to your page/g,
marker: 'installRtlTextPlugin(gl) (MapLibre RTL shaping)',
landed: 'rega, 2026-09-25',
why: 'Arabic, Hebrew and Persian map labels are shaped on MapLibre (keyless) maps, not drawn as disconnected glyphs',
},
]
// A marker is a literal (`marker`, matched with includes) unless the entry supplies regexes.
const inSource = (m, src) => (m.sourceRe ? m.sourceRe.test(src) : src.includes(m.marker))

View file

@ -24,9 +24,20 @@
* another worktree's tree — so this one refuses to guess.
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const i = process.argv.indexOf('--url')
const URL_ = i > -1 ? process.argv[i + 1] : ''
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(URL_, ROOT, 'STUDIO-EVERY-PLUGIN')
if (!URL_) {
console.error('check-studio-every-plugin: pass --url <studio page>, e.g. --url http://localhost:5299/')
process.exit(2)

View file

@ -33,9 +33,20 @@
* Exits non-zero if any level fails, so it can gate a release.
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
const GL=['--use-gl=swiftshader','--enable-unsafe-swiftshader','--ignore-gpu-blocklist','--enable-webgl','--no-sandbox']
const B=(process.env.BASE || 'https://nuxtbase.app/plugin-assets/doxa-maps/').replace(/\/?$/,'/')
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(B, ROOT, '5-CAPABILITIES')
// capability = 5 - PROFILE_TIER (discover.mjs). One representative per level.
const REPS=[
// ★ CORRECTED 2026-09-20 by the manifest reconciliation added below, on its FIRST RUN.

View file

@ -30,6 +30,9 @@
* Exits non-zero if any leaf fails, so it can become a gate.
*/
import { chromium } from 'playwright'
import { requireThisTree } from './_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
// The SwiftShader launch. Without these a headless Chromium here has NO GL context at all.
const GL_ARGS = [
@ -41,6 +44,14 @@ const GL_ARGS = [
]
const BASE = process.env.BASE || 'https://nuxtbase.app/plugin-assets/doxa-maps'
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(BASE, ROOT, 'MAP-PAINT')
// ★ WIDENED 2026-09-22 — 4 of 12 map profiles were covered, now 11.
// The four originals were the ones that happened to be under investigation when this file was
// written. Measuring the manifest showed 12 profiles carry isMap=true, so EIGHT painted leaves

View file

@ -39,7 +39,7 @@ import { tStatic } from '@map/i18n/index.js'
// reachable from mounts that install no i18n plugin, and an unguarded useI18n() throws and takes
// the subtree with it (the defect that blanked people-groups-grid, fixed in 6603dc17). English
// stays as the last argument, so a missing key degrades to today's text rather than to a key name.
const L = (key, en) => tStatic('controls.' + key) || en
const L = (key, en) => tStatic('controls.' + key) || tStatic('dashboard.' + key) || en
const mapStore = inject('mapStore')
const uiStore = inject('uiStore')
@ -94,7 +94,7 @@ useShadowStyles(`
<template>
<div class="rm-side-backdrop" :class="{ open: isOpen }" @click="emit('close')" />
<aside class="rm-side-drawer" :class="{ open: isOpen }" role="dialog" aria-label="Research map controls">
<aside class="rm-side-drawer" :class="{ open: isOpen }" role="dialog" :aria-label="L('map_controls', 'Research map controls')">
<header class="rm-side-header">
<h3 class="rm-side-title">{{ L('research_controls', 'Research controls') }}</h3>
<button class="rm-side-close" aria-label="Close" @click="emit('close')">×</button>

View file

@ -76,6 +76,7 @@ const OPENFREEMAP_DARK_STYLE = 'https://tiles.openfreemap.org/styles/fiord'
// 'midnight-glow' / … resolves per engine here; raw URLs pass through.
import { resolveNamedStyle, applyStylePaint } from '../styles/registry.js'
import { resolveMapProvider } from './useMapProvider.js'
import { installRtlTextPlugin } from '../maps/rtl-text.js'
/**
* The live engine global for a provider, or undefined if not yet loaded.
@ -387,6 +388,11 @@ export function useMapInstance({
return
}
// RTL labels (Arabic, Hebrew, Persian) need the RTL text plugin on THIS engine. Installed here,
// at the one moment every map is guaranteed to have its engine, because a bundle entry runs
// before a lazily-injected MapLibre exists. Idempotent and lazy (see maps/rtl-text.js).
installRtlTextPlugin(gl)
// ─── API Key validation (Mapbox only — MapLibre + OpenFreeMap need no token) ──
if (!isMaplibre) {
// Reusable fallback: a host that can't thread a per-instance token (e.g. a BAKED composite that

View file

@ -31,5 +31,22 @@
"filters": "عوامل التصفية",
"gospel_resources": "موارد الإنجيل",
"map": "الخريطة",
"search_placeholder": "ابحث عن الشعوب والأماكن واللغات والأديان…"
"search_placeholder": "ابحث عن الشعوب والأماكن واللغات والأديان…",
"any": "الكل",
"active_count": "{n} نشط",
"prayer_status": "حالة الصلاة",
"map_controls": "أدوات التحكم بالخريطة",
"close": "إغلاق",
"clear": "مسح",
"dashboard_title": "لوحة البحث الشاملة",
"align_dashboard": "محاذاة اللوحة",
"align_dashboard_tip": "إعادة تخطيط اللوحة إلى المحاذاة الافتراضية",
"selected": "المحدد",
"world": "العالم",
"vertical_legend": "مفتاح عمودي",
"groups_in_scope": "مجموعة ضمن النطاق",
"filter_by": "تصفية حسب",
"remove_filter": "إزالة التصفية",
"groups": "مجموعة",
"expand": "توسيع"
}

View file

@ -31,5 +31,22 @@
"filters": "Filter",
"gospel_resources": "Evangeliumsressourcen",
"map": "Karte",
"search_placeholder": "Volksgruppen, Orte, Sprachen, Religionen suchen…"
"search_placeholder": "Volksgruppen, Orte, Sprachen, Religionen suchen…",
"any": "Alle",
"active_count": "{n} aktiv",
"prayer_status": "Gebetsstatus",
"map_controls": "Kartensteuerung",
"close": "Schließen",
"clear": "Zurücksetzen",
"dashboard_title": "Big-Picture-Forschungsdashboard",
"align_dashboard": "Layout ausrichten",
"align_dashboard_tip": "Das Dashboard-Layout auf die Standardausrichtung zurücksetzen",
"selected": "Ausgewählt",
"world": "Welt",
"vertical_legend": "Vertikale Legende",
"groups_in_scope": "Volksgruppen im Bereich",
"filter_by": "Filtern nach",
"remove_filter": "Filter entfernen",
"groups": "Volksgruppen",
"expand": "Aufklappen"
}

View file

@ -31,5 +31,22 @@
"filters": "Filters",
"gospel_resources": "Gospel Resources",
"map": "Map",
"search_placeholder": "Search people groups, place, language, religion…"
"search_placeholder": "Search people groups, place, language, religion…",
"any": "Any",
"active_count": "{n} active",
"prayer_status": "Prayer Status",
"map_controls": "Research map controls",
"close": "Close",
"clear": "Clear",
"dashboard_title": "Big Picture Research Dashboard",
"align_dashboard": "Align Dashboard",
"align_dashboard_tip": "Reset the dashboard layout to its default alignment",
"selected": "Selected",
"world": "World",
"vertical_legend": "Vertical Legend",
"groups_in_scope": "groups in scope",
"filter_by": "Filter by",
"remove_filter": "Remove filter",
"groups": "groups",
"expand": "Expand"
}

View file

@ -31,5 +31,22 @@
"filters": "Filtros",
"gospel_resources": "Recursos del Evangelio",
"map": "Mapa",
"search_placeholder": "Buscar pueblos, lugares, idiomas, religiones…"
"search_placeholder": "Buscar pueblos, lugares, idiomas, religiones…",
"any": "Cualquiera",
"active_count": "{n} activos",
"prayer_status": "Estado de oración",
"map_controls": "Controles del mapa",
"close": "Cerrar",
"clear": "Borrar",
"dashboard_title": "Panel de investigación general",
"align_dashboard": "Alinear panel",
"align_dashboard_tip": "Restablecer la disposición del panel a su alineación predeterminada",
"selected": "Seleccionado",
"world": "Mundo",
"vertical_legend": "Leyenda vertical",
"groups_in_scope": "pueblos en el ámbito",
"filter_by": "Filtrar por",
"remove_filter": "Quitar filtro",
"groups": "pueblos",
"expand": "Expandir"
}

View file

@ -31,5 +31,22 @@
"filters": "Filtres",
"gospel_resources": "Ressources de l'Évangile",
"map": "Carte",
"search_placeholder": "Rechercher peuples, lieux, langues, religions…"
"search_placeholder": "Rechercher peuples, lieux, langues, religions…",
"any": "Tous",
"active_count": "{n} actifs",
"prayer_status": "État de prière",
"map_controls": "Commandes de la carte",
"close": "Fermer",
"clear": "Effacer",
"dashboard_title": "Tableau de bord de recherche global",
"align_dashboard": "Aligner le tableau",
"align_dashboard_tip": "Rétablir la disposition par défaut du tableau de bord",
"selected": "Sélectionné",
"world": "Monde",
"vertical_legend": "Légende verticale",
"groups_in_scope": "peuples dans le périmètre",
"filter_by": "Filtrer par",
"remove_filter": "Retirer le filtre",
"groups": "peuples",
"expand": "Développer"
}

View file

@ -31,5 +31,22 @@
"filters": "फ़िल्टर",
"gospel_resources": "सुसमाचार संसाधन",
"map": "नक्शा",
"search_placeholder": "जनसमूह, स्थान, भाषा, धर्म खोजें…"
"search_placeholder": "जनसमूह, स्थान, भाषा, धर्म खोजें…",
"any": "कोई भी",
"active_count": "{n} सक्रिय",
"prayer_status": "प्रार्थना स्थिति",
"map_controls": "मानचित्र नियंत्रण",
"close": "बंद करें",
"clear": "साफ़ करें",
"dashboard_title": "बिग पिक्चर शोध डैशबोर्ड",
"align_dashboard": "डैशबोर्ड संरेखित करें",
"align_dashboard_tip": "डैशबोर्ड लेआउट को डिफ़ॉल्ट संरेखण पर लौटाएँ",
"selected": "चयनित",
"world": "विश्व",
"vertical_legend": "लंबवत लेजेंड",
"groups_in_scope": "दायरे में जनसमूह",
"filter_by": "इससे फ़िल्टर करें",
"remove_filter": "फ़िल्टर हटाएँ",
"groups": "जनसमूह",
"expand": "विस्तार करें"
}

View file

@ -31,5 +31,22 @@
"filters": "Filtri",
"gospel_resources": "Risorse del Vangelo",
"map": "Mappa",
"search_placeholder": "Cerca popoli, luoghi, lingue, religioni…"
"search_placeholder": "Cerca popoli, luoghi, lingue, religioni…",
"any": "Tutti",
"active_count": "{n} attivi",
"prayer_status": "Stato di preghiera",
"map_controls": "Controlli della mappa",
"close": "Chiudi",
"clear": "Cancella",
"dashboard_title": "Cruscotto di ricerca generale",
"align_dashboard": "Allinea cruscotto",
"align_dashboard_tip": "Ripristina la disposizione predefinita del cruscotto",
"selected": "Selezionato",
"world": "Mondo",
"vertical_legend": "Legenda verticale",
"groups_in_scope": "popoli nell’ambito",
"filter_by": "Filtra per",
"remove_filter": "Rimuovi filtro",
"groups": "popoli",
"expand": "Espandi"
}

View file

@ -31,5 +31,22 @@
"filters": "Filtros",
"gospel_resources": "Recursos do Evangelho",
"map": "Mapa",
"search_placeholder": "Pesquisar povos, lugares, idiomas, religiões…"
"search_placeholder": "Pesquisar povos, lugares, idiomas, religiões…",
"any": "Qualquer",
"active_count": "{n} ativos",
"prayer_status": "Estado de oração",
"map_controls": "Controlos do mapa",
"close": "Fechar",
"clear": "Limpar",
"dashboard_title": "Painel de pesquisa geral",
"align_dashboard": "Alinhar painel",
"align_dashboard_tip": "Repor a disposição do painel para o alinhamento predefinido",
"selected": "Selecionado",
"world": "Mundo",
"vertical_legend": "Legenda vertical",
"groups_in_scope": "povos no âmbito",
"filter_by": "Filtrar por",
"remove_filter": "Remover filtro",
"groups": "povos",
"expand": "Expandir"
}

View file

@ -31,5 +31,22 @@
"filters": "Filtre",
"gospel_resources": "Resurse ale Evangheliei",
"map": "Hartă",
"search_placeholder": "Caută popoare, locuri, limbi, religii…"
"search_placeholder": "Caută popoare, locuri, limbi, religii…",
"any": "Oricare",
"active_count": "{n} active",
"prayer_status": "Stare de rugăciune",
"map_controls": "Comenzile hărții",
"close": "Închide",
"clear": "Șterge",
"dashboard_title": "Tablou de bord de cercetare general",
"align_dashboard": "Aliniază tabloul",
"align_dashboard_tip": "Readu aranjarea tabloului la alinierea implicită",
"selected": "Selectat",
"world": "Lume",
"vertical_legend": "Legendă verticală",
"groups_in_scope": "popoare în domeniu",
"filter_by": "Filtrează după",
"remove_filter": "Elimină filtrul",
"groups": "popoare",
"expand": "Extinde"
}

View file

@ -31,5 +31,22 @@
"filters": "Фильтры",
"gospel_resources": "Евангельские ресурсы",
"map": "Карта",
"search_placeholder": "Поиск народов, мест, языков, религий…"
"search_placeholder": "Поиск народов, мест, языков, религий…",
"any": "Любой",
"active_count": "{n} активно",
"prayer_status": "Статус молитвы",
"map_controls": "Элементы управления картой",
"close": "Закрыть",
"clear": "Очистить",
"dashboard_title": "Обзорная исследовательская панель",
"align_dashboard": "Выровнять панель",
"align_dashboard_tip": "Вернуть расположение панели к виду по умолчанию",
"selected": "Выбрано",
"world": "Мир",
"vertical_legend": "Вертикальная легенда",
"groups_in_scope": "народов в выборке",
"filter_by": "Фильтровать по",
"remove_filter": "Убрать фильтр",
"groups": "народов",
"expand": "Развернуть"
}

View file

@ -31,5 +31,22 @@
"filters": "筛选",
"gospel_resources": "福音资源",
"map": "地图",
"search_placeholder": "搜索民族、地点、语言、宗教…"
"search_placeholder": "搜索民族、地点、语言、宗教…",
"any": "全部",
"active_count": "{n} 项启用",
"prayer_status": "代祷状态",
"map_controls": "地图控件",
"close": "关闭",
"clear": "清除",
"dashboard_title": "全局研究仪表板",
"align_dashboard": "对齐仪表板",
"align_dashboard_tip": "将仪表板布局恢复为默认对齐",
"selected": "已选择",
"world": "世界",
"vertical_legend": "垂直图例",
"groups_in_scope": "个民族在范围内",
"filter_by": "筛选",
"remove_filter": "移除筛选",
"groups": "个民族",
"expand": "展开"
}

View file

@ -1,5 +1,5 @@
/**
* rtl-text.js — load Mapbox's RTL text plugin ONCE per page.
* rtl-text.js — load the RTL text plugin ONCE per page, for Mapbox AND MapLibre.
*
* WHY THIS IS A SHARED FUNCTION AND NOT A COPY-PASTE BLOCK. Every bundle entry that boots a map
* needs this, and the block was duplicated into each `index.js` by hand. A baked cap-4 composite
@ -31,20 +31,67 @@
* is swallowed here, so calling this from several entries on one page is safe.
*/
const RTL_PLUGIN_URL =
'https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-rtl-text/v0.3.0/mapbox-gl-rtl-text.js'
// ONE PLUGIN, TWO ENGINES, TWO SOURCES. Mapbox keeps its own CDN (unchanged). MapLibre gets the same
// plugin package from jsDelivr — keyless and NOT api.mapbox.com, so a keyless page (provider
// maplibre) still makes zero Mapbox requests (check:gallery-embed:maplibre enforces that).
export const RTL_PLUGIN_URLS = {
mapbox: 'https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-rtl-text/v0.3.0/mapbox-gl-rtl-text.js',
maplibre: 'https://cdn.jsdelivr.net/npm/@mapbox/mapbox-gl-rtl-text@0.3.0/dist/mapbox-gl-rtl-text.js'
}
const RTL_PLUGIN_URL = RTL_PLUGIN_URLS.mapbox // kept for readers grepping the old name
export function installRtlTextPlugin() {
if (typeof window === 'undefined' || !window.mapboxgl?.setRTLTextPlugin) return false
try {
// `true` = LAZY: fetch the plugin only when RTL text is actually encountered, so a map with no
// RTL labels pays nothing.
window.mapboxgl.setRTLTextPlugin(RTL_PLUGIN_URL, null, true)
return true
} catch (_) {
// Already set in this session. Expected whenever two entries run on one page — not an error.
return false
// ★ MAPLIBRE WAS NEVER COVERED (2026-09-25). This used to check window.mapboxgl only, so every
// MapLibre map — every keyless embed — drew Arabic, Hebrew and Persian labels as disconnected,
// reversed glyphs. Measured on the Prayer Walk Planner's printed Arabic sheet. A second gap sat under
// it: bundle entries call this at LOAD time, before useMapInstance has injected a MapLibre engine,
// so even an engine-aware version found nothing to install into. useMapInstance now also calls it
// the moment an engine global exists, which is what makes it reach every map.
function isMaplibre(gl) { return !!gl && typeof window !== 'undefined' && gl === window.maplibregl }
/**
* Install the RTL text plugin, lazily, on the given engine — or on whichever engine globals exist.
* Idempotent: safe from several entries and from every map init on one page.
* @param {object} [engine] window.mapboxgl or window.maplibregl; omitted = both, if present
* @returns {boolean} true when this call installed it
*/
export function installRtlTextPlugin(engine) {
if (typeof window === 'undefined') return false
const engines = engine ? [engine] : [window.maplibregl, window.mapboxgl].filter(Boolean)
let installed = false
for (const gl of engines) {
if (!gl || !gl.setRTLTextPlugin) continue
try {
if (isMaplibre(gl)) {
// MapLibre: (url, lazy) → Promise. Guard on status: a second call rejects.
if (gl.getRTLTextPluginStatus && gl.getRTLTextPluginStatus() !== 'unavailable') continue
const r = gl.setRTLTextPlugin(RTL_PLUGIN_URLS.maplibre, true)
if (r && r.catch) r.catch(() => {})
} else {
// `true` = LAZY: fetch the plugin only when RTL text is actually encountered, so a map
// with no RTL labels pays nothing.
gl.setRTLTextPlugin(RTL_PLUGIN_URLS.mapbox, null, true)
}
installed = true
} catch (_) {
// Already set in this session. Expected whenever two entries run on one page — not an error.
}
}
return installed
}
/**
* Make sure the plugin is LOADED (not merely registered) before a single frame is captured — a
* print or snapshot takes one frame, and a lazily-loaded plugin can still be in flight when it
* does. MapLibre only (Mapbox has no status API); resolves after at most ~5s either way.
*/
export async function ensureRtlTextPlugin(gl) {
if (!gl || !isMaplibre(gl) || !gl.getRTLTextPluginStatus) return
try {
// Not registered yet → register EAGERLY. Already registered lazily ('deferred') → it loads on the
// first RTL label this map draws, so just wait for it below.
if (gl.getRTLTextPluginStatus() === 'unavailable') await gl.setRTLTextPlugin(RTL_PLUGIN_URLS.maplibre, false)
for (let i = 0; i < 50 && !['loaded', 'error'].includes(gl.getRTLTextPluginStatus()); i++) await new Promise(r => setTimeout(r, 100))
} catch (_) { /* shaping is a nicety; the map still renders */ }
}
export default installRtlTextPlugin

View file

@ -26,10 +26,20 @@ import { readdirSync, existsSync, readFileSync } from 'node:fs';
import { fileURLToPath } from 'node:url';
import { dirname, join } from 'node:path';
import { firefox } from 'playwright';
import { requireThisTree } from '../../../internal/_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
const __dirname = dirname(fileURLToPath(import.meta.url));
const DIR = process.env.POSTER_DIR || join(__dirname, 'out', 'posters');
const PREFIX = process.argv[2] || '';
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '../../..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(PREFIX, ROOT, 'POSTERS')
if (!existsSync(DIR)) { console.error('no out/posters — run the generator first'); process.exit(1); }
const files = readdirSync(DIR).filter((f) => f.endsWith('.html') && f.startsWith(PREFIX));

View file

@ -3,6 +3,9 @@
// running app can load a table — a renamed field or a moved file would pass both
// and leave an empty list view.
import { firefox } from 'playwright';
import { requireThisTree } from '../../../internal/_serves-this-tree.mjs'
import { resolve as _resolvePath, dirname as _dirnamePath } from 'node:path'
import { fileURLToPath as _fileURLToPath } from 'node:url'
// MUST be served over HTTP from THIS repo's public/. Two traps, both hit for real:
// * file:// does not mount the bundles at all — zero custom elements, no error.
@ -14,6 +17,14 @@ import { firefox } from 'playwright';
// other browser gate uses. It was 8917 — a port nothing in this repo has ever bound, so the guard
// could only ever fail unless someone happened to know the number. Override with APP_BASE.
const BASE = process.env.APP_BASE || 'http://127.0.0.1:4173';
const ROOT = _resolvePath(_dirnamePath(_fileURLToPath(import.meta.url)), '../../..')
// ★ MEASURE THIS BUILD, OR MEASURE NOTHING. Several worktrees run on one machine and a default port
// belongs to whichever server started first — measured 2026-09-24 on :4173, where browser gates
// reported confidently about a build nobody here had touched. 75 (EX_TEMPFAIL), not 1: the wrong
// tree is a precondition, not a product defect, and the wave runner reports 75 as ⊘ rather than ✗.
// A file:// target passes straight through — there is no server there to be wrong about.
await requireThisTree(BASE, ROOT, 'APP-TABLES')
// ★ REWRITTEN 2026-09-23: these are LEAF PAGES from the manifest, not hash fragments on a shell.
//
// The previous list was ['key-city-posters', 'cities-with-internet', 'gospel-resources'] navigated

View file

@ -20,6 +20,16 @@ import StackLayout from '@map/layouts/StackLayout.vue'
import ResearchDashboard from '../research-dashboard/research-dashboard.vue'
import PeopleGroupsGrid from '../people-groups-grid/people-groups-grid.vue'
// ★ THE HOST'S INLINE STYLE MUST NOT LAND ON OUR ROOT.
// This SFC is mounted AS a custom element, so a style attribute the HOST page puts on the tag falls
// through onto this component's root element. MEASURED 2026-09-25 with a host style of
// "display:flex; position:relative; height:100%": that exact string appeared verbatim on the inner
// root div of this component — the gallery sets one on every tab, and on the Prayer Walk Planner
// the same fallthrough collapsed the plugin to 76px. The element's own :host rules are the contract
// for how it sizes itself; a host styling the TAG is styling the box, not our internals.
defineOptions({ inheritAttrs: false })
// ── THE DASHBOARD → GRID LINK ────────────────────────────────────────────────────────────
// THE BUG THIS FIXES (Driver-reported; measured 2026-09-22). Selecting anything in the
// dashboard above did not filter the grid below. Measured: the dashboard reacted every time

View file

@ -56,6 +56,16 @@ import { RELIGION_FAMILIES } from '@map/colors/religion.js'
import { canonicalFamilyName } from '@map/colors/language-family.js'
import langFamilyByIso from '@map/data/langFamilyByIso.json'
// ★ THE HOST'S INLINE STYLE MUST NOT LAND ON OUR ROOT.
// This SFC is mounted AS a custom element, so a style attribute the HOST page puts on the tag falls
// through onto this component's root element. MEASURED 2026-09-25 with a host style of
// "display:flex; position:relative; height:100%": that exact string appeared verbatim on the inner
// root div of this component — the gallery sets one on every tab, and on the Prayer Walk Planner
// the same fallthrough collapsed the plugin to 76px. The element's own :host rules are the contract
// for how it sizes itself; a host styling the TAG is styling the box, not our internals.
defineOptions({ inheritAttrs: false })
const props = defineProps({
// ── injected standalone deps (replace Nuxt useRuntimeConfig / useI18n / useLocalePath) ──
profileConfig: { type: String, default: '' },

View file

@ -52,6 +52,7 @@ import { useShadowStyles } from '@map/composables/useShadowStyles.js'
import { openPrintFrame } from '@map/composables/printInPlace.js'
import ShareButton from '@map/components/map-controls/ShareButton.vue'
import { resolveNamedStyle } from '@map/styles/registry.js'
import { ensureRtlTextPlugin } from '@map/maps/rtl-text.js'
import { translate, LOCALES } from './src/strings.js'
// ─── The host's attributes stay on the host ───────────────────────────────────
@ -385,27 +386,14 @@ function localizeBasemapLabels(m, lang) {
// Render ONE zone as a print-resolution PNG data URL in a temporary, off-screen MapLibre map.
// Returns null when there is no engine (no WebGL) — the sheet then prints without a map.
// ★ ARABIC (and every RTL script) NEEDS THE RTL TEXT PLUGIN, and MapLibre never had it here.
// library/maps/rtl-text.js installs it for MAPBOX only (window.mapboxgl, from api.mapbox.com), so a
// MapLibre map drew Arabic place names as disconnected, reversed glyphs — measured on the printed
// Arabic sheet, 2026-09-25. This installs the same plugin for MapLibre from a keyless CDN and, for
// the print map, WAITS for it: a lazily-loaded plugin can still be loading when the frame is taken.
const RTL_PLUGIN_URL = 'https://cdn.jsdelivr.net/npm/@mapbox/mapbox-gl-rtl-text@0.3.0/dist/mapbox-gl-rtl-text.js'
async function ensureRtlText(gl) {
try {
const status = gl.getRTLTextPluginStatus ? gl.getRTLTextPluginStatus() : 'unavailable'
if (status === 'unavailable') await gl.setRTLTextPlugin(RTL_PLUGIN_URL, false)
for (let i = 0; i < 50 && gl.getRTLTextPluginStatus && gl.getRTLTextPluginStatus() !== 'loaded'; i++) {
if (gl.getRTLTextPluginStatus() === 'error') break
await new Promise(r => setTimeout(r, 100))
}
} catch (_) { /* shaping is a nicety; the map still renders */ }
}
// Arabic (and every RTL script) needs the RTL text plugin, and the print map must WAIT for it:
// it captures one frame, and a lazily-loaded plugin can still be in flight. The shared helper
// (library/maps/rtl-text.js) owns the URL and the engine logic; useMapInstance installs it lazily
// for the live map. Measured on the printed Arabic sheet 2026-09-25: without it, unshaped glyphs.
async function renderPrintMap(zone) {
const gl = typeof window !== 'undefined' && window.maplibregl
if (!gl) return null
await ensureRtlText(gl)
await ensureRtlTextPlugin(gl)
let minLng = Infinity, minLat = Infinity, maxLng = -Infinity, maxLat = -Infinity
for (const [lng, lat] of zone.coords) {
if (lng < minLng) minLng = lng; if (lng > maxLng) maxLng = lng
@ -603,7 +591,6 @@ onMounted(async () => {
try {
await initializeMap()
if (map.value) {
if (window.maplibregl) ensureRtlText(window.maplibregl)
map.value.on('load', () => { localizeBasemapLabels(map.value, uiLocale.value); setupMapLayers(); refreshMapSources() })
}
} catch (e) {

View file

@ -43,7 +43,7 @@ export default {
// element on a partner site, so the title is what a visitor reads there — it has to name the
// product, not just the page. "Big Picture" is also the cap-4 composite's name and tab-1 of the
// cap-5 SPA, so one term now runs consistently from the tab through to an embedded partner view.
title: 'Big Picture Research Dashboard',
get title() { return tStatic('dashboard.dashboard_title') || 'Big Picture Research Dashboard' },
element: 'doxa-research-dashboard',
// ── data source ── (consumed by useDashboardData; the arg is currently advisory —

View file

@ -1,4 +1,6 @@
<script setup>
import { tStatic } from '@map/i18n/index.js'
const L = (key, en) => tStatic('dashboard.' + key) || en
/**
* Breadcrumb — RDASH phase 8 delighter: drill-down breadcrumb (World ▸ Asia ▸ Hinduism …).
* Every filter pushes a crumb; click a crumb to pop back to that altitude (legible + reversible
@ -42,7 +44,7 @@ useShadowStyles(`
<template>
<nav class="rd-breadcrumb" data-breadcrumb @click="onClick" aria-label="Filter breadcrumb">
<span class="rd-crumb root" data-crumb="__root__">World</span>
<span class="rd-crumb root" data-crumb="__root__">{{ L('world', 'World') }}</span>
<template v-for="(c, i) in crumbs" :key="c.k">
<span class="rd-sep">▸</span>
<span class="rd-crumb" :class="{ cur: i === crumbs.length - 1 }" data-crumb-item :data-crumb="c.k">{{ c.v }}</span>

View file

@ -1,4 +1,6 @@
<script setup>
import { tStatic } from '@map/i18n/index.js'
const L = (key, en) => tStatic('dashboard.' + key) || en
/**
* DashboardFacetRail (was Sidebar.vue) — RDASH redesign phase 2: the floating @map SemanticTreeLegend is DROPPED.
*
@ -697,8 +699,8 @@ useShadowStyles(`
user-facing label (the component/docs still describe the semantic-tree MODEL).
The four stacked trees below it are People · Place · Language · Religion, in that
order — the four axes a researcher navigates to find who has gospel resources. -->
<div class="fr-title">Vertical Legend</div>
<div class="fr-scope" data-scope-count><b>{{ scopeCount.toLocaleString('en-US') }}</b> groups in scope</div>
<div class="fr-title">{{ L('vertical_legend', 'Vertical Legend') }}</div>
<div class="fr-scope" data-scope-count><b>{{ scopeCount.toLocaleString('en-US') }}</b> {{ L('groups_in_scope', 'groups in scope') }}</div>
</div>
<div class="fr-body" ref="railEl" @click="onRowClick" @keydown="onRowKey">
@ -714,7 +716,7 @@ useShadowStyles(`
:tabindex="(r.other || r.zero) ? null : 0"
:role="(r.other || r.zero) ? null : 'button'"
:aria-pressed="(r.other || r.zero) ? null : (r.active ? 'true' : 'false')"
:aria-label="(r.other || r.zero) ? null : ((r.active ? 'Remove filter ' : 'Filter by ') + r.label + ', ' + r.count.toLocaleString('en-US') + ' groups' + (r.dashboardOnly ? '. Updates the charts on this dashboard only; it does not filter the list below.' : ''))"
:aria-label="(r.other || r.zero) ? null : ((r.active ? L('remove_filter', 'Remove filter') : L('filter_by', 'Filter by')) + ' ' + r.label + ', ' + r.count.toLocaleString('en-US') + ' ' + L('groups', 'groups') + (r.dashboardOnly ? '. Updates the charts on this dashboard only; it does not filter the list below.' : ''))"
:title="r.dashboardOnly ? 'Updates this dashboard only — the list below does not filter on ' + r.label : null">
<!-- tree trunks: one span per ancestor level, same glyph vocabulary as the
research-map's SemanticTreeLegend so the hierarchy is DRAWN, not just padded. -->

View file

@ -1,4 +1,6 @@
<script setup>
import { tStatic } from '@map/i18n/index.js'
const L = (key, en) => tStatic('dashboard.' + key) || en
/**
* DashboardTopBar — RDASH P4 Command Bar (topbar grid region, 52px).
* One cohesive header surface holding, on ONE row:
@ -308,9 +310,9 @@ useShadowStyles(`
</div>
</div>
<span class="rd-align" role="button" tabindex="0" data-align-btn
title="Reset the dashboard layout to its default alignment"
:title="L('align_dashboard_tip', 'Reset the dashboard layout to its default alignment')"
@click="onAlignLayout" @keydown.enter.prevent="onAlignLayout" @keydown.space.prevent="onAlignLayout">
⤢ Align Dashboard
⤢ {{ L('align_dashboard', 'Align Dashboard') }}
</span>
<!-- CSV export MOVED to the people-groups table header (DashboardDataTable), below the map —
card BUILD-CSV-EXPORT-MOVE-TO-TABLE-HEADER-ALL-FIELDS. It exports THAT table, so it now

View file

@ -60,6 +60,16 @@ import StackLayout from '@map/layouts/StackLayout.vue'
import { resolveEmbedBase } from '@map/utils/embedBase.js'
import { publishMapToken } from '@map/composables/useSharedMapToken.js'
// ★ THE HOST'S INLINE STYLE MUST NOT LAND ON OUR ROOT.
// This SFC is mounted AS a custom element, so a style attribute the HOST page puts on the tag falls
// through onto this component's root element. MEASURED 2026-09-25 with a host style of
// "display:flex; position:relative; height:100%": that exact string appeared verbatim on the inner
// root div of this component — the gallery sets one on every tab, and on the Prayer Walk Planner
// the same fallthrough collapsed the plugin to 76px. The element's own :host rules are the contract
// for how it sizes itself; a host styling the TAG is styling the box, not our internals.
defineOptions({ inheritAttrs: false })
// ★ THE HOST'S OWN profile-config, WHICH THIS COMPOSITE USED TO THROW AWAY.
// It declared no props at all, so a partner's <research-map-plus-grid profile-config='{"tk":"..."}'>
// had its token dropped on the floor. On our own generated leaf that was invisible: the leaf page

View file

@ -17,6 +17,16 @@ import { computed } from 'vue'
import StackLayout from '@map/layouts/StackLayout.vue'
import { publishMapToken } from '@map/composables/useSharedMapToken.js'
// ★ THE HOST'S INLINE STYLE MUST NOT LAND ON OUR ROOT.
// This SFC is mounted AS a custom element, so a style attribute the HOST page puts on the tag falls
// through onto this component's root element. MEASURED 2026-09-25 with a host style of
// "display:flex; position:relative; height:100%": that exact string appeared verbatim on the inner
// root div of this component — the gallery sets one on every tab, and on the Prayer Walk Planner
// the same fallthrough collapsed the plugin to 76px. The element's own :host rules are the contract
// for how it sizes itself; a host styling the TAG is styling the box, not our internals.
defineOptions({ inheritAttrs: false })
// The two elements to stack. `src` is TREE-RELATIVE at build; the leaf pages resolve it against the
// bundle tree root. Both elements ship their own bundles in the same catalog.
// ── WHERE A SIBLING BUNDLE LIVES DEPENDS ON WHICH TREE IS SERVING ────────────────────────────

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <all-people-groups> custom element. -->
<script src="../all-people-groups.js" integrity="sha384-lJI0V+GhEdU/pZEFL7cQwTcYVqmzPyjApsqQqkXnhmk9hB1zKVzd2het4xGMdWxx" crossorigin="anonymous"></script>
<script src="../all-people-groups.js" integrity="sha384-jvdsSW2vNF+xKoQNtlAy4b8Oodc5avQOw9zn8IjiERCi/mCKMGJTEEUmtMgiJ4wF" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <bp-big-picture> custom element. -->
<script src="../../big-picture.js" integrity="sha384-ISt0kwPfFob7KBzHpcdJIVjv652N3alsxTyOfN13SGrBt0OKHD5NJQYQFt3jnYWQ" crossorigin="anonymous"></script>
<script src="../../big-picture.js" integrity="sha384-MIotyiMkAcAJizhxGzzi0k3Vjd4souqd8URA5CoGwZdBTmdFeXLxdsOQY0A/7OKf" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <bp-big-picture> custom element. -->
<script src="../../big-picture.js" integrity="sha384-ISt0kwPfFob7KBzHpcdJIVjv652N3alsxTyOfN13SGrBt0OKHD5NJQYQFt3jnYWQ" crossorigin="anonymous"></script>
<script src="../../big-picture.js" integrity="sha384-MIotyiMkAcAJizhxGzzi0k3Vjd4souqd8URA5CoGwZdBTmdFeXLxdsOQY0A/7OKf" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <bp-big-picture> custom element. -->
<script src="../big-picture.js" integrity="sha384-ISt0kwPfFob7KBzHpcdJIVjv652N3alsxTyOfN13SGrBt0OKHD5NJQYQFt3jnYWQ" crossorigin="anonymous"></script>
<script src="../big-picture.js" integrity="sha384-MIotyiMkAcAJizhxGzzi0k3Vjd4souqd8URA5CoGwZdBTmdFeXLxdsOQY0A/7OKf" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <country-posters-map> custom element. -->
<script src="../country-posters.js" integrity="sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V" crossorigin="anonymous"></script>
<script src="../country-posters.js" integrity="sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -26,7 +26,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <country-posters-map> custom element. -->
<script src="../country-posters.js" integrity="sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V" crossorigin="anonymous"></script>
<script src="../country-posters.js" integrity="sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -40,7 +40,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <country-posters-map> custom element. -->
<script src="../country-posters.js" integrity="sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V" crossorigin="anonymous"></script>
<script src="../country-posters.js" integrity="sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -40,7 +40,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <dashboard-plus-grid> custom element. -->
<script src="../../dashboard-plus-grid.js" integrity="sha384-yXe7qKTXdATjFRqUkMsxgt4ScSem7bPiIWsqpsj8PlYDO2VhZf+qtE2htlgtAsz4" crossorigin="anonymous"></script>
<script src="../../dashboard-plus-grid.js" integrity="sha384-f4Hc989WsNYgAn/eTyG/tfJ9sMJYbTY9D1P6oaZVvvxyU2Bm6rbU/P9Jh4fN8lcX" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -40,7 +40,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <dashboard-plus-grid> custom element. -->
<script src="../dashboard-plus-grid.js" integrity="sha384-yXe7qKTXdATjFRqUkMsxgt4ScSem7bPiIWsqpsj8PlYDO2VhZf+qtE2htlgtAsz4" crossorigin="anonymous"></script>
<script src="../dashboard-plus-grid.js" integrity="sha384-f4Hc989WsNYgAn/eTyG/tfJ9sMJYbTY9D1P6oaZVvvxyU2Bm6rbU/P9Jh4fN8lcX" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <demo-map> custom element. -->
<script src="../demo-map.js" integrity="sha384-3+0MJQUzG3zH9+mRTDaxHIfhyfjq8aiUNdKWETsBGqaz4+yUA0xtE1oxAX1I10aQ" crossorigin="anonymous"></script>
<script src="../demo-map.js" integrity="sha384-kk/cmUlZOPJKofRPRZ6xB1SPUnPewaFZPSNBVGWjWj10LPsiYA50/Q/D+zvl/nAz" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -27,7 +27,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <demo-map> custom element. -->
<script src="../../demo-map.js" integrity="sha384-3+0MJQUzG3zH9+mRTDaxHIfhyfjq8aiUNdKWETsBGqaz4+yUA0xtE1oxAX1I10aQ" crossorigin="anonymous"></script>
<script src="../../demo-map.js" integrity="sha384-kk/cmUlZOPJKofRPRZ6xB1SPUnPewaFZPSNBVGWjWj10LPsiYA50/Q/D+zvl/nAz" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-research-map> custom element. -->
<script src="../doxa-research-map.js" integrity="sha384-9H9uCJn3I20YD5RJpnSZaSCiC1QMF9/v0/NtymZBstslAOi3pf241KMEgRgFU2Hd" crossorigin="anonymous"></script>
<script src="../doxa-research-map.js" integrity="sha384-ZblpRN2LkrkSwRQwkcgAW6HliqJHNC6UroZfApRBE4LufTWKxVHYvhgXo7CHnMlE" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -27,7 +27,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-research-map> custom element. -->
<script src="../../doxa-research-map.js" integrity="sha384-9H9uCJn3I20YD5RJpnSZaSCiC1QMF9/v0/NtymZBstslAOi3pf241KMEgRgFU2Hd" crossorigin="anonymous"></script>
<script src="../../doxa-research-map.js" integrity="sha384-ZblpRN2LkrkSwRQwkcgAW6HliqJHNC6UroZfApRBE4LufTWKxVHYvhgXo7CHnMlE" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-map> custom element. -->
<script src="../../doxa-simple-map.js" integrity="sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc" crossorigin="anonymous"></script>
<script src="../../doxa-simple-map.js" integrity="sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-map> custom element. -->
<script src="../../doxa-simple-map.js" integrity="sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc" crossorigin="anonymous"></script>
<script src="../../doxa-simple-map.js" integrity="sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-map> custom element. -->
<script src="../doxa-simple-map.js" integrity="sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc" crossorigin="anonymous"></script>
<script src="../doxa-simple-map.js" integrity="sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <doxa-map> custom element. -->
<script src="../../doxa-simple-map.js" integrity="sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc" crossorigin="anonymous"></script>
<script src="../../doxa-simple-map.js" integrity="sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -13,7 +13,7 @@
"bundle": "all-people-groups",
"scriptUrl": "./all-people-groups/all-people-groups.js",
"output": "doxa-maps/all-people-groups/all-people-groups.js",
"integrity": "sha384-lJI0V+GhEdU/pZEFL7cQwTcYVqmzPyjApsqQqkXnhmk9hB1zKVzd2het4xGMdWxx",
"integrity": "sha384-jvdsSW2vNF+xKoQNtlAy4b8Oodc5avQOw9zn8IjiERCi/mCKMGJTEEUmtMgiJ4wF",
"elements": [
"all-people-groups"
],
@ -29,7 +29,7 @@
"scriptUrl": "./all-people-groups/all-people-groups.js",
"embed": {
"iframe": "<iframe src=\"./all-people-groups/all-people-groups/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./all-people-groups/all-people-groups.js\" integrity=\"sha384-lJI0V+GhEdU/pZEFL7cQwTcYVqmzPyjApsqQqkXnhmk9hB1zKVzd2het4xGMdWxx\" crossorigin=\"anonymous\"></script>\n<all-people-groups profile-config='{\"profile\":\"all-people-groups\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></all-people-groups>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./all-people-groups/all-people-groups.js\" integrity=\"sha384-jvdsSW2vNF+xKoQNtlAy4b8Oodc5avQOw9zn8IjiERCi/mCKMGJTEEUmtMgiJ4wF\" crossorigin=\"anonymous\"></script>\n<all-people-groups profile-config='{\"profile\":\"all-people-groups\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></all-people-groups>"
},
"bundle": "all-people-groups"
}
@ -39,7 +39,7 @@
"bundle": "big-picture",
"scriptUrl": "./big-picture/big-picture.js",
"output": "doxa-maps/big-picture/big-picture.js",
"integrity": "sha384-ISt0kwPfFob7KBzHpcdJIVjv652N3alsxTyOfN13SGrBt0OKHD5NJQYQFt3jnYWQ",
"integrity": "sha384-MIotyiMkAcAJizhxGzzi0k3Vjd4souqd8URA5CoGwZdBTmdFeXLxdsOQY0A/7OKf",
"elements": [
"bp-big-picture",
"bp-research-header",
@ -61,7 +61,7 @@
"scriptUrl": "./big-picture/big-picture.js",
"embed": {
"iframe": "<iframe src=\"./big-picture/big-picture/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./big-picture/big-picture.js\" integrity=\"sha384-ISt0kwPfFob7KBzHpcdJIVjv652N3alsxTyOfN13SGrBt0OKHD5NJQYQFt3jnYWQ\" crossorigin=\"anonymous\"></script>\n<bp-big-picture profile-config='{\"profile\":\"big-picture\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></bp-big-picture>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./big-picture/big-picture.js\" integrity=\"sha384-MIotyiMkAcAJizhxGzzi0k3Vjd4souqd8URA5CoGwZdBTmdFeXLxdsOQY0A/7OKf\" crossorigin=\"anonymous\"></script>\n<bp-big-picture profile-config='{\"profile\":\"big-picture\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></bp-big-picture>"
},
"instances": [
{
@ -158,7 +158,7 @@
"bundle": "country-posters",
"scriptUrl": "./country-posters/country-posters.js",
"output": "doxa-maps/country-posters/country-posters.js",
"integrity": "sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V",
"integrity": "sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu",
"elements": [
"country-posters-map"
],
@ -178,7 +178,7 @@
"scriptUrl": "./country-posters/country-posters.js",
"embed": {
"iframe": "<iframe src=\"./country-posters/countries-map/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"countries-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"countries-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
}
},
{
@ -192,7 +192,7 @@
"scriptUrl": "./country-posters/country-posters.js",
"embed": {
"iframe": "<iframe src=\"./country-posters/country-poster-wall/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"country-poster-wall\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"country-poster-wall\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
}
},
{
@ -206,7 +206,7 @@
"scriptUrl": "./country-posters/country-posters.js",
"embed": {
"iframe": "<iframe src=\"./country-posters/country-posters-mfe/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-v7L/+GJ4PJtgHuBHTblSHdMdpwDcU2snwsxbH/+T/hrItI4Nh5MHHcYoNzDhcS/V\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"country-posters-mfe\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./country-posters/country-posters.js\" integrity=\"sha384-0KSJMk7mxBXLvGx22IXjbGnqPD9uIV15iwF+zTJl5Evo8M6m0Zf8BTwfI7b3e5cu\" crossorigin=\"anonymous\"></script>\n<country-posters-map profile-config='{\"profile\":\"country-posters-mfe\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></country-posters-map>"
}
}
]
@ -215,7 +215,7 @@
"bundle": "dashboard-plus-grid",
"scriptUrl": "./dashboard-plus-grid/dashboard-plus-grid.js",
"output": "doxa-maps/dashboard-plus-grid/dashboard-plus-grid.js",
"integrity": "sha384-yXe7qKTXdATjFRqUkMsxgt4ScSem7bPiIWsqpsj8PlYDO2VhZf+qtE2htlgtAsz4",
"integrity": "sha384-f4Hc989WsNYgAn/eTyG/tfJ9sMJYbTY9D1P6oaZVvvxyU2Bm6rbU/P9Jh4fN8lcX",
"elements": [
"dashboard-plus-grid"
],
@ -235,7 +235,7 @@
"scriptUrl": "./dashboard-plus-grid/dashboard-plus-grid.js",
"embed": {
"iframe": "<iframe src=\"./dashboard-plus-grid/dashboard-plus-grid/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./dashboard-plus-grid/dashboard-plus-grid.js\" integrity=\"sha384-yXe7qKTXdATjFRqUkMsxgt4ScSem7bPiIWsqpsj8PlYDO2VhZf+qtE2htlgtAsz4\" crossorigin=\"anonymous\"></script>\n<dashboard-plus-grid profile-config='{\"profile\":\"dashboard-plus-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></dashboard-plus-grid>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./dashboard-plus-grid/dashboard-plus-grid.js\" integrity=\"sha384-f4Hc989WsNYgAn/eTyG/tfJ9sMJYbTY9D1P6oaZVvvxyU2Bm6rbU/P9Jh4fN8lcX\" crossorigin=\"anonymous\"></script>\n<dashboard-plus-grid profile-config='{\"profile\":\"dashboard-plus-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></dashboard-plus-grid>"
},
"instances": [
{
@ -259,7 +259,7 @@
"bundle": "demo-map",
"scriptUrl": "./demo-map/demo-map.js",
"output": "doxa-maps/demo-map/demo-map.js",
"integrity": "sha384-3+0MJQUzG3zH9+mRTDaxHIfhyfjq8aiUNdKWETsBGqaz4+yUA0xtE1oxAX1I10aQ",
"integrity": "sha384-kk/cmUlZOPJKofRPRZ6xB1SPUnPewaFZPSNBVGWjWj10LPsiYA50/Q/D+zvl/nAz",
"elements": [
"demo-map"
],
@ -275,7 +275,7 @@
"scriptUrl": "./demo-map/demo-map.js",
"embed": {
"iframe": "<iframe src=\"./demo-map/demo-map/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./demo-map/demo-map.js\" integrity=\"sha384-3+0MJQUzG3zH9+mRTDaxHIfhyfjq8aiUNdKWETsBGqaz4+yUA0xtE1oxAX1I10aQ\" crossorigin=\"anonymous\"></script>\n<demo-map profile-config='{\"profile\":\"demo-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></demo-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./demo-map/demo-map.js\" integrity=\"sha384-kk/cmUlZOPJKofRPRZ6xB1SPUnPewaFZPSNBVGWjWj10LPsiYA50/Q/D+zvl/nAz\" crossorigin=\"anonymous\"></script>\n<demo-map profile-config='{\"profile\":\"demo-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></demo-map>"
},
"instances": [
{
@ -354,7 +354,7 @@
"bundle": "doxa-research-map",
"scriptUrl": "./doxa-research-map/doxa-research-map.js",
"output": "doxa-maps/doxa-research-map/doxa-research-map.js",
"integrity": "sha384-9H9uCJn3I20YD5RJpnSZaSCiC1QMF9/v0/NtymZBstslAOi3pf241KMEgRgFU2Hd",
"integrity": "sha384-ZblpRN2LkrkSwRQwkcgAW6HliqJHNC6UroZfApRBE4LufTWKxVHYvhgXo7CHnMlE",
"elements": [
"doxa-research-map"
],
@ -370,7 +370,7 @@
"scriptUrl": "./doxa-research-map/doxa-research-map.js",
"embed": {
"iframe": "<iframe src=\"./doxa-research-map/research-map/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./doxa-research-map/doxa-research-map.js\" integrity=\"sha384-9H9uCJn3I20YD5RJpnSZaSCiC1QMF9/v0/NtymZBstslAOi3pf241KMEgRgFU2Hd\" crossorigin=\"anonymous\"></script>\n<doxa-research-map profile-config='{\"profile\":\"research-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></doxa-research-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./doxa-research-map/doxa-research-map.js\" integrity=\"sha384-ZblpRN2LkrkSwRQwkcgAW6HliqJHNC6UroZfApRBE4LufTWKxVHYvhgXo7CHnMlE\" crossorigin=\"anonymous\"></script>\n<doxa-research-map profile-config='{\"profile\":\"research-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></doxa-research-map>"
},
"instances": [
{
@ -396,7 +396,7 @@
"bundle": "doxa-simple-map",
"scriptUrl": "./doxa-simple-map/doxa-simple-map.js",
"output": "doxa-maps/doxa-simple-map/doxa-simple-map.js",
"integrity": "sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc",
"integrity": "sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2",
"elements": [
"doxa-map",
"doxa-simple-map"
@ -413,7 +413,7 @@
"scriptUrl": "./doxa-simple-map/doxa-simple-map.js",
"embed": {
"iframe": "<iframe src=\"./doxa-simple-map/doxa-simple-map/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./doxa-simple-map/doxa-simple-map.js\" integrity=\"sha384-UNTsuIGRBdH3u7q8NOdFm7YZCgyfNseZ35e5Z9sipJQo7m6cnmz3vEU19jehgtcc\" crossorigin=\"anonymous\"></script>\n<doxa-map profile-config='{\"profile\":\"doxa-simple-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></doxa-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./doxa-simple-map/doxa-simple-map.js\" integrity=\"sha384-UoEAocfZB2vPv7YfmlzcpOe/sdh1FV8XeZ8UdT6xIhmVia1arbnT+AG4m3vcpAd2\" crossorigin=\"anonymous\"></script>\n<doxa-map profile-config='{\"profile\":\"doxa-simple-map\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></doxa-map>"
},
"instances": [
{
@ -721,7 +721,7 @@
"bundle": "people-groups-grid",
"scriptUrl": "./people-groups-grid/people-groups-grid.js",
"output": "doxa-maps/people-groups-grid/people-groups-grid.js",
"integrity": "sha384-X3qjp89Dxlr8VW4cX0it+SuREyzXCeVDAba1YrKMyk7XWmlkFSpjLYNa2g6R5q4p",
"integrity": "sha384-SOgJZ7f+syLHYLSe0ZS99wYotonfFOt3imsoeiw1qpdqNPpdBOl/1mm0Kp+YNTFl",
"elements": [
"people-groups-grid"
],
@ -737,7 +737,7 @@
"scriptUrl": "./people-groups-grid/people-groups-grid.js",
"embed": {
"iframe": "<iframe src=\"./people-groups-grid/people-groups-grid/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./people-groups-grid/people-groups-grid.js\" integrity=\"sha384-X3qjp89Dxlr8VW4cX0it+SuREyzXCeVDAba1YrKMyk7XWmlkFSpjLYNa2g6R5q4p\" crossorigin=\"anonymous\"></script>\n<people-groups-grid profile-config='{\"profile\":\"people-groups-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></people-groups-grid>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./people-groups-grid/people-groups-grid.js\" integrity=\"sha384-SOgJZ7f+syLHYLSe0ZS99wYotonfFOt3imsoeiw1qpdqNPpdBOl/1mm0Kp+YNTFl\" crossorigin=\"anonymous\"></script>\n<people-groups-grid profile-config='{\"profile\":\"people-groups-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></people-groups-grid>"
},
"instances": [
{
@ -837,7 +837,7 @@
"bundle": "pplr-data-maps",
"scriptUrl": "./pplr-data-maps/pplr-data-maps.js",
"output": "doxa-maps/pplr-data-maps/pplr-data-maps.js",
"integrity": "sha384-u04GVRZqNXyBqfkyvCtm9IT6/RWbJTNTxTpv6ScsnE/5za+UIlTjAoZKIn9k2Zp3",
"integrity": "sha384-ARe/uZNMZehT22F9YI0tOasG9ay59Rdt4+x5wxlwFJZObTps4/+L6UwGq6G1yBG/",
"elements": [
"pplr-data-maps"
],
@ -853,7 +853,7 @@
"scriptUrl": "./pplr-data-maps/pplr-data-maps.js",
"embed": {
"iframe": "<iframe src=\"./pplr-data-maps/pplr-data-maps/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./pplr-data-maps/pplr-data-maps.js\" integrity=\"sha384-u04GVRZqNXyBqfkyvCtm9IT6/RWbJTNTxTpv6ScsnE/5za+UIlTjAoZKIn9k2Zp3\" crossorigin=\"anonymous\"></script>\n<pplr-data-maps profile-config='{\"profile\":\"pplr-data-maps\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></pplr-data-maps>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./pplr-data-maps/pplr-data-maps.js\" integrity=\"sha384-ARe/uZNMZehT22F9YI0tOasG9ay59Rdt4+x5wxlwFJZObTps4/+L6UwGq6G1yBG/\" crossorigin=\"anonymous\"></script>\n<pplr-data-maps profile-config='{\"profile\":\"pplr-data-maps\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></pplr-data-maps>"
},
"bundle": "pplr-data-maps"
}
@ -863,7 +863,7 @@
"bundle": "prayer-walk-planner",
"scriptUrl": "./prayer-walk-planner/prayer-walk-planner.js",
"output": "doxa-maps/prayer-walk-planner/prayer-walk-planner.js",
"integrity": "sha384-WPlrs8XIyGgif3VVs+wjcBzVny+9aSArtOKZBGhFOpiND8bbKZ+ijcM8nJh8kDhY",
"integrity": "sha384-2G+cCKCLOG56Rwg0sa46ImGAqQsk28HLULlHYz/MwbDrkdZDWtSuMgkrwGOJ+oCa",
"elements": [
"prayer-walk-planner"
],
@ -879,7 +879,7 @@
"scriptUrl": "./prayer-walk-planner/prayer-walk-planner.js",
"embed": {
"iframe": "<iframe src=\"./prayer-walk-planner/prayer-walk-planner/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./prayer-walk-planner/prayer-walk-planner.js\" integrity=\"sha384-WPlrs8XIyGgif3VVs+wjcBzVny+9aSArtOKZBGhFOpiND8bbKZ+ijcM8nJh8kDhY\" crossorigin=\"anonymous\"></script>\n<prayer-walk-planner profile-config='{\"profile\":\"prayer-walk-planner\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></prayer-walk-planner>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./prayer-walk-planner/prayer-walk-planner.js\" integrity=\"sha384-2G+cCKCLOG56Rwg0sa46ImGAqQsk28HLULlHYz/MwbDrkdZDWtSuMgkrwGOJ+oCa\" crossorigin=\"anonymous\"></script>\n<prayer-walk-planner profile-config='{\"profile\":\"prayer-walk-planner\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></prayer-walk-planner>"
}
}
]
@ -888,7 +888,7 @@
"bundle": "regions-dashboard",
"scriptUrl": "./regions-dashboard/regions-dashboard.js",
"output": "doxa-maps/regions-dashboard/regions-dashboard.js",
"integrity": "sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c",
"integrity": "sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5",
"elements": [
"regions-dashboard"
],
@ -908,7 +908,7 @@
"scriptUrl": "./regions-dashboard/regions-dashboard.js",
"embed": {
"iframe": "<iframe src=\"./regions-dashboard/region-dashboards/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"region-dashboards\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"region-dashboards\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
}
},
{
@ -922,7 +922,7 @@
"scriptUrl": "./regions-dashboard/regions-dashboard.js",
"embed": {
"iframe": "<iframe src=\"./regions-dashboard/regions-list/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"regions-list\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"regions-list\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
}
},
{
@ -936,7 +936,7 @@
"scriptUrl": "./regions-dashboard/regions-dashboard.js",
"embed": {
"iframe": "<iframe src=\"./regions-dashboard/regions-mfe/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"regions-mfe\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./regions-dashboard/regions-dashboard.js\" integrity=\"sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5\" crossorigin=\"anonymous\"></script>\n<regions-dashboard profile-config='{\"profile\":\"regions-mfe\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></regions-dashboard>"
}
}
]
@ -945,7 +945,7 @@
"bundle": "research-dashboard",
"scriptUrl": "./research-dashboard/research-dashboard.js",
"output": "doxa-maps/research-dashboard/research-dashboard.js",
"integrity": "sha384-/cNWbEog9InaGevwn9Ar08H1bRBIWKKtoF/3ZTCNRfzabRPZUY0K1YlrzvQeAcXD",
"integrity": "sha384-LmHOyS5GYBnyavuyb+Kmd8czZ+D9zr7JavLH9WuerdgS1cmx2ZYqxiH6XCRNTk3b",
"elements": [
"research-dashboard-map"
],
@ -961,7 +961,7 @@
"scriptUrl": "./research-dashboard/research-dashboard.js",
"embed": {
"iframe": "<iframe src=\"./research-dashboard/research-dashboard/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./research-dashboard/research-dashboard.js\" integrity=\"sha384-/cNWbEog9InaGevwn9Ar08H1bRBIWKKtoF/3ZTCNRfzabRPZUY0K1YlrzvQeAcXD\" crossorigin=\"anonymous\"></script>\n<research-dashboard-map profile-config='{\"profile\":\"research-dashboard\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></research-dashboard-map>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./research-dashboard/research-dashboard.js\" integrity=\"sha384-LmHOyS5GYBnyavuyb+Kmd8czZ+D9zr7JavLH9WuerdgS1cmx2ZYqxiH6XCRNTk3b\" crossorigin=\"anonymous\"></script>\n<research-dashboard-map profile-config='{\"profile\":\"research-dashboard\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></research-dashboard-map>"
},
"bundle": "research-dashboard"
}
@ -971,7 +971,7 @@
"bundle": "research-map-plus-grid",
"scriptUrl": "./research-map-plus-grid/research-map-plus-grid.js",
"output": "doxa-maps/research-map-plus-grid/research-map-plus-grid.js",
"integrity": "sha384-QF8HNGDjuEGTpVgkTEayOohmab9QdwnO5jLCoEy9P8nr6Zp7JWKrMC5mvDPBOXhB",
"integrity": "sha384-hETnSGVenHXQXaI+EUClxIoaB0xyA9jHa3AaZE6grq4UHxTuX0QNZj93mAUi3H7b",
"elements": [
"research-map-plus-grid"
],
@ -991,7 +991,7 @@
"scriptUrl": "./research-map-plus-grid/research-map-plus-grid.js",
"embed": {
"iframe": "<iframe src=\"./research-map-plus-grid/research-map-plus-grid/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./research-map-plus-grid/research-map-plus-grid.js\" integrity=\"sha384-QF8HNGDjuEGTpVgkTEayOohmab9QdwnO5jLCoEy9P8nr6Zp7JWKrMC5mvDPBOXhB\" crossorigin=\"anonymous\"></script>\n<research-map-plus-grid profile-config='{\"profile\":\"research-map-plus-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></research-map-plus-grid>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./research-map-plus-grid/research-map-plus-grid.js\" integrity=\"sha384-hETnSGVenHXQXaI+EUClxIoaB0xyA9jHa3AaZE6grq4UHxTuX0QNZj93mAUi3H7b\" crossorigin=\"anonymous\"></script>\n<research-map-plus-grid profile-config='{\"profile\":\"research-map-plus-grid\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></research-map-plus-grid>"
},
"instances": [
{
@ -1015,7 +1015,7 @@
"bundle": "stack-demo",
"scriptUrl": "./stack-demo/stack-demo.js",
"output": "doxa-maps/stack-demo/stack-demo.js",
"integrity": "sha384-EI3V6JX9ws4fGxKBzMOgwhG5de8MvL6va3zqmB2gTXecd/m0mxNq8eUht/SGzH1B",
"integrity": "sha384-3Rjk4pZDcTABDfBIAbT2tu+D6J9/U3jx3UJDkiPynH+oeiwzCGFotSX7hbhdT48G",
"elements": [
"stack-demo"
],
@ -1035,7 +1035,7 @@
"scriptUrl": "./stack-demo/stack-demo.js",
"embed": {
"iframe": "<iframe src=\"./stack-demo/stack-demo/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./stack-demo/stack-demo.js\" integrity=\"sha384-EI3V6JX9ws4fGxKBzMOgwhG5de8MvL6va3zqmB2gTXecd/m0mxNq8eUht/SGzH1B\" crossorigin=\"anonymous\"></script>\n<stack-demo profile-config='{\"profile\":\"stack-demo\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></stack-demo>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./stack-demo/stack-demo.js\" integrity=\"sha384-3Rjk4pZDcTABDfBIAbT2tu+D6J9/U3jx3UJDkiPynH+oeiwzCGFotSX7hbhdT48G\" crossorigin=\"anonymous\"></script>\n<stack-demo profile-config='{\"profile\":\"stack-demo\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></stack-demo>"
},
"instances": [
{
@ -1059,7 +1059,7 @@
"bundle": "upg-neighbor",
"scriptUrl": "./upg-neighbor/upg-neighbor.js",
"output": "doxa-maps/upg-neighbor/upg-neighbor.js",
"integrity": "sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D",
"integrity": "sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8",
"elements": [
"upg-neighbor"
],
@ -1075,7 +1075,7 @@
"scriptUrl": "./upg-neighbor/upg-neighbor.js",
"embed": {
"iframe": "<iframe src=\"./upg-neighbor/upg-neighbor/index.html?utm_source=YOUR_SOURCE\" width=\"100%\" height=\"600\" style=\"border:none;border-radius:12px;\" allowfullscreen></iframe>",
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./upg-neighbor/upg-neighbor.js\" integrity=\"sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D\" crossorigin=\"anonymous\"></script>\n<upg-neighbor profile-config='{\"profile\":\"upg-neighbor\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></upg-neighbor>"
"script": "<script>window.MAP_APP_API_URL=\"https://pray.doxa.life\";</script>\n<script src=\"./upg-neighbor/upg-neighbor.js\" integrity=\"sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8\" crossorigin=\"anonymous\"></script>\n<upg-neighbor profile-config='{\"profile\":\"upg-neighbor\",\"tk\":\"YOUR_MAPBOX_TOKEN\",\"utmSource\":\"YOUR_SOURCE\",\"assetsBase\":\"YOUR_TREE_URL/assets\"}'></upg-neighbor>"
},
"instances": [
{

File diff suppressed because one or more lines are too long

View file

@ -26,7 +26,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <people-groups-grid> custom element. -->
<script src="../../people-groups-grid.js" integrity="sha384-X3qjp89Dxlr8VW4cX0it+SuREyzXCeVDAba1YrKMyk7XWmlkFSpjLYNa2g6R5q4p" crossorigin="anonymous"></script>
<script src="../../people-groups-grid.js" integrity="sha384-SOgJZ7f+syLHYLSe0ZS99wYotonfFOt3imsoeiw1qpdqNPpdBOl/1mm0Kp+YNTFl" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -26,7 +26,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <people-groups-grid> custom element. -->
<script src="../people-groups-grid.js" integrity="sha384-X3qjp89Dxlr8VW4cX0it+SuREyzXCeVDAba1YrKMyk7XWmlkFSpjLYNa2g6R5q4p" crossorigin="anonymous"></script>
<script src="../people-groups-grid.js" integrity="sha384-SOgJZ7f+syLHYLSe0ZS99wYotonfFOt3imsoeiw1qpdqNPpdBOl/1mm0Kp+YNTFl" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -26,7 +26,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <people-groups-grid> custom element. -->
<script src="../../people-groups-grid.js" integrity="sha384-X3qjp89Dxlr8VW4cX0it+SuREyzXCeVDAba1YrKMyk7XWmlkFSpjLYNa2g6R5q4p" crossorigin="anonymous"></script>
<script src="../../people-groups-grid.js" integrity="sha384-SOgJZ7f+syLHYLSe0ZS99wYotonfFOt3imsoeiw1qpdqNPpdBOl/1mm0Kp+YNTFl" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <pplr-data-maps> custom element. -->
<script src="../pplr-data-maps.js" integrity="sha384-u04GVRZqNXyBqfkyvCtm9IT6/RWbJTNTxTpv6ScsnE/5za+UIlTjAoZKIn9k2Zp3" crossorigin="anonymous"></script>
<script src="../pplr-data-maps.js" integrity="sha384-ARe/uZNMZehT22F9YI0tOasG9ay59Rdt4+x5wxlwFJZObTps4/+L6UwGq6G1yBG/" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <prayer-walk-planner> custom element. -->
<script src="../prayer-walk-planner.js" integrity="sha384-WPlrs8XIyGgif3VVs+wjcBzVny+9aSArtOKZBGhFOpiND8bbKZ+ijcM8nJh8kDhY" crossorigin="anonymous"></script>
<script src="../prayer-walk-planner.js" integrity="sha384-2G+cCKCLOG56Rwg0sa46ImGAqQsk28HLULlHYz/MwbDrkdZDWtSuMgkrwGOJ+oCa" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <regions-dashboard> custom element. -->
<script src="../regions-dashboard.js" integrity="sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c" crossorigin="anonymous"></script>
<script src="../regions-dashboard.js" integrity="sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <regions-dashboard> custom element. -->
<script src="../regions-dashboard.js" integrity="sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c" crossorigin="anonymous"></script>
<script src="../regions-dashboard.js" integrity="sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -40,7 +40,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <regions-dashboard> custom element. -->
<script src="../regions-dashboard.js" integrity="sha384-DClm3BV580b9LYTon03X8XJD4uza6w2fKBPQTMpeIugtHgyqZXqpoCg88c+d6i1c" crossorigin="anonymous"></script>
<script src="../regions-dashboard.js" integrity="sha384-13XAnTeIg8uMelj4GVTXRAO0hO4noWL8fIaOQ2fMuz7T0TVsEOkb2dAkQ5HIA5Z5" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <research-dashboard-map> custom element. -->
<script src="../research-dashboard.js" integrity="sha384-/cNWbEog9InaGevwn9Ar08H1bRBIWKKtoF/3ZTCNRfzabRPZUY0K1YlrzvQeAcXD" crossorigin="anonymous"></script>
<script src="../research-dashboard.js" integrity="sha384-LmHOyS5GYBnyavuyb+Kmd8czZ+D9zr7JavLH9WuerdgS1cmx2ZYqxiH6XCRNTk3b" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <research-map-plus-grid> custom element. -->
<script src="../../research-map-plus-grid.js" integrity="sha384-QF8HNGDjuEGTpVgkTEayOohmab9QdwnO5jLCoEy9P8nr6Zp7JWKrMC5mvDPBOXhB" crossorigin="anonymous"></script>
<script src="../../research-map-plus-grid.js" integrity="sha384-hETnSGVenHXQXaI+EUClxIoaB0xyA9jHa3AaZE6grq4UHxTuX0QNZj93mAUi3H7b" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <research-map-plus-grid> custom element. -->
<script src="../research-map-plus-grid.js" integrity="sha384-QF8HNGDjuEGTpVgkTEayOohmab9QdwnO5jLCoEy9P8nr6Zp7JWKrMC5mvDPBOXhB" crossorigin="anonymous"></script>
<script src="../research-map-plus-grid.js" integrity="sha384-hETnSGVenHXQXaI+EUClxIoaB0xyA9jHa3AaZE6grq4UHxTuX0QNZj93mAUi3H7b" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -44,4 +44,4 @@
.stl ::-webkit-scrollbar-thumb { background:#c4c8c0; border-radius:8px; }
.stl ::-webkit-scrollbar-thumb:hover { background:#9aa197; }
.stl ::-webkit-scrollbar-corner { background:transparent; }
`,ql=ei({name:"StackLayout",props:{sections:{type:Array,default:()=>[]},title:{type:String,default:""},maxSectionHeight:{type:String,default:""},minSectionHeight:{type:String,default:""}},setup(){$l(zl,"stack-layout")},data(){return{_hosts:{},_mounted:{}}},mounted(){for(const t of this.sections||[])t.element&&this.mountSection(t)},methods:{registerHost(t,e){e&&(this._hosts[t]=e)},sectionStyle(t){const e={},s=t.maxHeight||this.maxSectionHeight,n=t.minHeight||this.minSectionHeight,i=!!(s&&n&&s===n);return s&&(e.maxHeight=s,i||(e.overflow="auto")),n&&(e.minHeight=n),Object.keys(e).length?e:null},hasDefiniteHeight(t){const e=t.maxHeight||this.maxSectionHeight,s=t.minHeight||this.minSectionHeight;return!!(e&&s&&e===s)},mountSection(t){if(this._mounted[t.key])return;this._mounted[t.key]=!0;const e=this._hosts[t.key];e&&Bl(t.src).then(()=>Wl(t.element)).then(()=>{if(!customElements.get(t.element))return;const s=document.createElement(t.element),n=t.attrs||{};for(const i in n){const r=n[i];try{s[i]=r}catch{}try{s.setAttribute(i,r==null?"":String(r))}catch{}}e.innerHTML="",e.appendChild(s)}).catch(s=>{const n=s&&s.message||String(s);console.error('[StackLayout] section "'+t.key+'" failed to mount <'+t.element+">"+(t.src?" from "+t.src:"")+": "+n);try{e.innerHTML="";const i=document.createElement("div");i.setAttribute("role","status"),i.style.cssText="box-sizing:border-box;max-width:100%;padding:16px;font:13px/1.5 ui-monospace,SFMono-Regular,Menlo,monospace;color:#6d766e;background:#fff;border:1px solid #d1d4cd;border-radius:8px;margin:12px 0;overflow-wrap:anywhere;word-break:break-word",i.textContent="Could not load <"+t.element+">"+(t.src?" from "+t.src:"")+" — "+n,e.appendChild(i)}catch{}})}}}),Jl={class:"stl"},Gl={key:0,class:"stl-top"},Yl={class:"stl-brand"},Xl={key:0,class:"stl-title"},Zl={class:"stl-meta"},Ql={class:"stl-stack"},tc={key:0,class:"stl-sec-head"},ec={class:"stl-sec-title"},sc={key:0,class:"stl-sec-sub"},nc={key:2,class:"stl-slot"},ic={class:"stl-tail"};function rc(t,e,s,n,i,r){return ut(),kt("div",Jl,[t.$slots.brand||t.$slots.meta||t.title?(ut(),kt("header",Gl,[Xt("span",Yl,[is(t.$slots,"brand")]),t.title?(ut(),kt("b",Xl,Ke(t.title),1)):us("",!0),Xt("span",Zl,[is(t.$slots,"meta")])])):us("",!0),Xt("div",Ql,[(ut(!0),kt(ct,null,So(t.sections,o=>(ut(),kt("section",{key:o.key,class:Ve(["stl-sec",{"stl-sec-fill":t.hasDefiniteHeight(o)}]),style:Le(t.sectionStyle(o))},[o.title?(ut(),kt("div",tc,[Xt("b",ec,Ke(o.title),1),o.sub?(ut(),kt("span",sc,Ke(o.sub),1)):us("",!0)])):us("",!0),o.element?(ut(),kt("div",{key:1,class:"stl-host",ref_for:!0,ref:l=>t.registerHost(o.key,l)},null,512)):(ut(),kt("div",nc,[is(t.$slots,"section-"+o.key)]))],6))),128)),Xt("div",ic,[is(t.$slots,"default")])])])}const oc=ir(ql,[["render",rc],["styles",[Ul]]]),rr="__doxaMapToken",lc="doxa:map-token",or=()=>{if(typeof window>"u")return"";const t=window[rr];return typeof t=="string"?t:""};function cc(t){if(typeof window>"u")return"";const e=typeof t=="string"?t.trim():"";if(!e||e===or())return or();window[rr]=e;try{window.dispatchEvent(new CustomEvent(lc,{detail:e}))}catch{}return e}const fc=Fl(ir({__name:"stack-demo",props:{profileConfig:{type:[String,Object],default:null}},setup(t){const e=(l,c)=>`../../${l}/${c}.js`,s=t,n=Ee(()=>{const l=s.profileConfig;if(!l)return{};if(typeof l=="object")return l;try{return JSON.parse(l)}catch{return{}}}),i=Ee(()=>{var c;const l=(c=n.value)==null?void 0:c.tk;return typeof l=="string"&&l?l:""});i.value&&cc(i.value);const r=Ee(()=>{var c;const l=(c=n.value)==null?void 0:c.provider;return l==="maplibre"||l==="mapbox"?l:""}),o=Ee(()=>[{key:"dashboard",title:"Research Dashboard",sub:"facets · map · charts · table (live)",element:"research-dashboard-map",src:e("research-dashboard","research-dashboard"),attrs:{"profile-config":JSON.stringify({profile:"research-dashboard",dataSource:"pray-tools",instanceId:"stack-demo-research-dashboard",...i.value?{tk:i.value}:{},...r.value?{provider:r.value}:{},assetsBase:"../../assets"})}},{key:"grid",title:"People Groups",sub:"the full searchable list (live)",element:"people-groups-grid",src:e("people-groups-grid","people-groups-grid")}]);return(l,c)=>(ut(),cs(oc,{title:"Stacked view",sections:o.value},{meta:Xn(()=>[...c[0]||(c[0]=[ji("scroll ↓",-1)])]),_:1},8,["sections"]))}},[["styles",[":host{display:block;width:100%}"]]]));typeof customElements<"u"&&(customElements.get("stack-demo")||customElements.define("stack-demo",fc))})();
`,ql=ei({name:"StackLayout",props:{sections:{type:Array,default:()=>[]},title:{type:String,default:""},maxSectionHeight:{type:String,default:""},minSectionHeight:{type:String,default:""}},setup(){$l(zl,"stack-layout")},data(){return{_hosts:{},_mounted:{}}},mounted(){for(const t of this.sections||[])t.element&&this.mountSection(t)},methods:{registerHost(t,e){e&&(this._hosts[t]=e)},sectionStyle(t){const e={},s=t.maxHeight||this.maxSectionHeight,n=t.minHeight||this.minSectionHeight,i=!!(s&&n&&s===n);return s&&(e.maxHeight=s,i||(e.overflow="auto")),n&&(e.minHeight=n),Object.keys(e).length?e:null},hasDefiniteHeight(t){const e=t.maxHeight||this.maxSectionHeight,s=t.minHeight||this.minSectionHeight;return!!(e&&s&&e===s)},mountSection(t){if(this._mounted[t.key])return;this._mounted[t.key]=!0;const e=this._hosts[t.key];e&&Bl(t.src).then(()=>Wl(t.element)).then(()=>{if(!customElements.get(t.element))return;const s=document.createElement(t.element),n=t.attrs||{};for(const i in n){const r=n[i];try{s[i]=r}catch{}try{s.setAttribute(i,r==null?"":String(r))}catch{}}e.innerHTML="",e.appendChild(s)}).catch(s=>{const n=s&&s.message||String(s);console.error('[StackLayout] section "'+t.key+'" failed to mount <'+t.element+">"+(t.src?" from "+t.src:"")+": "+n);try{e.innerHTML="";const i=document.createElement("div");i.setAttribute("role","status"),i.style.cssText="box-sizing:border-box;max-width:100%;padding:16px;font:13px/1.5 ui-monospace,SFMono-Regular,Menlo,monospace;color:#6d766e;background:#fff;border:1px solid #d1d4cd;border-radius:8px;margin:12px 0;overflow-wrap:anywhere;word-break:break-word",i.textContent="Could not load <"+t.element+">"+(t.src?" from "+t.src:"")+" — "+n,e.appendChild(i)}catch{}})}}}),Jl={class:"stl"},Gl={key:0,class:"stl-top"},Yl={class:"stl-brand"},Xl={key:0,class:"stl-title"},Zl={class:"stl-meta"},Ql={class:"stl-stack"},tc={key:0,class:"stl-sec-head"},ec={class:"stl-sec-title"},sc={key:0,class:"stl-sec-sub"},nc={key:2,class:"stl-slot"},ic={class:"stl-tail"};function rc(t,e,s,n,i,r){return ut(),kt("div",Jl,[t.$slots.brand||t.$slots.meta||t.title?(ut(),kt("header",Gl,[Xt("span",Yl,[is(t.$slots,"brand")]),t.title?(ut(),kt("b",Xl,Ke(t.title),1)):us("",!0),Xt("span",Zl,[is(t.$slots,"meta")])])):us("",!0),Xt("div",Ql,[(ut(!0),kt(ct,null,So(t.sections,o=>(ut(),kt("section",{key:o.key,class:Ve(["stl-sec",{"stl-sec-fill":t.hasDefiniteHeight(o)}]),style:Le(t.sectionStyle(o))},[o.title?(ut(),kt("div",tc,[Xt("b",ec,Ke(o.title),1),o.sub?(ut(),kt("span",sc,Ke(o.sub),1)):us("",!0)])):us("",!0),o.element?(ut(),kt("div",{key:1,class:"stl-host",ref_for:!0,ref:l=>t.registerHost(o.key,l)},null,512)):(ut(),kt("div",nc,[is(t.$slots,"section-"+o.key)]))],6))),128)),Xt("div",ic,[is(t.$slots,"default")])])])}const oc=ir(ql,[["render",rc],["styles",[Ul]]]),rr="__doxaMapToken",lc="doxa:map-token",or=()=>{if(typeof window>"u")return"";const t=window[rr];return typeof t=="string"?t:""};function cc(t){if(typeof window>"u")return"";const e=typeof t=="string"?t.trim():"";if(!e||e===or())return or();window[rr]=e;try{window.dispatchEvent(new CustomEvent(lc,{detail:e}))}catch{}return e}const fc=Fl(ir(Object.assign({inheritAttrs:!1},{__name:"stack-demo",props:{profileConfig:{type:[String,Object],default:null}},setup(t){const e=(l,c)=>`../../${l}/${c}.js`,s=t,n=Ee(()=>{const l=s.profileConfig;if(!l)return{};if(typeof l=="object")return l;try{return JSON.parse(l)}catch{return{}}}),i=Ee(()=>{var c;const l=(c=n.value)==null?void 0:c.tk;return typeof l=="string"&&l?l:""});i.value&&cc(i.value);const r=Ee(()=>{var c;const l=(c=n.value)==null?void 0:c.provider;return l==="maplibre"||l==="mapbox"?l:""}),o=Ee(()=>[{key:"dashboard",title:"Research Dashboard",sub:"facets · map · charts · table (live)",element:"research-dashboard-map",src:e("research-dashboard","research-dashboard"),attrs:{"profile-config":JSON.stringify({profile:"research-dashboard",dataSource:"pray-tools",instanceId:"stack-demo-research-dashboard",...i.value?{tk:i.value}:{},...r.value?{provider:r.value}:{},assetsBase:"../../assets"})}},{key:"grid",title:"People Groups",sub:"the full searchable list (live)",element:"people-groups-grid",src:e("people-groups-grid","people-groups-grid")}]);return(l,c)=>(ut(),cs(oc,{title:"Stacked view",sections:o.value},{meta:Xn(()=>[...c[0]||(c[0]=[ji("scroll ↓",-1)])]),_:1},8,["sections"]))}}),[["styles",[":host{display:block;width:100%}"]]]));typeof customElements<"u"&&(customElements.get("stack-demo")||customElements.define("stack-demo",fc))})();

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <stack-demo> custom element. -->
<script src="../stack-demo.js" integrity="sha384-EI3V6JX9ws4fGxKBzMOgwhG5de8MvL6va3zqmB2gTXecd/m0mxNq8eUht/SGzH1B" crossorigin="anonymous"></script>
<script src="../stack-demo.js" integrity="sha384-3Rjk4pZDcTABDfBIAbT2tu+D6J9/U3jx3UJDkiPynH+oeiwzCGFotSX7hbhdT48G" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -37,7 +37,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <stack-demo> custom element. -->
<script src="../../stack-demo.js" integrity="sha384-EI3V6JX9ws4fGxKBzMOgwhG5de8MvL6va3zqmB2gTXecd/m0mxNq8eUht/SGzH1B" crossorigin="anonymous"></script>
<script src="../../stack-demo.js" integrity="sha384-3Rjk4pZDcTABDfBIAbT2tu+D6J9/U3jx3UJDkiPynH+oeiwzCGFotSX7hbhdT48G" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

File diff suppressed because one or more lines are too long

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order:

View file

@ -29,7 +29,7 @@
<script>window.MAP_APP_API_URL = "https://pray.doxa.life";</script>
<!-- Bundle IIFE — registers the <upg-neighbor> custom element. -->
<script src="../../upg-neighbor.js" integrity="sha384-sE35m8x3cE7I+dIJBRekLFr7/7C81p6ohDN/LpV6VjVKXkPaDKwtNj7Yt8f/hB+D" crossorigin="anonymous"></script>
<script src="../../upg-neighbor.js" integrity="sha384-RjeHRKWYHkHQFAtuZbQJwoPlDZofDa2/hReWM3GVlzD+1lk/NKcwtBEPWohKKqs8" crossorigin="anonymous"></script>
<script>
// Mapbox token resolution — the A3 ladder, in precedence order: