yonigozlan HF Staff commited on
Commit
19a56ad
·
1 Parent(s): 8be71fe

add missing tasks and improve style

Browse files
Files changed (1) hide show
  1. app.py +282 -69
app.py CHANGED
@@ -294,7 +294,11 @@ class TransformersTimelineParser:
294
  # Import the model mappings from transformers
295
  from transformers.models.auto.modeling_auto import (
296
  MODEL_FOR_AUDIO_CLASSIFICATION_MAPPING_NAMES,
 
 
 
297
  MODEL_FOR_CAUSAL_LM_MAPPING_NAMES,
 
298
  MODEL_FOR_DEPTH_ESTIMATION_MAPPING_NAMES,
299
  MODEL_FOR_DOCUMENT_QUESTION_ANSWERING_MAPPING_NAMES,
300
  MODEL_FOR_IMAGE_CLASSIFICATION_MAPPING_NAMES,
@@ -302,15 +306,21 @@ class TransformersTimelineParser:
302
  MODEL_FOR_IMAGE_TEXT_TO_TEXT_MAPPING_NAMES,
303
  MODEL_FOR_IMAGE_TO_IMAGE_MAPPING_NAMES,
304
  MODEL_FOR_INSTANCE_SEGMENTATION_MAPPING_NAMES,
 
 
305
  MODEL_FOR_MASK_GENERATION_MAPPING_NAMES,
 
306
  MODEL_FOR_MASKED_LM_MAPPING_NAMES,
 
307
  MODEL_FOR_OBJECT_DETECTION_MAPPING_NAMES,
308
  MODEL_FOR_QUESTION_ANSWERING_MAPPING_NAMES,
309
  MODEL_FOR_SEMANTIC_SEGMENTATION_MAPPING_NAMES,
310
  MODEL_FOR_SEQ_TO_SEQ_CAUSAL_LM_MAPPING_NAMES,
311
  MODEL_FOR_SEQUENCE_CLASSIFICATION_MAPPING_NAMES,
 
312
  MODEL_FOR_TABLE_QUESTION_ANSWERING_MAPPING_NAMES,
313
  MODEL_FOR_TEXT_TO_SPECTROGRAM_MAPPING_NAMES,
 
314
  MODEL_FOR_TIME_SERIES_CLASSIFICATION_MAPPING_NAMES,
315
  MODEL_FOR_TIME_SERIES_PREDICTION_MAPPING_NAMES,
316
  MODEL_FOR_TIME_SERIES_REGRESSION_MAPPING_NAMES,
@@ -331,6 +341,7 @@ class TransformersTimelineParser:
331
  "question-answering": MODEL_FOR_QUESTION_ANSWERING_MAPPING_NAMES,
332
  "fill-mask": MODEL_FOR_MASKED_LM_MAPPING_NAMES,
333
  "text2text-generation": MODEL_FOR_SEQ_TO_SEQ_CAUSAL_LM_MAPPING_NAMES,
 
334
  "image-classification": MODEL_FOR_IMAGE_CLASSIFICATION_MAPPING_NAMES,
335
  "object-detection": MODEL_FOR_OBJECT_DETECTION_MAPPING_NAMES,
336
  "image-segmentation": MODEL_FOR_IMAGE_SEGMENTATION_MAPPING_NAMES,
@@ -338,8 +349,16 @@ class TransformersTimelineParser:
338
  "instance-segmentation": MODEL_FOR_INSTANCE_SEGMENTATION_MAPPING_NAMES,
339
  "universal-segmentation": MODEL_FOR_UNIVERSAL_SEGMENTATION_MAPPING_NAMES,
340
  "depth-estimation": MODEL_FOR_DEPTH_ESTIMATION_MAPPING_NAMES,
 
 
 
 
341
  "video-classification": MODEL_FOR_VIDEO_CLASSIFICATION_MAPPING_NAMES,
342
  "audio-classification": MODEL_FOR_AUDIO_CLASSIFICATION_MAPPING_NAMES,
 
 
 
 
343
  "image-to-text": MODEL_FOR_VISION_2_SEQ_MAPPING_NAMES,
344
  "image-text-to-text": MODEL_FOR_IMAGE_TEXT_TO_TEXT_MAPPING_NAMES,
345
  "visual-question-answering": MODEL_FOR_VISUAL_QUESTION_ANSWERING_MAPPING_NAMES,
@@ -350,6 +369,7 @@ class TransformersTimelineParser:
350
  "image-to-image": MODEL_FOR_IMAGE_TO_IMAGE_MAPPING_NAMES,
351
  "mask-generation": MODEL_FOR_MASK_GENERATION_MAPPING_NAMES,
352
  "text-to-audio": MODEL_FOR_TEXT_TO_SPECTROGRAM_MAPPING_NAMES,
 
353
  "time-series-classification": MODEL_FOR_TIME_SERIES_CLASSIFICATION_MAPPING_NAMES,
354
  "time-series-regression": MODEL_FOR_TIME_SERIES_REGRESSION_MAPPING_NAMES,
355
  "time-series-prediction": MODEL_FOR_TIME_SERIES_PREDICTION_MAPPING_NAMES,
@@ -536,6 +556,7 @@ def get_tasks():
536
  "question-answering": {"name": "Question Answering", "color": "#c084fc"},
537
  "fill-mask": {"name": "Fill Mask", "color": "#d8b4fe"},
538
  "text2text-generation": {"name": "Text2Text Generation", "color": "#e879f9"},
 
539
  "image-classification": {"name": "Image Classification", "color": "#06b6d4"},
540
  "object-detection": {"name": "Object Detection", "color": "#0891b2"},
541
  "image-segmentation": {"name": "Image Segmentation", "color": "#0e7490"},
@@ -543,6 +564,10 @@ def get_tasks():
543
  "instance-segmentation": {"name": "Instance Segmentation", "color": "#164e63"},
544
  "universal-segmentation": {"name": "Universal Segmentation", "color": "#1e40af"},
545
  "depth-estimation": {"name": "Depth Estimation", "color": "#1d4ed8"},
 
 
 
 
546
  "zero-shot-image-classification": {"name": "Zero-Shot Image Classification", "color": "#2563eb"},
547
  "zero-shot-object-detection": {"name": "Zero-Shot Object Detection", "color": "#3b82f6"},
548
  "image-to-image": {"name": "Image to Image", "color": "#60a5fa"},
@@ -554,7 +579,15 @@ def get_tasks():
554
  "table-question-answering": {"name": "Table Question Answering", "color": "#064e3b"},
555
  "video-classification": {"name": "Video Classification", "color": "#dc2626"},
556
  "audio-classification": {"name": "Audio Classification", "color": "#ea580c"},
 
 
 
 
 
 
 
557
  "text-to-audio": {"name": "Text to Audio", "color": "#f97316"},
 
558
  "time-series-classification": {"name": "Time Series Classification", "color": "#84cc16"},
559
  "time-series-regression": {"name": "Time Series Regression", "color": "#65a30d"},
560
  "time-series-prediction": {"name": "Time Series Prediction", "color": "#4d7c0f"},
@@ -604,7 +637,8 @@ def create_timeline_template():
604
  body {
605
  font-family: 'Inter', system-ui, -apple-system, sans-serif;
606
  background: linear-gradient(135deg, #fef3c7 0%, #fed7aa 100%);
607
- min-height: 100vh;
 
608
  color: #333;
609
  display: flex;
610
  flex-direction: column;
@@ -1198,7 +1232,7 @@ def create_timeline_template():
1198
  flex: 1;
1199
  display: flex;
1200
  flex-direction: column;
1201
- height: calc(100vh - 110px);
1202
  transition: all 0.3s ease;
1203
  }
1204
 
@@ -1409,23 +1443,22 @@ def create_timeline_template():
1409
  position: absolute;
1410
  top: 0;
1411
  bottom: 0;
1412
- width: 2px;
1413
- background: #9ca3af;
1414
- opacity: 0.8;
1415
  pointer-events: none;
1416
- z-index: 1; /* In background, below everything */
1417
  transition: all 0.3s ease;
1418
  }
1419
 
1420
  /* Dark mode date markers */
1421
  [data-theme="dark"] .date-marker {
1422
- background: #6b7280;
1423
- opacity: 0.9;
1424
  }
1425
 
1426
  .date-label {
1427
  position: absolute;
1428
- top: 20px; /* Near the top of timeline viewport */
1429
  left: 8px; /* Offset to the right of the line */
1430
  font-size: 0.75rem;
1431
  color: #6b7280;
@@ -1437,7 +1470,7 @@ def create_timeline_template():
1437
  border: 1px solid rgba(156, 163, 175, 0.4);
1438
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
1439
  white-space: nowrap;
1440
- z-index: 2; /* Just above the dotted line but below everything else */
1441
  backdrop-filter: blur(4px);
1442
  transition: all 0.3s ease;
1443
  }
@@ -1451,15 +1484,15 @@ def create_timeline_template():
1451
  }
