@@ -119,24 +119,34 @@ db = {
119119}
120120```
121121
122- <div class =" legend " >
122+ ``` {ojs}
123+ //| echo: false
124+ // Render legend and stats bar from OJS so they're in the DOM before phase1 runs
125+ legend_html = html`<div class="legend">
123126 <strong>Source:</strong>
124127 <span class="legend-item"><span class="legend-dot" style="background:#3366CC"></span> SESAR</span>
125128 <span class="legend-item"><span class="legend-dot" style="background:#DC3912"></span> OpenContext</span>
126129 <span class="legend-item"><span class="legend-dot" style="background:#109618"></span> GEOME</span>
127130 <span class="legend-item"><span class="legend-dot" style="background:#FF9900"></span> Smithsonian</span>
128- </div >
131+ </div>`
132+ ```
129133
130- <div id =" statsBar " class =" stats-bar " >
134+ ``` {ojs}
135+ //| echo: false
136+ statsBar = html`<div class="stats-bar">
131137 <span class="stat"><span class="stat-label">Phase:</span> <span id="statPhase" class="stat-value">Loading...</span></span>
132138 <span class="stat"><span class="stat-label">Points:</span> <span id="statPoints" class="stat-value">0</span></span>
133139 <span class="stat"><span class="stat-label">Samples:</span> <span id="statSamples" class="stat-value">0</span></span>
134140 <span class="stat"><span class="stat-label">Time:</span> <span id="statTime" class="stat-value">-</span></span>
135- </div >
141+ </div>`
142+ ```
136143
137- <div id =" phaseIndicator " class =" phase-indicator " style =" background : #e3f2fd ; color : #1565c0 ;" >
144+ ``` {ojs}
145+ //| echo: false
146+ phaseIndicatorEl = html`<div id="phaseIndicator" class="phase-indicator" style="background: #e3f2fd; color: #1565c0;">
138147 Phase 1: Loading H3 global overview (580 KB)...
139- </div >
148+ </div>`
149+ ```
140150
141151::: {.panel-tabset}
142152
@@ -343,13 +353,18 @@ viewer = {
343353
344354// === PHASE 1: Load H3 res4 aggregates (instant) ===
345355phase1 = {
356+ // Ensure OJS-rendered DOM elements are available
357+ void statsBar;
358+ void phaseIndicatorEl;
359+
346360 performance.mark('phase1-start');
347361
348362 const updateStats = (phase, points, samples, time) => {
349- document.getElementById('statPhase').textContent = phase;
350- document.getElementById('statPoints').textContent = points.toLocaleString();
351- document.getElementById('statSamples').textContent = samples.toLocaleString();
352- document.getElementById('statTime').textContent = time;
363+ const el = (id) => document.getElementById(id);
364+ if (el('statPhase')) el('statPhase').textContent = phase;
365+ if (el('statPoints')) el('statPoints').textContent = points.toLocaleString();
366+ if (el('statSamples')) el('statSamples').textContent = samples.toLocaleString();
367+ if (el('statTime')) el('statTime').textContent = time;
353368 };
354369
355370 const indicator = document.getElementById('phaseIndicator');
@@ -420,8 +435,10 @@ phase1 = {
420435// === PHASE 2: Zoom-triggered detail loading ===
421436// Monitor camera height and load finer resolution when zoomed in
422437zoomWatcher = {
423- // Wait for phase 1 to complete
438+ // Wait for phase 1 to complete and DOM to be ready
424439 if (!phase1) return;
440+ void statsBar;
441+ void phaseIndicatorEl;
425442
426443 let currentResolution = 4;
427444 let loadingRes = false;
@@ -501,10 +518,11 @@ zoomWatcher = {
501518 performance.measure(`res${res}-total`, `res${res}-start`, `res${res}-end`);
502519 const elapsed = performance.getEntriesByName(`res${res}-total`)[0].duration;
503520
504- document.getElementById('statPhase').textContent = `H3 Res${res}`;
505- document.getElementById('statPoints').textContent = data.length.toLocaleString();
506- document.getElementById('statSamples').textContent = totalSamples.toLocaleString();
507- document.getElementById('statTime').textContent = `${(elapsed/1000).toFixed(1)}s`;
521+ const el = (id) => document.getElementById(id);
522+ if (el('statPhase')) el('statPhase').textContent = `H3 Res${res}`;
523+ if (el('statPoints')) el('statPoints').textContent = data.length.toLocaleString();
524+ if (el('statSamples')) el('statSamples').textContent = totalSamples.toLocaleString();
525+ if (el('statTime')) el('statTime').textContent = `${(elapsed/1000).toFixed(1)}s`;
508526
509527 if (indicator) {
510528 indicator.style.background = '#e8f5e9';
0 commit comments