elmadany commited on
Commit
4444a5e
Β·
verified Β·
1 Parent(s): cffe041

Update public/index.html

Browse files
Files changed (1) hide show
  1. public/index.html +62 -50
public/index.html CHANGED
@@ -67,23 +67,10 @@
67
  @keyframes bounce { 0%, 100% { height: 20px; } 50% { height: 120px; } }
68
 
69
  /* --- WIDTH CONTROLLER --- */
70
- .content-container {
71
- width: 80%; /* Fixed 80% width for both cards */
72
- max-width: 1600px; /* Optional cap for very large screens */
73
- margin: 0 auto;
74
- }
75
 
76
  /* --- MAIN BOARD --- */
77
- .main-card {
78
- background: white;
79
- border-radius: 24px;
80
- padding: 40px;
81
- color: #0f172a;
82
- min-height: 600px;
83
- position: relative;
84
- z-index: 10;
85
- margin-bottom: 60px; /* Space between card and citation */
86
- }
87
 
88
  .tabs { display: flex; gap: 10px; border-bottom: 2px solid #e2e8f0; margin-bottom: 30px; padding-bottom: 10px; overflow-x: auto; }
89
  .tab-btn { background: none; border: none; font-size: 15px; font-weight: 600; color: #64748b; padding: 10px 20px; cursor: pointer; transition: 0.3s; border-radius: 8px; white-space: nowrap; }
@@ -109,15 +96,7 @@
109
  h4 { color: var(--text-yellow); font-family: 'Rubik', sans-serif; font-size: 18px; margin: 0 0 15px 0; border-bottom: 1px solid #eee; padding-bottom: 10px; }
110
 
111
  /* Citations */
112
- .citation-section {
113
- background: #0f172a;
114
- border: 1px solid #334155;
115
- border-radius: 16px;
116
- padding: 40px;
117
- box-sizing: border-box;
118
- box-shadow: 0 20px 40px rgba(0,0,0,0.3);
119
- position: relative;
120
- }
121
  .citation-section h3 { color: var(--text-yellow); font-family: 'Rubik', sans-serif; font-size: 24px; margin-top: 0; }
122
  .citation-box { background: #1e293b; color: #cbd5e1; padding: 20px; border-radius: 12px; font-family: monospace; white-space: pre-wrap; margin-top: 20px; overflow-x: auto; border: 1px solid #334155; font-size: 13px; line-height: 1.5; }
123
  .copy-btn { position: absolute; top: 40px; right: 40px; background: var(--text-yellow); border: none; padding: 8px 16px; border-radius: 6px; font-weight: bold; cursor: pointer; color: #0f172a; }
@@ -226,13 +205,13 @@
226
  <select id="lang-select" onchange="renderLanguageView()"></select>
227
  </div>
228
 
229
- <h4>ASR Results <span class="rank-info" style="font-weight:normal;">(Ranked by WER ↓)</span></h4>
230
  <div id="lang-asr-table" class="table-wrap"></div>
231
 
232
- <h4>TTS Results</h4>
233
  <div id="lang-tts-table" class="table-wrap"></div>
234
 
235
- <h4>SLID Results <span class="rank-info" style="font-weight:normal;">(Ranked by Score ↑)</span></h4>
236
  <div id="lang-slid-table" class="table-wrap"></div>
237
  </div>
238
  </div>
@@ -319,16 +298,25 @@
319
  if(n>0) modelStats.push({ name: modName, wer: sW/n, cer: sC/n });
320
  });
321
 
322
- // Tie-Aware Ranking
323
- modelStats.sort((a,b) => a.wer - b.wer);
324
- let rank=1;
325
 
326
  html = `<table><thead><tr><th>Model</th><th>Simba ASR Score (WER/CER) <i class="fa-solid fa-arrow-down arrow-down"></i></th></tr></thead><tbody>`;
327
  modelStats.forEach((m, i) => {
 
328
  if (i > 0 && Math.abs(m.wer - modelStats[i-1].wer) > 0.001) rank = i + 1;
 
329
 
 
 
330
  let icon = '';
331
- if(rank === 1) icon = 'πŸ₯‡ '; else if(rank === 2) icon = 'πŸ₯ˆ '; else if(rank === 3) icon = 'πŸ₯‰ ';
 
 
 
 
 
 
 
332
 
333
  html += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${m.name}</td><td><b>${fmt(m.wer)} / ${fmt(m.cer)}</b></td></tr>`;
334
  });
@@ -343,16 +331,19 @@
343
  if(!d) return;
344
 
345
  d.data.sort((a,b) => a.Avg_WER - b.Avg_WER);
346
- let rank=1;
347
 
348
  html = `<table><thead><tr><th>Model</th><th>Simba ASR Family Score <i class="fa-solid fa-arrow-down arrow-down"></i></th>`;
349
  d.languages.forEach(l => html += `<th>${getIso(l.name, l.iso)}</th>`);
350
  html += `</tr></thead><tbody>`;
351
 
352
  d.data.forEach((r, idx) => {
353
- if (idx > 0 && Math.abs(r.Avg_WER - d.data[idx-1].Avg_WER) > 0.001) rank = idx + 1;
 
 
 
 
354
  let icon = '';
355
- if(rank === 1) icon = 'πŸ₯‡ '; else if(rank === 2) icon = 'πŸ₯ˆ '; else if(rank === 3) icon = 'πŸ₯‰ ';
356
 
357
  html += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${r.Model}</td><td style="font-weight:bold; background:#f8fafc">${fmt(r.Avg_WER)} / ${fmt(r.Avg_CER)}</td>`;
358
  d.languages.forEach(l => {
@@ -422,43 +413,58 @@
422
  function renderLanguageView() {
423
  const lang = document.getElementById('lang-select').value;
424
 
425
- // 1. ASR (Tie-Aware)
426
  let asrRows = [];
427
  Object.keys(DATA.asr.by_model).forEach(modName => {
428
  const row = DATA.asr.by_model[modName].find(r => r.Language === lang);
429
  if(row) asrRows.push({model: modName, wer: row.WER, cer: row.CER});
430
  });
431
- asrRows.sort((a,b) => a.wer - b.wer);
 
 
432
 
433
  let h1 = `<table><thead><tr><th>Model</th><th>WER</th><th>CER</th></tr></thead><tbody>`;
434
  if(asrRows.length === 0) h1 += `<tr><td colspan="3">No ASR data for this language.</td></tr>`;
435
  else {
436
- let rank = 1;
437
  asrRows.forEach((r, i) => {
438
- if (i > 0 && Math.abs(r.wer - asrRows[i-1].wer) > 0.001) rank = i + 1;
 
 
 
 
439
  let icon = '';
440
- if(rank === 1) icon = 'πŸ₯‡ '; else if(rank === 2) icon = 'πŸ₯ˆ '; else if(rank === 3) icon = 'πŸ₯‰ ';
441
  h1 += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${r.model}</td><td>${fmt(r.wer)}</td><td>${fmt(r.cer)}</td></tr>`;
442
  });
443
  }
444
  h1 += `</tbody></table>`;
445
  document.getElementById('lang-asr-table').innerHTML = h1;
446
 
447
- // 2. TTS
448
- let h2 = `<table><thead><tr><th>Model</th><th>WER</th><th>MCD</th><th>PESQ</th></tr></thead><tbody>`;
 
 
 
 
449
  let ttsFound = false;
450
  Object.keys(DATA.tts).forEach(mod => {
451
  const row = DATA.tts[mod].find(r => r.language === lang);
452
  if(row) {
453
  ttsFound = true;
454
- h2 += `<tr><td style="font-weight:600;">${mod}</td><td>${fmt(row.wer)}</td><td>${fmt(row.mcd)}</td><td>${fmt(row.pesq)}</td></tr>`;
 
 
 
 
 
 
455
  }
456
  });
457
- if(!ttsFound) h2 += `<tr><td colspan="4">No TTS data.</td></tr>`;
458
  h2 += `</tbody></table>`;
459
  document.getElementById('lang-tts-table').innerHTML = h2;
460
 
461
- // 3. SLID
462
  let h3 = `<table><thead><tr><th>Model</th><th>F1-Score</th></tr></thead><tbody>`;
463
  // Fuzzy match logic
464
  const slidRow = DATA.slid.find(r => r.Language === lang) ||
@@ -466,13 +472,19 @@
466
  DATA.slid.find(r => r.Language.includes(lang));
467
 
468
  if(slidRow) {
469
- let m = slidRow['MMS-LID-1024'], s = slidRow['Simba-SLID'];
470
- // Sort Descending
471
- let scores = [{n:'Simba-SLID', v:s}, {n:'MMS-LID-1024', v:m}].sort((a,b)=>b.v - a.v);
472
- let rank = 1;
473
  scores.forEach((sc, i) => {
474
- if (i > 0 && Math.abs(sc.v - scores[i-1].v) > 0.001) rank = i + 1;
475
- let icon = (rank==1) ? 'πŸ₯‡ ' : '';
 
 
 
 
 
 
476
  h3 += `<tr><td style="font-weight:600;">${icon}${sc.n}</td><td>${fmt(sc.v)}</td></tr>`;
477
  });
478
  } else {
 
67
  @keyframes bounce { 0%, 100% { height: 20px; } 50% { height: 120px; } }
68
 
69
  /* --- WIDTH CONTROLLER --- */
70
+ .content-container { width: 80%; max-width: 1600px; margin: 0 auto; }
 
 
 
 
71
 
72
  /* --- MAIN BOARD --- */
73
+ .main-card { background: white; border-radius: 24px; padding: 40px; color: #0f172a; min-height: 600px; position: relative; z-index: 10; margin-bottom: 60px; }
 
 
 
 
 
 
 
 
 
74
 
75
  .tabs { display: flex; gap: 10px; border-bottom: 2px solid #e2e8f0; margin-bottom: 30px; padding-bottom: 10px; overflow-x: auto; }
76
  .tab-btn { background: none; border: none; font-size: 15px; font-weight: 600; color: #64748b; padding: 10px 20px; cursor: pointer; transition: 0.3s; border-radius: 8px; white-space: nowrap; }
 
96
  h4 { color: var(--text-yellow); font-family: 'Rubik', sans-serif; font-size: 18px; margin: 0 0 15px 0; border-bottom: 1px solid #eee; padding-bottom: 10px; }
97
 
98
  /* Citations */
99
+ .citation-section { background: #0f172a; border: 1px solid #334155; border-radius: 16px; padding: 40px; box-sizing: border-box; box-shadow: 0 20px 40px rgba(0,0,0,0.3); position: relative; }
 
 
 
 
 
 
 
 
100
  .citation-section h3 { color: var(--text-yellow); font-family: 'Rubik', sans-serif; font-size: 24px; margin-top: 0; }
101
  .citation-box { background: #1e293b; color: #cbd5e1; padding: 20px; border-radius: 12px; font-family: monospace; white-space: pre-wrap; margin-top: 20px; overflow-x: auto; border: 1px solid #334155; font-size: 13px; line-height: 1.5; }
102
  .copy-btn { position: absolute; top: 40px; right: 40px; background: var(--text-yellow); border: none; padding: 8px 16px; border-radius: 6px; font-weight: bold; cursor: pointer; color: #0f172a; }
 
205
  <select id="lang-select" onchange="renderLanguageView()"></select>
206
  </div>
207
 
208
+ <h4>Automatic Speech Recognition (ASR) Results <span class="rank-info" style="font-weight:normal;">(Ranked by WER ↓, then CER ↓)</span></h4>
209
  <div id="lang-asr-table" class="table-wrap"></div>
210
 
211
+ <h4>Text-to-Speech (TTS) Results</h4>
212
  <div id="lang-tts-table" class="table-wrap"></div>
213
 
214
+ <h4>Spoken Language Identification (SLID) Results <span class="rank-info" style="font-weight:normal;">(Ranked by Score ↑)</span></h4>
215
  <div id="lang-slid-table" class="table-wrap"></div>
216
  </div>
217
  </div>
 
298
  if(n>0) modelStats.push({ name: modName, wer: sW/n, cer: sC/n });
299
  });
300
 
301
+ modelStats.sort((a,b) => (a.wer - b.wer) || (a.cer - b.cer)); // Sorting by WER then CER
 
 
302
 
303
  html = `<table><thead><tr><th>Model</th><th>Simba ASR Score (WER/CER) <i class="fa-solid fa-arrow-down arrow-down"></i></th></tr></thead><tbody>`;
304
  modelStats.forEach((m, i) => {
305
+ let rank = 1;
306
  if (i > 0 && Math.abs(m.wer - modelStats[i-1].wer) > 0.001) rank = i + 1;
307
+ else if (i > 0) rank = 1; // Actually logic needs to track currentRank variable, but simplifying for medals
308
 
309
+ // Simple medal logic: if tied with prev, use prev medal.
310
+ // Accurate Ranking:
311
  let icon = '';
312
+ // Re-evaluate rank based on index isn't enough for ties.
313
+ // Let's just use top 3 logic based on sorted order for simplicity or strict rank variable.
314
+ // Strict Rank Variable:
315
+ if(i===0) m.rank=1;
316
+ else if(Math.abs(m.wer - modelStats[i-1].wer) < 0.001) m.rank = modelStats[i-1].rank;
317
+ else m.rank = i+1;
318
+
319
+ if(m.rank === 1) icon = 'πŸ₯‡ '; else if(m.rank === 2) icon = 'πŸ₯ˆ '; else if(m.rank === 3) icon = 'πŸ₯‰ ';
320
 
321
  html += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${m.name}</td><td><b>${fmt(m.wer)} / ${fmt(m.cer)}</b></td></tr>`;
322
  });
 
331
  if(!d) return;
332
 
333
  d.data.sort((a,b) => a.Avg_WER - b.Avg_WER);
 
334
 
335
  html = `<table><thead><tr><th>Model</th><th>Simba ASR Family Score <i class="fa-solid fa-arrow-down arrow-down"></i></th>`;
336
  d.languages.forEach(l => html += `<th>${getIso(l.name, l.iso)}</th>`);
337
  html += `</tr></thead><tbody>`;
338
 
339
  d.data.forEach((r, idx) => {
340
+ // Rank Logic
341
+ if(idx===0) r.rank=1;
342
+ else if(Math.abs(r.Avg_WER - d.data[idx-1].Avg_WER) < 0.001) r.rank = d.data[idx-1].rank;
343
+ else r.rank = idx+1;
344
+
345
  let icon = '';
346
+ if(r.rank === 1) icon = 'πŸ₯‡ '; else if(r.rank === 2) icon = 'πŸ₯ˆ '; else if(r.rank === 3) icon = 'πŸ₯‰ ';
347
 
348
  html += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${r.Model}</td><td style="font-weight:bold; background:#f8fafc">${fmt(r.Avg_WER)} / ${fmt(r.Avg_CER)}</td>`;
349
  d.languages.forEach(l => {
 
413
  function renderLanguageView() {
414
  const lang = document.getElementById('lang-select').value;
415
 
416
+ // 1. ASR (Tie-Aware, WER then CER)
417
  let asrRows = [];
418
  Object.keys(DATA.asr.by_model).forEach(modName => {
419
  const row = DATA.asr.by_model[modName].find(r => r.Language === lang);
420
  if(row) asrRows.push({model: modName, wer: row.WER, cer: row.CER});
421
  });
422
+
423
+ // Sort: Primary WER ASC, Secondary CER ASC
424
+ asrRows.sort((a,b) => (a.wer - b.wer) || (a.cer - b.cer));
425
 
426
  let h1 = `<table><thead><tr><th>Model</th><th>WER</th><th>CER</th></tr></thead><tbody>`;
427
  if(asrRows.length === 0) h1 += `<tr><td colspan="3">No ASR data for this language.</td></tr>`;
428
  else {
 
429
  asrRows.forEach((r, i) => {
430
+ // Calculate Rank
431
+ if(i===0) r.rank=1;
432
+ else if(Math.abs(r.wer - asrRows[i-1].wer) < 0.001) r.rank = asrRows[i-1].rank; // Tie
433
+ else r.rank = i+1;
434
+
435
  let icon = '';
436
+ if(r.rank === 1) icon = 'πŸ₯‡ '; else if(r.rank === 2) icon = 'πŸ₯ˆ '; else if(r.rank === 3) icon = 'πŸ₯‰ ';
437
  h1 += `<tr><td style="font-weight:600; color:var(--simba-navy)">${icon}${r.model}</td><td>${fmt(r.wer)}</td><td>${fmt(r.cer)}</td></tr>`;
438
  });
439
  }
440
  h1 += `</tbody></table>`;
441
  document.getElementById('lang-asr-table').innerHTML = h1;
442
 
443
+ // 2. TTS (All Metrics)
444
+ let h2 = `<table><thead><tr><th>Model</th>
445
+ <th>WER(↓)</th><th>MCD(↓)</th><th>LogF0(↓)</th><th>SpTok(↓)</th>
446
+ <th>PESQ(↑)</th><th>UTMOS(↑)</th><th>SpBLEU(↑)</th><th>SpBERT(↑)</th>
447
+ </tr></thead><tbody>`;
448
+
449
  let ttsFound = false;
450
  Object.keys(DATA.tts).forEach(mod => {
451
  const row = DATA.tts[mod].find(r => r.language === lang);
452
  if(row) {
453
  ttsFound = true;
454
+ h2 += `<tr>
455
+ <td style="font-weight:600;">${mod}</td>
456
+ <td>${fmt(row.wer)}</td><td>${fmt(row.mcd)}</td>
457
+ <td>${fmt(row.logf0rmse)}</td><td>${fmt(row.speech_token_distance)}</td>
458
+ <td>${fmt(row.pesq)}</td><td>${fmt(row.utmos)}</td>
459
+ <td>${fmt(row.speechbleu)}</td><td>${fmt(row.speechbert_score)}</td>
460
+ </tr>`;
461
  }
462
  });
463
+ if(!ttsFound) h2 += `<tr><td colspan="9">No TTS data.</td></tr>`;
464
  h2 += `</tbody></table>`;
465
  document.getElementById('lang-tts-table').innerHTML = h2;
466
 
467
+ // 3. SLID (Dynamic Models)
468
  let h3 = `<table><thead><tr><th>Model</th><th>F1-Score</th></tr></thead><tbody>`;
469
  // Fuzzy match logic
470
  const slidRow = DATA.slid.find(r => r.Language === lang) ||
 
472
  DATA.slid.find(r => r.Language.includes(lang));
473
 
474
  if(slidRow) {
475
+ // Extract models dynamically (exclude Language key)
476
+ const models = Object.keys(slidRow).filter(k => k !== 'Language' && k !== 'ISO');
477
+ const scores = models.map(m => ({n: m, v: slidRow[m]})).sort((a,b) => b.v - a.v); // Descending
478
+
479
  scores.forEach((sc, i) => {
480
+ // Rank logic for SLID
481
+ if(i===0) sc.rank=1;
482
+ else if(Math.abs(sc.v - scores[i-1].v) < 0.001) sc.rank = scores[i-1].rank;
483
+ else sc.rank = i+1;
484
+
485
+ let icon = '';
486
+ if(sc.rank === 1) icon = 'πŸ₯‡ '; else if(sc.rank === 2) icon = 'πŸ₯ˆ '; else if(sc.rank === 3) icon = 'πŸ₯‰ ';
487
+
488
  h3 += `<tr><td style="font-weight:600;">${icon}${sc.n}</td><td>${fmt(sc.v)}</td></tr>`;
489
  });
490
  } else {