From 7e50c534811ad0554b51ddb31fd91564593f52c7 Mon Sep 17 00:00:00 2001 From: Mika Date: Sat, 24 Jan 2026 12:03:27 +0000 Subject: [PATCH] Add visualization_tool/js/ui.js --- visualization_tool/js/ui.js | 109 ++++++++++++++++++++++++++++++++++++ 1 file changed, 109 insertions(+) create mode 100644 visualization_tool/js/ui.js diff --git a/visualization_tool/js/ui.js b/visualization_tool/js/ui.js new file mode 100644 index 0000000..7bd81c9 --- /dev/null +++ b/visualization_tool/js/ui.js @@ -0,0 +1,109 @@ +/* ui.js - UI Renderer for Frozen Runs Visualization */ + +/** + * Zeichnet Bootstrap-Verteilungen und CI-Diagramme für die gegebenen Metrikdaten. + * @param {Array} metricsData - Array der Metrikobjekte mit Namen, Run-ID, pinned_flag, Effektgröße und CI. + */ +export function renderCharts(metricsData = []) { + const chartContainer = document.querySelector('#chartsContainer'); + if (!chartContainer) return; + chartContainer.innerHTML = ''; + + metricsData.forEach(metric => { + const { metricName, effectSize, ci_lower, ci_upper } = metric; + const chartEl = document.createElement('div'); + chartEl.className = 'chart-item'; + + const title = document.createElement('h3'); + title.textContent = metricName; + + const canvas = document.createElement('canvas'); + canvas.setAttribute('role', 'img'); + canvas.setAttribute('aria-label', `Bootstrap-Verteilung für ${metricName}`); + + chartEl.appendChild(title); + chartEl.appendChild(canvas); + chartContainer.appendChild(chartEl); + + // Example mock rendering logic (replace with chart lib rendering) + const ctx = canvas.getContext('2d'); + if (ctx) { + ctx.fillStyle = '#cce5ff'; + ctx.fillRect(0, 0, canvas.width, canvas.height); + ctx.fillStyle = '#004085'; + ctx.fillText(`Effektgröße: ${effectSize}`, 10, 20); + ctx.fillText(`CI: [${ci_lower}, ${ci_upper}]`, 10, 40); + } + }); +} + +/** + * Erstellt die Tabellenansicht der Metriken mit Effektgrößen und CI. + * @param {Array} metricsData - Array strukturierter Metrikdaten. + */ +export function renderMetricsTable(metricsData = []) { + const tableContainer = document.querySelector('#metricsTable'); + if (!tableContainer) return; + tableContainer.innerHTML = ''; + + const table = document.createElement('table'); + table.className = 'table table-striped'; + + const thead = document.createElement('thead'); + const headerRow = document.createElement('tr'); + ['Metrik', 'Run-ID', 'Pinned', 'Effektgröße', 'CI Lower', 'CI Upper'].forEach(label => { + const th = document.createElement('th'); + th.textContent = label; + headerRow.appendChild(th); + }); + thead.appendChild(headerRow); + table.appendChild(thead); + + const tbody = document.createElement('tbody'); + metricsData.forEach(row => { + const tr = document.createElement('tr'); + + const tdName = document.createElement('td'); + tdName.textContent = row.metricName; + + const tdRun = document.createElement('td'); + tdRun.textContent = row.run_id ?? '-'; + + const tdPinned = document.createElement('td'); + tdPinned.textContent = row.pinned_flag ? 'pinned' : 'unpinned'; + + const tdEffect = document.createElement('td'); + tdEffect.textContent = row.effectSize; + + const tdCiLow = document.createElement('td'); + tdCiLow.textContent = row.ci_lower; + + const tdCiHigh = document.createElement('td'); + tdCiHigh.textContent = row.ci_upper; + + [tdName, tdRun, tdPinned, tdEffect, tdCiLow, tdCiHigh].forEach(td => tr.appendChild(td)); + tbody.appendChild(tr); + }); + + table.appendChild(tbody); + tableContainer.appendChild(table); +} + +/** + * Aktualisiert Diagramme und Tabellen basierend auf der Filterauswahl. + * @param {string} filter - 'pinned' oder 'unpinned'. + * @param {Array} allMetrics - gesamte Metrikdaten. + */ +export function updateUIOnFilter(filter, allMetrics = []) { + const filtered = allMetrics.filter(m => { + if (filter === 'pinned') return m.pinned_flag; + if (filter === 'unpinned') return !m.pinned_flag; + return true; + }); + + renderCharts(filtered); + renderMetricsTable(filtered); + + const statusEl = document.querySelector('#filterStatus'); + if (statusEl) statusEl.textContent = `Aktueller Filter: ${filter}`; +}