1452
 
1453
  .date-marker.year {
1454
- opacity: 0.9;
1455
- background: #6b7280;
1456
- width: 3px;
1457
  }
1458
 
1459
  /* Dark mode year markers */
1460
  [data-theme="dark"] .date-marker.year {
1461
- background: #9ca3af;
1462
- opacity: 1.0;
1463
  }
1464
 
1465
  .date-marker.year .date-label {
@@ -2203,6 +2236,76 @@ def create_timeline_template():
2203
  const maxZoom = 3.0; // Maximum zoom (300%)
2204
  let taskData = {}; // Store task data for easy lookup
2205
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2206
  // Theme management
2207
  let currentTheme = 'light';
2208
 
@@ -2433,6 +2536,9 @@ def create_timeline_template():
2433
  // Add date markers before adding models
2434
  addDateMarkers(sortedModels, actualSpacing);
2435
 
 
 
 
2436
  // Create wave patterns for stacking - simpler pattern
2437
  const abovePattern = [1, 2, 3]; // 3 levels above
2438
  const belowPattern = [1, 2, 3]; // 3 levels below
@@ -2461,6 +2567,19 @@ def create_timeline_template():
2461
  item.className = `timeline-item ${positionClass}`;
2462
  item.style.left = position + 'px';
2463
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2464
  const dot = document.createElement('div');
2465
  dot.className = 'timeline-dot';
2466
 
@@ -2480,12 +2599,31 @@ def create_timeline_template():
2480
 
2481
  const connector = document.createElement('div');
2482
  connector.className = 'timeline-connector';
 
 
 
 
 
 
 
 
2483
 
2484
  const label = document.createElement('div');
2485
  label.className = 'timeline-label';
2486
  label.style.borderLeftColor = model.modality_color || '#8B5CF6';
2487
  // Set the modality color as a CSS custom property for hover effects
2488
  label.style.setProperty('--modality-color', model.modality_color || '#8B5CF6');
 
 
 
 
 
 
 
 
 
 
 
2489
 
2490
  // Ensure the model name is always displayed
2491
  const modelName = model.display_name || model.model_name || 'Unknown Model';
@@ -2529,10 +2667,17 @@ def create_timeline_template():
2529
  <div class="timeline-date">${otherLabel.dataset.modelDate}</div>
2530
  `;
2531
 
2532
- // Reset positioning after content change
2533
  setTimeout(() => {
2534
- otherLabel.style.top = '';
2535
- otherLabel.style.bottom = '';
 
 
 
 
 
 
 
2536
  otherLabel.style.left = '';
2537
  otherLabel.style.right = '';
2538
  otherLabel.style.transform = 'translateX(-50%)';
@@ -2659,10 +2804,17 @@ def create_timeline_template():
2659
  <div class="timeline-date">${label.dataset.modelDate}</div>
2660
  `;
2661
 
2662
- // Reset positioning after content change
2663
  setTimeout(() => {
2664
- label.style.top = '';
2665
- label.style.bottom = '';
 
 
 
 
 
 
 
2666
  label.style.left = '';
2667
  label.style.right = '';
2668
  // Reset transform: depends on current position
@@ -2816,11 +2968,8 @@ def create_timeline_template():
2816
  // Check if the marker date falls between these two models
2817
  // The marker should appear where the time period actually starts
2818
  if (currentModelDate < currentDate && currentDate <= nextModelDate) {
2819
- // Position the marker between these two models, then move left by half segment
2820
- const currentPos = i * spacing + 100;
2821
- const nextPos = (i + 1) * spacing + 100;
2822
- const midpoint = (currentPos + nextPos) / 2;
2823
- boundaryPosition = midpoint - (spacing / 2); // Move left by half segment length
2824
  break;
2825
  }
2826
  }
@@ -2839,45 +2988,64 @@ def create_timeline_template():
2839
  const position = boundaryPosition;
2840
 
2841
  // Create marker only if it's within visible range and not too close to adjacent markers
 
2842
  const existingMarkers = timeline.querySelectorAll('.date-marker');
2843
- let tooClose = false;
2844
- existingMarkers.forEach(existing => {
2845
- const existingPos = parseFloat(existing.style.left);
2846
- if (Math.abs(existingPos - position) < 120) { // Minimum spacing between markers
2847
- tooClose = true;
 
 
 
 
2848
  }
2849
- });
2850
 
2851
- if (!tooClose) {
2852
- const marker = document.createElement('div');
2853
- marker.className = `date-marker ${markerType}`;
2854
- marker.style.left = position + 'px';
2855
-
2856
- // Create label
2857
- const label = document.createElement('div');
2858
- label.className = 'date-label';
2859
- label.textContent = format(currentDate);
2860
- marker.appendChild(label);
2861
-
2862
- // Create vertical line
2863
- const line = document.createElement('div');
2864
- line.style.position = 'absolute';
2865
- line.style.top = '0px';
2866
- line.style.bottom = '0px';
2867
- line.style.left = '0px';
2868
- line.style.width = '2px';
2869
- line.style.background = '#9ca3af';
2870
- line.style.opacity = '0.6';
2871
- line.style.zIndex = '1';
2872
- if (markerType === 'year') {
2873
- line.style.width = '3px';
2874
- line.style.background = '#6b7280';
2875
- line.style.opacity = '0.8';
2876
  }
2877
- marker.appendChild(line);
2878
 
2879
- timeline.appendChild(marker);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2880
  }
 
 
 
 
 
 
 
 
 
 
2881
 
2882
  // Move to next marker
2883
  currentDate.setMonth(currentDate.getMonth() + increment);
@@ -3161,6 +3329,7 @@ def create_timeline_template():
3161
  "question-answering": "#c084fc",
3162
  "fill-mask": "#d8b4fe",
3163
  "text2text-generation": "#e879f9",
 
3164
 
3165
  "image-classification": "#06b6d4",
3166
  "object-detection": "#0891b2",
@@ -3169,6 +3338,10 @@ def create_timeline_template():
3169
  "instance-segmentation": "#164e63",
3170
  "universal-segmentation": "#1e40af",
3171
  "depth-estimation": "#1d4ed8",
 
 
 
 
3172
  "zero-shot-image-classification": "#2563eb",
3173
  "zero-shot-object-detection": "#3b82f6",
3174
  "image-to-image": "#60a5fa",
@@ -3182,7 +3355,12 @@ def create_timeline_template():
3182
 
3183
  "video-classification": "#dc2626",
3184
  "audio-classification": "#ea580c",
 
 
 
 
3185
  "text-to-audio": "#f97316",
 
3186
 
3187
  "time-series-classification": "#84cc16",
3188
  "time-series-regression": "#65a30d",
@@ -3225,7 +3403,7 @@ def create_timeline_template():
3225
  checkbox.type = 'checkbox';
3226
  checkbox.value = modality.key;
3227
  checkbox.id = `modality-${modality.key}`;
3228
- checkbox.checked = true; // All modalities selected by default
3229
 
3230
  const label = document.createElement('label');
3231
  label.htmlFor = `modality-${modality.key}`;
@@ -3244,8 +3422,7 @@ def create_timeline_template():
3244
  loadTimeline();
3245
  });
