The spectrum chart was missing xMin/xMax persistence and data boundary clamping in enablePan(). Align with the background/cps chart patterns. Bump cache versions to force browser refresh. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
118 lines
4.4 KiB
JavaScript
118 lines
4.4 KiB
JavaScript
const API_BASE = '';
|
|
let refreshInterval = null;
|
|
const REFRESH_MS = 30000; // 30 seconds
|
|
|
|
// Load detector config
|
|
const DETECTOR_CONFIG = {};
|
|
async function loadDetectorConfig() {
|
|
try {
|
|
const resp = await fetch(`${API_BASE}/static/js/detectors.json`);
|
|
if (!resp.ok) return;
|
|
const data = await resp.json();
|
|
Object.assign(DETECTOR_CONFIG, data);
|
|
if (DETECTOR_CONFIG.default) {
|
|
const d = DETECTOR_CONFIG.detectors[DETECTOR_CONFIG.default]?.display || {};
|
|
Object.assign(DETECTOR_CONFIG, d);
|
|
// Apply default chart settings from config
|
|
if (typeof d.default_log_scale === 'boolean') {
|
|
const el = document.getElementById('log-scale');
|
|
if (el) el.checked = d.default_log_scale;
|
|
const el2 = document.getElementById('bg-scale-log');
|
|
if (el2) el2.checked = d.default_log_scale;
|
|
}
|
|
if (typeof d.default_smooth === 'boolean') {
|
|
const el = document.getElementById('show-bg-smooth');
|
|
if (el) el.checked = d.default_smooth;
|
|
}
|
|
}
|
|
} catch { /* use defaults */ }
|
|
}
|
|
loadDetectorConfig();
|
|
|
|
// Tab navigation
|
|
document.querySelectorAll('nav a').forEach(link => {
|
|
link.addEventListener('click', e => {
|
|
e.preventDefault();
|
|
const tab = link.dataset.tab;
|
|
document.querySelectorAll('.tab').forEach(t => t.classList.remove('active'));
|
|
document.querySelectorAll('.tab-content').forEach(t => t.classList.remove('active'));
|
|
link.classList.add('active');
|
|
document.getElementById(`tab-${tab}`).classList.add('active');
|
|
// Refresh the active tab
|
|
if (tab === 'spectrum') refreshSpectrum();
|
|
if (tab === 'background') refreshBackground();
|
|
if (tab === 'cps') loadCps(24);
|
|
});
|
|
});
|
|
|
|
// Status bar refresh
|
|
async function refreshStatus() {
|
|
try {
|
|
const resp = await fetch(`${API_BASE}/api/status`);
|
|
if (!resp.ok) {
|
|
document.getElementById('status-connected').className = 'status-dot';
|
|
return;
|
|
}
|
|
const data = await resp.json();
|
|
const dot = document.getElementById('status-connected');
|
|
const ok = data.connected && !data.stale;
|
|
dot.className = ok ? 'status-dot connected' : 'status-dot';
|
|
document.getElementById('status-cps').textContent = `${data.cps.toFixed(1)} CPS`;
|
|
document.getElementById('status-live-time').textContent = `${data.cumulated_live_time_h.toFixed(1)} h`;
|
|
document.title = ok
|
|
? `${data.cps.toFixed(1)} CPS · ${data.cumulated_live_time_h.toFixed(1)}h`
|
|
: 'Hors ligne';
|
|
} catch {
|
|
document.getElementById('status-connected').className = 'status-dot';
|
|
}
|
|
}
|
|
|
|
// Auto-refresh
|
|
function startRefresh() {
|
|
refreshStatus();
|
|
refreshSpectrum();
|
|
refreshInterval = setInterval(() => {
|
|
refreshStatus();
|
|
const activeTab = document.querySelector('.tab.active')?.dataset.tab;
|
|
if (activeTab === 'spectrum') refreshSpectrum();
|
|
}, REFRESH_MS);
|
|
}
|
|
|
|
// Isotope lines toggle — show/hide "detected only" checkbox
|
|
document.getElementById('show-isotope-lines').addEventListener('change', (e) => {
|
|
document.getElementById('lines-detected-label').style.display = e.target.checked ? 'flex' : 'none';
|
|
if (!e.target.checked) refreshSpectrum();
|
|
});
|
|
|
|
// Fullscreen toggle for charts
|
|
function exitFullscreen() {
|
|
document.querySelectorAll('.chart-container.fullscreen').forEach(c => c.classList.remove('fullscreen'));
|
|
document.querySelectorAll('.fullscreen-btn, #fullscreen-btn').forEach(btn => btn.innerHTML = '⛶');
|
|
setTimeout(() => window.dispatchEvent(new Event('resize')), 100);
|
|
}
|
|
|
|
document.querySelectorAll('.fullscreen-btn, #fullscreen-btn').forEach(btn => {
|
|
btn.addEventListener('click', () => {
|
|
const container = btn.closest('section').querySelector('.chart-container');
|
|
if (container.classList.contains('fullscreen')) {
|
|
exitFullscreen();
|
|
} else {
|
|
container.classList.add('fullscreen');
|
|
btn.innerHTML = '✕';
|
|
setTimeout(() => window.dispatchEvent(new Event('resize')), 100);
|
|
}
|
|
});
|
|
});
|
|
|
|
// Exit fullscreen buttons inside chart containers
|
|
document.querySelectorAll('.exit-fullscreen-btn').forEach(btn => {
|
|
btn.addEventListener('click', exitFullscreen);
|
|
});
|
|
|
|
// ESC to exit fullscreen
|
|
document.addEventListener('keydown', (e) => {
|
|
if (e.key === 'Escape') exitFullscreen();
|
|
});
|
|
|
|
// Initialize — called after all scripts are loaded
|
|
window.addEventListener('load', startRefresh); |