3246
 
3247
- // Set initial state
3248
- checkboxContainer.classList.add('checked');
3249
 
3250
  modalityFilters.appendChild(checkboxContainer);
3251
  });
@@ -3255,11 +3432,19 @@ def create_timeline_template():
3255
  }
3256
  }
3257
 
3258
- // Window resize handler
 
3259
  window.addEventListener('resize', () => {
3260
- if (currentModels.length > 0) {
3261
- renderTimeline(currentModels);
3262
- }
 
 
 
 
 
 
 
3263
  });
3264
 
3265
  document.addEventListener('DOMContentLoaded', async () => {
@@ -3304,10 +3489,17 @@ def create_timeline_template():
3304
  <div class="timeline-date">${label.dataset.modelDate}</div>
3305
  `;
3306
 
3307
- // Reset positioning after content change
3308
  setTimeout(() => {
3309
- label.style.top = '';
3310
- label.style.bottom = '';
 
 
 
 
 
 
 
3311
  label.style.transform = 'translateX(-50%)';
3312
  label.parentElement.style.zIndex = '';
3313
  }, 50);
@@ -3364,6 +3556,27 @@ def create_timeline_template():
3364
  btn.textContent = '▸';
3365
  localStorage.setItem('filtersCollapsed', 'true');
3366
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
3367
  }
3368
  </script>
3369
  </body>
 
294
  # Import the model mappings from transformers
295
  from transformers.models.auto.modeling_auto import (
296
  MODEL_FOR_AUDIO_CLASSIFICATION_MAPPING_NAMES,
297
+ MODEL_FOR_AUDIO_FRAME_CLASSIFICATION_MAPPING_NAMES,
298
+ MODEL_FOR_AUDIO_XVECTOR_MAPPING_NAMES,
299
+ MODEL_FOR_CAUSAL_IMAGE_MODELING_MAPPING_NAMES,
300
  MODEL_FOR_CAUSAL_LM_MAPPING_NAMES,
301
+ MODEL_FOR_CTC_MAPPING_NAMES,
302
  MODEL_FOR_DEPTH_ESTIMATION_MAPPING_NAMES,
303
  MODEL_FOR_DOCUMENT_QUESTION_ANSWERING_MAPPING_NAMES,
304
  MODEL_FOR_IMAGE_CLASSIFICATION_MAPPING_NAMES,
 
306
  MODEL_FOR_IMAGE_TEXT_TO_TEXT_MAPPING_NAMES,
307
  MODEL_FOR_IMAGE_TO_IMAGE_MAPPING_NAMES,
308
  MODEL_FOR_INSTANCE_SEGMENTATION_MAPPING_NAMES,
309
+ MODEL_FOR_KEYPOINT_DETECTION_MAPPING_NAMES,
310
+ MODEL_FOR_KEYPOINT_MATCHING_MAPPING_NAMES,
311
  MODEL_FOR_MASK_GENERATION_MAPPING_NAMES,
312
+ MODEL_FOR_MASKED_IMAGE_MODELING_MAPPING_NAMES,
313
  MODEL_FOR_MASKED_LM_MAPPING_NAMES,
314
+ MODEL_FOR_MULTIPLE_CHOICE_MAPPING_NAMES,
315
  MODEL_FOR_OBJECT_DETECTION_MAPPING_NAMES,
316
  MODEL_FOR_QUESTION_ANSWERING_MAPPING_NAMES,
317
  MODEL_FOR_SEMANTIC_SEGMENTATION_MAPPING_NAMES,
318
  MODEL_FOR_SEQ_TO_SEQ_CAUSAL_LM_MAPPING_NAMES,
319
  MODEL_FOR_SEQUENCE_CLASSIFICATION_MAPPING_NAMES,
320
+ MODEL_FOR_SPEECH_SEQ_2_SEQ_MAPPING_NAMES,
321
  MODEL_FOR_TABLE_QUESTION_ANSWERING_MAPPING_NAMES,
322
  MODEL_FOR_TEXT_TO_SPECTROGRAM_MAPPING_NAMES,
323
+ MODEL_FOR_TEXT_TO_WAVEFORM_MAPPING_NAMES,
324
  MODEL_FOR_TIME_SERIES_CLASSIFICATION_MAPPING_NAMES,
325
  MODEL_FOR_TIME_SERIES_PREDICTION_MAPPING_NAMES,
326
  MODEL_FOR_TIME_SERIES_REGRESSION_MAPPING_NAMES,
 
341
  "question-answering": MODEL_FOR_QUESTION_ANSWERING_MAPPING_NAMES,
342
  "fill-mask": MODEL_FOR_MASKED_LM_MAPPING_NAMES,
343
  "text2text-generation": MODEL_FOR_SEQ_TO_SEQ_CAUSAL_LM_MAPPING_NAMES,
344
+ "multiple-choice": MODEL_FOR_MULTIPLE_CHOICE_MAPPING_NAMES,
345
  "image-classification": MODEL_FOR_IMAGE_CLASSIFICATION_MAPPING_NAMES,
346
  "object-detection": MODEL_FOR_OBJECT_DETECTION_MAPPING_NAMES,
347
  "image-segmentation": MODEL_FOR_IMAGE_SEGMENTATION_MAPPING_NAMES,
 
349
  "instance-segmentation": MODEL_FOR_INSTANCE_SEGMENTATION_MAPPING_NAMES,
350
  "universal-segmentation": MODEL_FOR_UNIVERSAL_SEGMENTATION_MAPPING_NAMES,
351
  "depth-estimation": MODEL_FOR_DEPTH_ESTIMATION_MAPPING_NAMES,
352
+ "masked-image-modeling": MODEL_FOR_MASKED_IMAGE_MODELING_MAPPING_NAMES,
353
+ "causal-image-modeling": MODEL_FOR_CAUSAL_IMAGE_MODELING_MAPPING_NAMES,
354
+ "keypoint-detection": MODEL_FOR_KEYPOINT_DETECTION_MAPPING_NAMES,
355
+ "keypoint-matching": MODEL_FOR_KEYPOINT_MATCHING_MAPPING_NAMES,
356
  "video-classification": MODEL_FOR_VIDEO_CLASSIFICATION_MAPPING_NAMES,
357
  "audio-classification": MODEL_FOR_AUDIO_CLASSIFICATION_MAPPING_NAMES,
358
+ "audio-frame-classification": MODEL_FOR_AUDIO_FRAME_CLASSIFICATION_MAPPING_NAMES,
359
+ "audio-xvector": MODEL_FOR_AUDIO_XVECTOR_MAPPING_NAMES,
360
+ "automatic-speech-recognition": MODEL_FOR_SPEECH_SEQ_2_SEQ_MAPPING_NAMES,
361
+ "connectionist-temporal-classification": MODEL_FOR_CTC_MAPPING_NAMES,
362
  "image-to-text": MODEL_FOR_VISION_2_SEQ_MAPPING_NAMES,
363
  "image-text-to-text": MODEL_FOR_IMAGE_TEXT_TO_TEXT_MAPPING_NAMES,
364
  "visual-question-answering": MODEL_FOR_VISUAL_QUESTION_ANSWERING_MAPPING_NAMES,
 
369
  "image-to-image": MODEL_FOR_IMAGE_TO_IMAGE_MAPPING_NAMES,
370
  "mask-generation": MODEL_FOR_MASK_GENERATION_MAPPING_NAMES,
371
  "text-to-audio": MODEL_FOR_TEXT_TO_SPECTROGRAM_MAPPING_NAMES,
372
+ "text-to-waveform": MODEL_FOR_TEXT_TO_WAVEFORM_MAPPING_NAMES,
373
  "time-series-classification": MODEL_FOR_TIME_SERIES_CLASSIFICATION_MAPPING_NAMES,
374
  "time-series-regression": MODEL_FOR_TIME_SERIES_REGRESSION_MAPPING_NAMES,
375
  "time-series-prediction": MODEL_FOR_TIME_SERIES_PREDICTION_MAPPING_NAMES,
 
556
  "question-answering": {"name": "Question Answering", "color": "#c084fc"},
557
  "fill-mask": {"name": "Fill Mask", "color": "#d8b4fe"},
558
  "text2text-generation": {"name": "Text2Text Generation", "color": "#e879f9"},
559
+ "multiple-choice": {"name": "Multiple Choice", "color": "#c026d3"},
560
  "image-classification": {"name": "Image Classification", "color": "#06b6d4"},
561
  "object-detection": {"name": "Object Detection", "color": "#0891b2"},
562
  "image-segmentation": {"name": "Image Segmentation", "color": "#0e7490"},
 
564
  "instance-segmentation": {"name": "Instance Segmentation", "color": "#164e63"},
565
  "universal-segmentation": {"name": "Universal Segmentation", "color": "#1e40af"},
566
  "depth-estimation": {"name": "Depth Estimation", "color": "#1d4ed8"},
567
+ "masked-image-modeling": {"name": "Masked Image Modeling", "color": "#7c3aed"},
568
+ "causal-image-modeling": {"name": "Causal Image Modeling", "color": "#6d28d9"},
569
+ "keypoint-detection": {"name": "Keypoint Detection", "color": "#4338ca"},
570
+ "keypoint-matching": {"name": "Keypoint Matching", "color": "#3730a3"},
571
  "zero-shot-image-classification": {"name": "Zero-Shot Image Classification", "color": "#2563eb"},
572
  "zero-shot-object-detection": {"name": "Zero-Shot Object Detection", "color": "#3b82f6"},
573
  "image-to-image": {"name": "Image to Image", "color": "#60a5fa"},
 
579
  "table-question-answering": {"name": "Table Question Answering", "color": "#064e3b"},
580
  "video-classification": {"name": "Video Classification", "color": "#dc2626"},
581
  "audio-classification": {"name": "Audio Classification", "color": "#ea580c"},
582
+ "audio-frame-classification": {"name": "Audio Frame Classification", "color": "#fb923c"},
583
+ "audio-xvector": {"name": "Audio X-Vector", "color": "#fdba74"},
584
+ "automatic-speech-recognition": {"name": "Automatic Speech Recognition", "color": "#e11d48"},
585
+ "connectionist-temporal-classification": {
586
+ "name": "Connectionist Temporal Classification",
587
+ "color": "#be123c",
588
+ },
589
  "text-to-audio": {"name": "Text to Audio", "color": "#f97316"},
590
+ "text-to-waveform": {"name": "Text to Waveform", "color": "#fb923c"},
591
  "time-series-classification": {"name": "Time Series Classification", "color": "#84cc16"},
592
  "time-series-regression": {"name": "Time Series Regression", "color": "#65a30d"},
593
  "time-series-prediction": {"name": "Time Series Prediction", "color": "#4d7c0f"},
 
637
  body {
638
  font-family: 'Inter', system-ui, -apple-system, sans-serif;
639
  background: linear-gradient(135deg, #fef3c7 0%, #fed7aa 100%);
640
+ height: 100vh;
641
+ overflow: hidden;
642
  color: #333;
643
  display: flex;
644
  flex-direction: column;
 
1232
  flex: 1;
1233
  display: flex;
1234
  flex-direction: column;
1235
+ min-height: 400px;
1236
  transition: all 0.3s ease;
1237
  }
1238
 
 
1443
  position: absolute;
1444
  top: 0;
1445
  bottom: 0;
1446
+ width: 1px;
1447
+ border-left: 1px dashed #9ca3af;
1448
+ opacity: 0.5;
1449
  pointer-events: none;
 
1450
  transition: all 0.3s ease;
1451
  }
1452
 
1453
  /* Dark mode date markers */
1454
  [data-theme="dark"] .date-marker {
1455
+ border-left-color: #6b7280;
1456
+ opacity: 0.6;
1457
  }
1458
 
1459
  .date-label {
1460
  position: absolute;
1461
+ top: 10px; /* Near the top of timeline viewport */
1462
  left: 8px; /* Offset to the right of the line */
1463
  font-size: 0.75rem;
1464
  color: #6b7280;
 
1470
  border: 1px solid rgba(156, 163, 175, 0.4);
1471
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
1472
  white-space: nowrap;
1473
+ z-index: 9; /* Just above the dotted line but below cards */
1474
  backdrop-filter: blur(4px);
1475
  transition: all 0.3s ease;
1476
  }
 
1484
  }
1485
 
1486
  .date-marker.year {
1487
+ opacity: 0.7;
1488
+ border-left: 1px dashed #6b7280;
1489
+ width: 1px;
1490
  }
1491
 
1492
  /* Dark mode year markers */
1493
  [data-theme="dark"] .date-marker.year {
1494
+ border-left-color: #9ca3af;
1495
+ opacity: 0.8;
1496
  }
1497
 
1498
  .date-marker.year .date-label {
 
2236
  const maxZoom = 3.0; // Maximum zoom (300%)
2237
  let taskData = {}; // Store task data for easy lookup
2238
 
2239
+ // Function to calculate dynamic card spacing based on available height
2240
+ function getCardSpacing() {
2241
+ const timelineWrapper = document.querySelector('.timeline-wrapper');
2242
+ if (!timelineWrapper) return { above: [60, 120, 180], below: [60, 120, 180] };
2243
+
2244
+ const availableHeight = timelineWrapper.clientHeight;
2245
+ const centerLineOffset = availableHeight / 2;
2246
+ const usableHeight = Math.max(centerLineOffset - 80, 80); // Leave margin for card height
2247
+
2248
+ // Calculate spacing between levels (3 levels each side)
2249
+ // Use the minimum of: default spacing OR available space divided by 3
2250
+ const levelSpacing = Math.max(40, Math.min(60, usableHeight / 3)); // At least 40px, max 60px
2251
+
2252
+ return {
2253
+ above: [
2254
+ levelSpacing,
2255
+ levelSpacing * 2,
2256
+ levelSpacing * 3
2257
+ ],
2258
+ below: [
2259
+ levelSpacing,
2260
+ levelSpacing * 2,
2261
+ levelSpacing * 3
2262
+ ]
2263
+ };
2264
+ }
2265
+
2266
+ // Efficiently update card positions without re-rendering
2267
+ function updateCardPositions() {
2268
+ const cardSpacing = getCardSpacing();
2269
+ const timeline = document.getElementById('timeline');
2270
+ if (!timeline) return;
2271
+
2272
+ // Update all timeline items
2273
+ const items = timeline.querySelectorAll('.timeline-item');
2274
+ items.forEach(item => {
2275
+ const positionClass = item.className.match(/(above|below)-(\\d)/);
2276
+ if (!positionClass) return;
2277
+
2278
+ const isAbove = positionClass[1] === 'above';
2279
+ const level = parseInt(positionClass[2]) - 1; // 0, 1, or 2
2280
+
2281
+ // Update connector height
2282
+ const connector = item.querySelector('.timeline-connector');
2283
+ if (connector) {
2284
+ if (isAbove) {
2285
+ connector.style.height = cardSpacing.above[level] + 'px';
2286
+ } else {
2287
+ connector.style.height = cardSpacing.below[level] + 'px';
2288
+ }
2289
+ }
2290
+
2291
+ // Update label position
2292
+ const label = item.querySelector('.timeline-label');
2293
+ if (label) {
2294
+ if (isAbove) {
2295
+ const dynamicBottom = cardSpacing.above[level] + 'px';
2296
+ label.style.bottom = dynamicBottom;
2297
+ label.style.top = '';
2298
+ label.dataset.dynamicBottom = dynamicBottom;
2299
+ } else {
2300
+ const dynamicTop = cardSpacing.below[level] + 'px';
2301
+ label.style.top = dynamicTop;
2302
+ label.style.bottom = '';
2303
+ label.dataset.dynamicTop = dynamicTop;
2304
+ }
2305
+ }
2306
+ });
2307
+ }
2308
+
2309
  // Theme management
2310
  let currentTheme = 'light';
2311
 
 
2536
  // Add date markers before adding models
2537
  addDateMarkers(sortedModels, actualSpacing);
2538
 
2539
+ // Get dynamic card spacing based on available height
2540
+ const cardSpacing = getCardSpacing();
2541
+
2542
  // Create wave patterns for stacking - simpler pattern
2543
  const abovePattern = [1, 2, 3]; // 3 levels above
2544
  const belowPattern = [1, 2, 3]; // 3 levels below
 
2567
  item.className = `timeline-item ${positionClass}`;
2568
  item.style.left = position + 'px';
2569
 
2570
+ // Apply dynamic positioning based on available height
2571
+ const levelIndex = parseInt(positionClass.split('-')[1]) - 1; // Get 0, 1, or 2
2572
+ const isAbove = positionClass.includes('above');
2573
+
2574
+ // Store the dynamic spacing as data attributes for later use
2575
+ if (isAbove) {
2576
+ item.dataset.dynamicBottom = cardSpacing.above[levelIndex] + 'px';
2577
+ item.dataset.dynamicHeight = cardSpacing.above[levelIndex] + 'px';
2578
+ } else {
2579
+ item.dataset.dynamicTop = cardSpacing.below[levelIndex] + 'px';
2580
+ item.dataset.dynamicHeight = cardSpacing.below[levelIndex] + 'px';
2581
+ }
2582
+
2583
  const dot = document.createElement('div');
2584
  dot.className = 'timeline-dot';
2585
 
 
2599
 
2600
  const connector = document.createElement('div');
2601
  connector.className = 'timeline-connector';
2602
+ // Apply dynamic height to connector
2603
+ if (isAbove) {
2604
+ connector.style.bottom = '9px';
2605
+ connector.style.height = cardSpacing.above[levelIndex] + 'px';
2606
+ } else {
2607
+ connector.style.top = '9px';
2608
+ connector.style.height = cardSpacing.below[levelIndex] + 'px';
2609
+ }
2610
 
2611
  const label = document.createElement('div');
2612
  label.className = 'timeline-label';
2613
  label.style.borderLeftColor = model.modality_color || '#8B5CF6';
2614
  // Set the modality color as a CSS custom property for hover effects
2615
  label.style.setProperty('--modality-color', model.modality_color || '#8B5CF6');
2616
+ // Apply dynamic positioning to label and store for later restoration
2617
+ if (isAbove) {
2618
+ const dynamicBottom = cardSpacing.above[levelIndex] + 'px';
2619
+ label.style.bottom = dynamicBottom;
2620
+ label.dataset.dynamicBottom = dynamicBottom;
2621
+ } else {
2622
+ const dynamicTop = cardSpacing.below[levelIndex] + 'px';
2623
+ label.style.top = dynamicTop;
2624
+ label.dataset.dynamicTop = dynamicTop;
2625
+ }
2626
+ label.dataset.positionClass = positionClass; // Store for collapse restoration
2627
 
2628
  // Ensure the model name is always displayed
2629
  const modelName = model.display_name || model.model_name || 'Unknown Model';
 
2667
  <div class="timeline-date">${otherLabel.dataset.modelDate}</div>
2668
  `;
2669
 
2670
+ // Restore dynamic positioning after content change
2671
  setTimeout(() => {
2672
+ // Restore the dynamically calculated position
2673
+ const isAbove = otherLabel.dataset.positionClass && otherLabel.dataset.positionClass.includes('above');
2674
+ if (isAbove && otherLabel.dataset.dynamicBottom) {
2675
+ otherLabel.style.bottom = otherLabel.dataset.dynamicBottom;
2676
+ otherLabel.style.top = '';
2677
+ } else if (!isAbove && otherLabel.dataset.dynamicTop) {
2678
+ otherLabel.style.top = otherLabel.dataset.dynamicTop;
2679
+ otherLabel.style.bottom = '';
2680
+ }
2681
  otherLabel.style.left = '';
2682
  otherLabel.style.right = '';
2683
  otherLabel.style.transform = 'translateX(-50%)';
 
2804
  <div class="timeline-date">${label.dataset.modelDate}</div>
2805
  `;
2806
 
2807
+ // Restore dynamic positioning after content change
2808
  setTimeout(() => {
2809
+ // Restore the dynamically calculated position
2810
+ const isAbove = label.dataset.positionClass && label.dataset.positionClass.includes('above');
2811
+ if (isAbove && label.dataset.dynamicBottom) {
2812
+ label.style.bottom = label.dataset.dynamicBottom;
2813
+ label.style.top = '';
2814
+ } else if (!isAbove && label.dataset.dynamicTop) {
2815
+ label.style.top = label.dataset.dynamicTop;
2816
+ label.style.bottom = '';
2817
+ }
2818
  label.style.left = '';
2819
  label.style.right = '';
2820
  // Reset transform: depends on current position
 
2968
  // Check if the marker date falls between these two models
2969
  // The marker should appear where the time period actually starts
2970
  if (currentModelDate < currentDate && currentDate <= nextModelDate) {
2971
+ // Position the marker between these two models
2972
+ boundaryPosition = (i + 1) * spacing + 68;
 
 
 
2973
  break;
2974
  }
2975
  }
 
2988
  const position = boundaryPosition;
2989
 
2990
  // Create marker only if it's within visible range and not too close to adjacent markers
2991
+ // Only check VS the last existing marker, since markers are added more recent each time.
2992
  const existingMarkers = timeline.querySelectorAll('.date-marker');
2993
+ let shouldRemovePrevious = false;
2994
+ let lastMarker = null;
2995
+ let lastPos = null;
2996
+
2997
+ if (existingMarkers.length > 0) {
2998
+ lastMarker = existingMarkers[existingMarkers.length - 1];
2999
+ lastPos = parseFloat(lastMarker.style.left);
3000
+ if (Math.abs(position - lastPos) < 60) { // Minimum spacing between markers
3001
+ shouldRemovePrevious = true;
3002
  }
3003
+ }
3004
 
3005
+ if (shouldRemovePrevious && lastMarker) {
3006
+ lastMarker.remove();
3007
+ // Also remove the label associated with that marker (next sibling in .date-label)
3008
+ const timelineLabels = timeline.querySelectorAll('.date-label');
3009
+ // Find the label with the left matching the previous marker
3010
+ for (let i = 0; i < timelineLabels.length; i++) {
3011
+ const lbl = timelineLabels[i];
3012
+ // label.style.left is like "123px"
3013
+ if (Math.abs(parseFloat(lbl.style.left) - (lastPos + 8)) < 2) { // allow for rounding errors
3014
+ lbl.remove();
3015
+ break;
3016
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
3017
  }
3018
+ }
3019
 
3020
+ // Create marker
3021
+ const marker = document.createElement('div');
3022
+ marker.className = `date-marker ${markerType}`;
3023
+ marker.style.left = position + 'px';
3024
+
3025
+ // Create vertical line (dashed)
3026
+ const line = document.createElement('div');
3027
+ line.style.position = 'absolute';
3028
+ line.style.top = '0px';
3029
+ line.style.bottom = '0px';
3030
+ line.style.left = '0px';
3031
+ line.style.width = '1px';
3032
+ line.style.borderLeft = '1px dashed #9ca3af';
3033
+ line.style.opacity = '0.5';
3034
+ line.style.zIndex = '0';
3035
+ if (markerType === 'year') {
3036
+ line.style.borderLeft = '1px dashed #6b7280';
3037
+ line.style.opacity = '0.7';
3038
  }
3039
+ marker.appendChild(line);
3040
+
3041
+ // Create label (as a separate sibling, not a child)
3042
+ const label = document.createElement('div');
3043
+ label.className = 'date-label';
3044
+ label.textContent = format(currentDate);
3045
+ label.style.left = position + 8 + 'px'; // offset similar to CSS left: 8px for label
3046
+
3047
+ timeline.appendChild(marker);
3048
+ timeline.appendChild(label);
3049
 
3050
  // Move to next marker
3051
  currentDate.setMonth(currentDate.getMonth() + increment);
 
3329
  "question-answering": "#c084fc",
3330
  "fill-mask": "#d8b4fe",
3331
  "text2text-generation": "#e879f9",
3332
+ "multiple-choice": "#c026d3",
3333
 
3334
  "image-classification": "#06b6d4",
3335
  "object-detection": "#0891b2",
 
3338
  "instance-segmentation": "#164e63",
3339
  "universal-segmentation": "#1e40af",
3340
  "depth-estimation": "#1d4ed8",
3341
+ "masked-image-modeling": "#7c3aed",
3342
+ "causal-image-modeling": "#6d28d9",
3343
+ "keypoint-detection": "#4338ca",
3344
+ "keypoint-matching": "#3730a3",
3345
  "zero-shot-image-classification": "#2563eb",
3346
  "zero-shot-object-detection": "#3b82f6",
3347
  "image-to-image": "#60a5fa",
 
3355
 
3356
  "video-classification": "#dc2626",
3357
  "audio-classification": "#ea580c",
3358
+ "audio-frame-classification": "#fb923c",
3359
+ "audio-xvector": "#fdba74",
3360
+ "automatic-speech-recognition": "#e11d48",
3361
+ "connectionist-temporal-classification": "#be123c",
3362
  "text-to-audio": "#f97316",
3363
+ "text-to-waveform": "#fb923c",
3364
 
3365
  "time-series-classification": "#84cc16",
3366
  "time-series-regression": "#65a30d",
 
3403
  checkbox.type = 'checkbox';
3404
  checkbox.value = modality.key;
3405
  checkbox.id = `modality-${modality.key}`;
3406
+ checkbox.checked = false; // All modalities unchecked by default
3407
 
3408
  const label = document.createElement('label');
3409
  label.htmlFor = `modality-${modality.key}`;
 
3422
  loadTimeline();
3423
  });
3424
 
3425
+ // Set initial state (unchecked, so no 'checked' class)
 
3426
 
3427
  modalityFilters.appendChild(checkboxContainer);
3428
  });
 
3432
  }
3433
  }
3434
 
3435
+ // Window resize handler - use efficient position update
3436
+ let resizeTimeout;
3437
  window.addEventListener('resize', () => {
3438
+ // Update immediately for responsiveness
3439
+ updateCardPositions();
3440
+
3441
+ // Debounce full re-render for final adjustment
3442
+ clearTimeout(resizeTimeout);
3443
+ resizeTimeout = setTimeout(() => {
3444
+ if (currentModels.length > 0) {
3445
+ renderTimeline(currentModels, true);
3446
+ }
3447
+ }, 250);
3448
  });
3449
 
3450
  document.addEventListener('DOMContentLoaded', async () => {
 
3489
  <div class="timeline-date">${label.dataset.modelDate}</div>
3490
  `;
3491
 
3492
+ // Restore dynamic positioning after content change
3493
  setTimeout(() => {
3494
+ // Restore the dynamically calculated position
3495
+ const isAbove = label.dataset.positionClass && label.dataset.positionClass.includes('above');
3496
+ if (isAbove && label.dataset.dynamicBottom) {
3497
+ label.style.bottom = label.dataset.dynamicBottom;
3498
+ label.style.top = '';
3499
+ } else if (!isAbove && label.dataset.dynamicTop) {
3500
+ label.style.top = label.dataset.dynamicTop;
3501
+ label.style.bottom = '';
3502
+ }
3503
  label.style.transform = 'translateX(-50%)';
3504
  label.parentElement.style.zIndex = '';
3505
  }, 50);
 
3556
  btn.textContent = '▸';
3557
  localStorage.setItem('filtersCollapsed', 'true');
3558
  }
3559
+
3560
+ // Update card positions immediately
3561
+ updateCardPositions();
3562
+
3563
+ // Continue updating during animation for smooth transition
3564
+ const startTime = performance.now();
3565
+ const animationDuration = 250; // Match CSS transition time
3566
+
3567
+ const animatePositions = (currentTime) => {
3568
+ const elapsed = currentTime - startTime;
3569
+
3570
+ if (elapsed < animationDuration) {
3571
+ updateCardPositions();
3572
+ requestAnimationFrame(animatePositions);
3573
+ } else {
3574
+ // Final update after animation completes
3575
+ updateCardPositions();
3576
+ }
3577
+ };
3578
+
3579
+ requestAnimationFrame(animatePositions);
3580
  }
3581
  </script>
3582
  </body>