unified-video-framework 1.4.255 → 1.4.257

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1184,7 +1184,7 @@ export class WebPlayer extends BasePlayer {
1184
1184
  width: '100%',
1185
1185
  height: '100%',
1186
1186
  playerVars: {
1187
- controls: 0, // Hide YouTube controls
1187
+ controls: this.config.youtubeNativeControls !== false ? 1 : 0, // Native controls enabled by default
1188
1188
  disablekb: 0, // Allow keyboard controls
1189
1189
  fs: 0, // Hide fullscreen button
1190
1190
  iv_load_policy: 3, // Hide annotations
@@ -1252,16 +1252,16 @@ export class WebPlayer extends BasePlayer {
1252
1252
  this.youtubePlayer.mute();
1253
1253
  }
1254
1254
 
1255
- // Extract available YouTube qualities
1256
- this.extractYouTubeAvailableQualities();
1255
+ // Detect if YouTube video is Live and handle controls
1256
+ this.detectYouTubeLiveStatus();
1257
1257
 
1258
1258
  // Try to get video title from YouTube API
1259
1259
  this.getYouTubeVideoTitle();
1260
1260
 
1261
- // Update metadata UI and settings after player is ready
1261
+ // Update metadata UI and controls visibility after player is ready
1262
1262
  setTimeout(() => {
1263
1263
  this.updateMetadataUI();
1264
- this.updateSettingsMenu();
1264
+ this.updateControlsVisibility();
1265
1265
  }, 500);
1266
1266
  }
1267
1267
 
@@ -1277,16 +1277,10 @@ export class WebPlayer extends BasePlayer {
1277
1277
  switch (state) {
1278
1278
  case window.YT.PlayerState.PLAYING:
1279
1279
  this.state.isPlaying = true;
1280
- this.state.isPaused = false;
1281
- this.state.isBuffering = false;
1282
- this.updateYouTubeUI('playing');
1283
-
1284
- // Extract qualities when video starts playing
1285
- setTimeout(() => {
1286
- this.extractYouTubeAvailableQualities();
1287
- }, 1000);
1288
-
1289
- this.emit('onPlay');
1280
+ this.state.isPaused = false;
1281
+ this.state.isBuffering = false;
1282
+ this.updateYouTubeUI('playing');
1283
+ this.emit('onPlay');
1290
1284
  break;
1291
1285
 
1292
1286
  case window.YT.PlayerState.PAUSED:
@@ -1297,16 +1291,10 @@ export class WebPlayer extends BasePlayer {
1297
1291
  this.emit('onPause');
1298
1292
  break;
1299
1293
 
1300
- case window.YT.PlayerState.BUFFERING:
1301
- this.state.isBuffering = true;
1302
- this.updateYouTubeUI('buffering');
1303
-
1304
- // Try to extract qualities during buffering as well
1305
- setTimeout(() => {
1306
- this.extractYouTubeAvailableQualities();
1307
- }, 500);
1308
-
1309
- this.emit('onBuffering', true);
1294
+ case window.YT.PlayerState.BUFFERING:
1295
+ this.state.isBuffering = true;
1296
+ this.updateYouTubeUI('buffering');
1297
+ this.emit('onBuffering', true);
1310
1298
  break;
1311
1299
 
1312
1300
  case window.YT.PlayerState.ENDED:
@@ -1317,15 +1305,16 @@ export class WebPlayer extends BasePlayer {
1317
1305
  this.emit('onEnded');
1318
1306
  break;
1319
1307
 
1320
- case window.YT.PlayerState.CUED:
1321
- this.state.duration = this.youtubePlayer.getDuration();
1322
- this.updateYouTubeUI('cued');
1323
-
1324
- // Try to get video title when video is cued
1325
- setTimeout(() => {
1326
- this.getYouTubeVideoTitle();
1327
- }, 100);
1328
- break;
1308
+ case window.YT.PlayerState.CUED:
1309
+ this.state.duration = this.youtubePlayer.getDuration();
1310
+ this.updateYouTubeUI('cued');
1311
+
1312
+ // Re-check Live status when video is cued
1313
+ setTimeout(() => {
1314
+ this.detectYouTubeLiveStatus();
1315
+ this.updateControlsVisibility();
1316
+ }, 500);
1317
+ break;
1329
1318
  }
1330
1319
  }
1331
1320
 
@@ -1402,6 +1391,159 @@ export class WebPlayer extends BasePlayer {
1402
1391
  }
1403
1392
  }
1404
1393
 
1394
+ /**
1395
+ * Detect if YouTube video is Live
1396
+ */
1397
+ private detectYouTubeLiveStatus(): void {
1398
+ if (!this.youtubePlayer || !this.youtubePlayerReady) return;
1399
+
1400
+ try {
1401
+ const videoData = this.youtubePlayer.getVideoData();
1402
+ this.isYouTubeLive = videoData?.isLive || false;
1403
+
1404
+ // Auto-enable native controls for all YouTube content by default, unless explicitly disabled
1405
+ this.useYouTubeNativeControls = this.config.youtubeNativeControls !== false;
1406
+
1407
+ this.debugLog('YouTube Live status:', {
1408
+ isLive: this.isYouTubeLive,
1409
+ useNativeControls: this.useYouTubeNativeControls,
1410
+ videoId: videoData?.video_id
1411
+ });
1412
+
1413
+ } catch (error) {
1414
+ this.debugWarn('Could not detect YouTube Live status:', error);
1415
+ // Fallback: check duration - Live videos typically have duration = 0
1416
+ try {
1417
+ const duration = this.youtubePlayer.getDuration();
1418
+ this.isYouTubeLive = !duration || duration === 0;
1419
+ this.useYouTubeNativeControls = this.config.youtubeNativeControls !== false;
1420
+
1421
+ this.debugLog('YouTube Live detected via duration check:', {
1422
+ duration,
1423
+ isLive: this.isYouTubeLive,
1424
+ useNativeControls: this.useYouTubeNativeControls
1425
+ });
1426
+ } catch (e) {
1427
+ this.debugWarn('Could not check YouTube duration for Live detection:', e);
1428
+ }
1429
+ }
1430
+ }
1431
+
1432
+ /**
1433
+ * Update controls visibility based on YouTube Live status and config
1434
+ */
1435
+ private updateControlsVisibility(): void {
1436
+ const controlsContainer = document.getElementById('uvf-controls-container');
1437
+ if (!controlsContainer) return;
1438
+
1439
+ if (this.youtubePlayer && this.useYouTubeNativeControls) {
1440
+ // Hide custom controls and show YouTube native controls
1441
+ controlsContainer.style.display = 'none';
1442
+
1443
+ // Re-create YouTube player with native controls if needed
1444
+ if (!this.config.youtubeNativeControls) {
1445
+ this.recreateYouTubePlayerWithNativeControls();
1446
+ }
1447
+
1448
+ this.debugLog('✅ YouTube native controls enabled', {
1449
+ isLive: this.isYouTubeLive,
1450
+ reason: this.config.youtubeNativeControls !== false ? 'Default behavior (all YouTube content)' : 'Live stream detected'
1451
+ });
1452
+ } else {
1453
+ // Show custom controls
1454
+ controlsContainer.style.display = 'flex';
1455
+ this.debugLog('✅ Custom controls enabled for YouTube video');
1456
+ }
1457
+ }
1458
+
1459
+ /**
1460
+ * Recreate YouTube player with native controls enabled
1461
+ */
1462
+ private recreateYouTubePlayerWithNativeControls(): void {
1463
+ if (!this.source?.metadata?.videoId) return;
1464
+
1465
+ const videoId = this.source.metadata.videoId;
1466
+ const currentTime = this.youtubePlayer?.getCurrentTime() || 0;
1467
+
1468
+ // Find the container
1469
+ const container = this.playerWrapper || this.video?.parentElement;
1470
+ if (!container) return;
1471
+
1472
+ // Destroy current player
1473
+ if (this.youtubePlayer) {
1474
+ this.youtubePlayer.destroy();
1475
+ }
1476
+
1477
+ // Remove existing iframe container
1478
+ const existingContainer = container.querySelector(`#youtube-player-${videoId}`);
1479
+ if (existingContainer) {
1480
+ existingContainer.remove();
1481
+ }
1482
+
1483
+ // Create new iframe container
1484
+ const iframeContainer = document.createElement('div');
1485
+ iframeContainer.id = `youtube-player-${videoId}`;
1486
+ iframeContainer.style.cssText = `
1487
+ position: absolute;
1488
+ top: 0;
1489
+ left: 0;
1490
+ width: 100%;
1491
+ height: 100%;
1492
+ z-index: 1;
1493
+ `;
1494
+ container.appendChild(iframeContainer);
1495
+
1496
+ // Create new player with native controls
1497
+ this.youtubePlayer = new window.YT.Player(iframeContainer.id, {
1498
+ videoId: videoId,
1499
+ width: '100%',
1500
+ height: '100%',
1501
+ playerVars: {
1502
+ autoplay: this.config.autoPlay ? 1 : 0,
1503
+ controls: 1, // Enable native controls
1504
+ modestbranding: 1,
1505
+ rel: 0,
1506
+ showinfo: 0,
1507
+ iv_load_policy: 3,
1508
+ playsinline: 1,
1509
+ start: Math.floor(currentTime)
1510
+ },
1511
+ events: {
1512
+ onReady: () => {
1513
+ this.youtubePlayerReady = true;
1514
+ this.debugLog('YouTube player with native controls ready');
1515
+ this.emit('onReady');
1516
+ },
1517
+ onStateChange: (event: any) => this.onYouTubePlayerStateChange(event),
1518
+ onError: (event: any) => this.onYouTubePlayerError(event)
1519
+ }
1520
+ });
1521
+ }
1522
+
1523
+ /**
1524
+ * Toggle between native and custom YouTube controls
1525
+ */
1526
+ public toggleYouTubeControls(useNative: boolean = !this.useYouTubeNativeControls): void {
1527
+ if (!this.youtubePlayer) {
1528
+ this.debugWarn('Cannot toggle YouTube controls - no YouTube player active');
1529
+ return;
1530
+ }
1531
+
1532
+ this.useYouTubeNativeControls = useNative;
1533
+ this.config.youtubeNativeControls = useNative; // Update config
1534
+ this.updateControlsVisibility();
1535
+
1536
+ this.debugLog('YouTube controls toggled:', {
1537
+ useNative: this.useYouTubeNativeControls,
1538
+ isLive: this.isYouTubeLive
1539
+ });
1540
+
1541
+ // Show notification
1542
+ this.showNotification(
1543
+ `YouTube Controls: ${this.useYouTubeNativeControls ? 'Native' : 'Custom'}`
1544
+ );
1545
+ }
1546
+
1405
1547
  /**
1406
1548
  * Fallback method to get title from YouTube oembed API
1407
1549
  */
@@ -1433,243 +1575,24 @@ export class WebPlayer extends BasePlayer {
1433
1575
  }
1434
1576
 
1435
1577
  private youtubeTimeTrackingInterval: NodeJS.Timeout | null = null;
1436
- private youtubeAvailableQualities: any[] = [];
1437
- private youtubeCurrentQuality: any = null;
1438
-
1439
- /**
1440
- * Extract available YouTube video qualities with retry logic
1441
- */
1442
- private extractYouTubeAvailableQualities(retryCount: number = 0): void {
1443
- if (!this.youtubePlayer || !this.youtubePlayerReady) {
1444
- this.debugLog('YouTube player not ready for quality extraction');
1445
- return;
1446
- }
1447
-
1448
- try {
1449
- const availableQualityLevels = this.youtubePlayer.getAvailableQualityLevels();
1450
- this.debugLog('🔍 YouTube quality detection attempt', retryCount + 1, '- Found levels:', availableQualityLevels);
1451
- this.debugLog('🔍 YouTube player state:', this.youtubePlayer.getPlayerState());
1452
- this.debugLog('🔍 Current YouTube quality:', this.youtubePlayer.getPlaybackQuality());
1453
-
1454
- // If no qualities detected and we haven't retried too much, retry after a delay
1455
- if ((!availableQualityLevels || availableQualityLevels.length === 0 || (availableQualityLevels.length === 1 && availableQualityLevels[0] === 'auto')) && retryCount < 5) {
1456
- this.debugLog('No meaningful qualities detected, retrying in', (retryCount + 1) * 1000, 'ms...');
1457
- setTimeout(() => {
1458
- this.extractYouTubeAvailableQualities(retryCount + 1);
1459
- }, (retryCount + 1) * 1000);
1460
- return;
1461
- }
1462
-
1463
- // Map YouTube quality levels to standard labels
1464
- const qualityMap: Record<string, any> = {
1465
- 'hd2160': { label: '4K', value: 'hd2160', height: 2160 },
1466
- 'hd1440': { label: '1440p', value: 'hd1440', height: 1440 },
1467
- 'hd1080': { label: '1080p', value: 'hd1080', height: 1080 },
1468
- 'hd720': { label: '720p', value: 'hd720', height: 720 },
1469
- 'large': { label: '480p', value: 'large', height: 480 },
1470
- 'medium': { label: '360p', value: 'medium', height: 360 },
1471
- 'small': { label: '240p', value: 'small', height: 240 },
1472
- 'tiny': { label: '144p', value: 'tiny', height: 144 },
1473
- 'auto': { label: 'Auto', value: 'auto', height: 0 }
1474
- };
1475
-
1476
- this.youtubeAvailableQualities = [];
1477
-
1478
- // Always add auto quality option first
1479
- this.youtubeAvailableQualities.push({ label: 'Auto', value: 'auto', height: 0 });
1480
-
1481
- // Add detected qualities, filtering out 'auto' since we already added it
1482
- if (availableQualityLevels && availableQualityLevels.length > 0) {
1483
- availableQualityLevels.forEach((qualityLevel: string) => {
1484
- if (qualityLevel !== 'auto' && qualityMap[qualityLevel]) {
1485
- this.youtubeAvailableQualities.push(qualityMap[qualityLevel]);
1486
- }
1487
- });
1488
-
1489
- // Sort qualities by height (descending, excluding auto)
1490
- const autoQuality = this.youtubeAvailableQualities.shift(); // Remove auto temporarily
1491
- this.youtubeAvailableQualities.sort((a, b) => (b.height || 0) - (a.height || 0));
1492
- if (autoQuality) this.youtubeAvailableQualities.unshift(autoQuality); // Add auto back at beginning
1493
- }
1494
-
1495
- this.debugLog('✅ Successfully mapped YouTube qualities:', this.youtubeAvailableQualities);
1496
-
1497
- // Get current quality
1498
- try {
1499
- const currentQuality = this.youtubePlayer.getPlaybackQuality();
1500
- this.youtubeCurrentQuality = qualityMap[currentQuality] || qualityMap['auto'];
1501
- this.debugLog('Current YouTube quality:', this.youtubeCurrentQuality);
1502
- } catch (e) {
1503
- this.debugWarn('Could not get current YouTube quality:', e);
1504
- this.youtubeCurrentQuality = qualityMap['auto'];
1505
- }
1506
-
1507
- // Update detected qualities to include YouTube qualities
1508
- this.detectAvailableQualities();
1509
-
1510
- this.debugLog('🚀 YouTube qualities successfully detected! Available qualities now:', this.availableQualities.length);
1511
-
1512
- // Update quality badge with current YouTube quality
1513
- this.updateQualityBadge();
1514
-
1515
- // Force settings menu refresh with new qualities
1516
- setTimeout(() => {
1517
- this.debugLog('🔄 Force refreshing settings menu with YouTube qualities');
1518
- this.updateSettingsMenu();
1519
- }, 100);
1520
-
1521
- } catch (error) {
1522
- this.debugWarn('Could not extract YouTube qualities:', error);
1523
- // Retry if we haven't tried too many times
1524
- if (retryCount < 3) {
1525
- setTimeout(() => {
1526
- this.extractYouTubeAvailableQualities(retryCount + 1);
1527
- }, 2000);
1528
- }
1529
- }
1530
- }
1531
-
1532
- /**
1533
- * Set YouTube video quality
1534
- */
1535
- private setYouTubeQuality(qualityLevel: string): void {
1536
- if (!this.youtubePlayer) return;
1537
-
1538
- try {
1539
- const qualityMap: Record<string, any> = {
1540
- 'hd2160': { label: '4K', value: 'hd2160', height: 2160 },
1541
- 'hd1440': { label: '1440p', value: 'hd1440', height: 1440 },
1542
- 'hd1080': { label: '1080p', value: 'hd1080', height: 1080 },
1543
- 'hd720': { label: '720p', value: 'hd720', height: 720 },
1544
- 'large': { label: '480p', value: 'large', height: 480 },
1545
- 'medium': { label: '360p', value: 'medium', height: 360 },
1546
- 'small': { label: '240p', value: 'small', height: 240 },
1547
- 'tiny': { label: '144p', value: 'tiny', height: 144 },
1548
- 'auto': { label: 'Auto', value: 'auto', height: 0 }
1549
- };
1550
-
1551
- this.debugLog('📊 Attempting to set YouTube quality to:', qualityLevel);
1552
-
1553
- // Multiple approaches to force YouTube quality change
1554
- if (qualityLevel === 'auto') {
1555
- // For auto, just use setPlaybackQuality
1556
- this.youtubePlayer.setPlaybackQuality(qualityLevel);
1557
- } else {
1558
- // For specific qualities, try multiple methods
1559
- try {
1560
- // Method 1: Set quality range (most effective for forcing specific quality)
1561
- if (typeof this.youtubePlayer.setPlaybackQualityRange === 'function') {
1562
- this.youtubePlayer.setPlaybackQualityRange(qualityLevel, qualityLevel);
1563
- this.debugLog('✅ setPlaybackQualityRange called for:', qualityLevel);
1564
- }
1565
- } catch (e) {
1566
- this.debugWarn('setPlaybackQualityRange failed:', e);
1567
- }
1568
-
1569
- try {
1570
- // Method 2: Standard quality setting
1571
- this.youtubePlayer.setPlaybackQuality(qualityLevel);
1572
- this.debugLog('✅ setPlaybackQuality called for:', qualityLevel);
1573
- } catch (e) {
1574
- this.debugWarn('setPlaybackQuality failed:', e);
1575
- }
1576
-
1577
- // Method 3: Force quality by pausing and resuming (more aggressive)
1578
- try {
1579
- const wasPlaying = this.youtubePlayer.getPlayerState() === window.YT.PlayerState.PLAYING;
1580
- if (wasPlaying) {
1581
- this.youtubePlayer.pauseVideo();
1582
- setTimeout(() => {
1583
- this.youtubePlayer.setPlaybackQuality(qualityLevel);
1584
- this.youtubePlayer.playVideo();
1585
- }, 100);
1586
- }
1587
- } catch (e) {
1588
- this.debugWarn('Force quality change with pause/play failed:', e);
1589
- }
1590
- }
1591
-
1592
- // Verify quality was changed after a delay
1593
- setTimeout(() => {
1594
- try {
1595
- const currentQuality = this.youtubePlayer.getPlaybackQuality();
1596
- this.youtubeCurrentQuality = qualityMap[currentQuality] || qualityMap['auto'];
1597
-
1598
- this.debugLog('📊 Current quality after set:', currentQuality, '(', this.youtubeCurrentQuality?.label, ')');
1599
-
1600
- // Show notification with result - be more user-friendly
1601
- if (currentQuality === qualityLevel) {
1602
- this.showNotification(`Quality: ${qualityMap[currentQuality]?.label || 'requested quality'}`);
1603
- this.debugLog('✅ Quality successfully changed to:', qualityLevel);
1604
- } else {
1605
- // Don't show "YouTube optimized" message to users - it's confusing
1606
- this.showNotification(`Quality: ${qualityMap[currentQuality]?.label || currentQuality}`);
1607
- this.debugLog('⚠️ Requested quality:', qualityLevel, '| Actual quality:', currentQuality, '(YouTube may have optimized)');
1608
- }
1609
-
1610
- // Update quality badge
1611
- this.updateQualityBadge();
1612
-
1613
- // Update settings menu UI
1614
- this.updateSettingsMenu();
1615
- } catch (verifyError) {
1616
- this.debugWarn('Could not verify YouTube quality:', verifyError);
1617
- }
1618
- }, 1000);
1619
-
1620
- } catch (error) {
1621
- this.debugWarn('❌ Could not set YouTube quality:', error);
1622
- this.showNotification('Quality control limited on YouTube');
1623
- }
1624
- }
1625
-
1626
- /**
1627
- * Update quality badge with current quality
1628
- */
1629
- private updateQualityBadge(): void {
1630
- const qualityBadge = document.getElementById('uvf-quality-badge');
1631
- if (!qualityBadge) return;
1632
-
1633
- // For YouTube, use YouTube current quality
1634
- if (this.youtubePlayer && this.youtubePlayerReady && this.youtubeCurrentQuality) {
1635
- qualityBadge.textContent = this.youtubeCurrentQuality.label || 'AUTO';
1636
- this.debugLog('Updated quality badge for YouTube:', this.youtubeCurrentQuality.label);
1637
- } else if (this.currentQualityIndex >= 0 && this.qualities[this.currentQualityIndex]) {
1638
- // For other sources, use current quality
1639
- const quality = this.qualities[this.currentQualityIndex];
1640
- qualityBadge.textContent = quality.label || 'HD';
1641
- this.debugLog('Updated quality badge for standard video:', quality.label);
1642
- } else {
1643
- // Default
1644
- qualityBadge.textContent = 'AUTO';
1645
- }
1646
- }
1578
+ private isYouTubeLive: boolean = false;
1579
+ private useYouTubeNativeControls: boolean = false;
1647
1580
 
1648
1581
  private startYouTubeTimeTracking(): void {
1649
1582
  if (this.youtubeTimeTrackingInterval) {
1650
1583
  clearInterval(this.youtubeTimeTrackingInterval);
1651
1584
  }
1652
1585
 
1653
- let qualityCheckCounter = 0;
1654
-
1655
- this.youtubeTimeTrackingInterval = setInterval(() => {
1656
- if (this.youtubePlayer && this.youtubePlayerReady) {
1657
- try {
1658
- const currentTime = this.youtubePlayer.getCurrentTime();
1659
- const duration = this.youtubePlayer.getDuration();
1660
- const buffered = this.youtubePlayer.getVideoLoadedFraction() * 100;
1661
-
1662
- this.state.currentTime = currentTime || 0;
1663
- this.state.duration = duration || 0;
1664
- this.state.bufferedPercentage = buffered || 0;
1665
-
1666
- // Check for qualities periodically (every 10 seconds) if we don't have them yet
1667
- qualityCheckCounter++;
1668
- if (qualityCheckCounter >= 40 && this.youtubeAvailableQualities.length <= 1) { // 40 * 250ms = 10s
1669
- this.debugLog('Periodic YouTube quality check triggered');
1670
- this.extractYouTubeAvailableQualities();
1671
- qualityCheckCounter = 0; // Reset counter
1672
- }
1586
+ this.youtubeTimeTrackingInterval = setInterval(() => {
1587
+ if (this.youtubePlayer && this.youtubePlayerReady) {
1588
+ try {
1589
+ const currentTime = this.youtubePlayer.getCurrentTime();
1590
+ const duration = this.youtubePlayer.getDuration();
1591
+ const buffered = this.youtubePlayer.getVideoLoadedFraction() * 100;
1592
+
1593
+ this.state.currentTime = currentTime || 0;
1594
+ this.state.duration = duration || 0;
1595
+ this.state.bufferedPercentage = buffered || 0;
1673
1596
 
1674
1597
  // Update UI progress bar
1675
1598
  this.updateYouTubeProgressBar(currentTime, duration, buffered);
@@ -9450,23 +9373,15 @@ export class WebPlayer extends BasePlayer {
9450
9373
  private setQualityByLabel(quality: string): void {
9451
9374
  // Handle YouTube player
9452
9375
  if (this.youtubePlayer && this.youtubePlayerReady) {
9453
- // Set YouTube quality directly
9454
- this.setYouTubeQuality(quality);
9455
-
9456
- // Update UI to reflect selection
9376
+ // YouTube quality is limited - show notification
9377
+ this.showShortcutIndicator('Quality control not available for YouTube');
9378
+ // Update UI to reflect current quality
9457
9379
  document.querySelectorAll('.quality-option').forEach(option => {
9458
9380
  option.classList.remove('active');
9459
- if ((option as HTMLElement).dataset.quality === quality) {
9381
+ if ((option as HTMLElement).dataset.quality === 'auto') {
9460
9382
  option.classList.add('active');
9461
9383
  }
9462
9384
  });
9463
-
9464
- // Update quality badge
9465
- const qualityBadge = document.getElementById('uvf-quality-badge');
9466
- if (qualityBadge) {
9467
- const qualityOption = this.youtubeAvailableQualities.find(q => q.value === quality);
9468
- qualityBadge.textContent = qualityOption ? qualityOption.label : 'AUTO';
9469
- }
9470
9385
  return;
9471
9386
  }
9472
9387
 
@@ -9767,17 +9682,9 @@ export class WebPlayer extends BasePlayer {
9767
9682
 
9768
9683
  // Quality Accordion Section (only if enabled in config and qualities detected)
9769
9684
  if (this.settingsConfig.quality && this.availableQualities.length > 0) {
9770
- this.debugLog('🎛️ Building quality menu with', this.availableQualities.length, 'qualities:', this.availableQualities.map(q => q.label));
9771
-
9772
- // For YouTube, use youtubeCurrentQuality; otherwise use currentQuality
9773
- const qualityForDisplay = this.youtubePlayer && this.youtubePlayerReady && this.youtubeCurrentQuality
9774
- ? this.youtubeCurrentQuality.value
9775
- : this.currentQuality;
9776
- const currentQuality = this.availableQualities.find(q => q.value === qualityForDisplay);
9685
+ const currentQuality = this.availableQualities.find(q => q.value === this.currentQuality);
9777
9686
  const currentQualityLabel = currentQuality ? currentQuality.label : 'Auto';
9778
9687
 
9779
- this.debugLog('🎛️ Current quality for display:', qualityForDisplay, '(', currentQualityLabel, ')');
9780
-
9781
9688
  menuHTML += `
9782
9689
  <div class="uvf-accordion-item">
9783
9690
  <div class="uvf-accordion-header" data-section="quality">
@@ -9795,11 +9702,7 @@ export class WebPlayer extends BasePlayer {
9795
9702
  <div class="uvf-accordion-content" data-section="quality">`;
9796
9703
 
9797
9704
  this.availableQualities.forEach(quality => {
9798
- // For YouTube, compare against youtubeCurrentQuality
9799
- const qualityValue = this.youtubePlayer && this.youtubePlayerReady && this.youtubeCurrentQuality
9800
- ? this.youtubeCurrentQuality.value
9801
- : this.currentQuality;
9802
- const isActive = quality.value === qualityValue ? 'active' : '';
9705
+ const isActive = quality.value === this.currentQuality ? 'active' : '';
9803
9706
  const isPremium = this.isQualityPremium(quality);
9804
9707
  const isLocked = isPremium && !this.isPremiumUser();
9805
9708
  const qualityHeight = (quality as any).height || 0;
@@ -9867,22 +9770,10 @@ export class WebPlayer extends BasePlayer {
9867
9770
  * Detect available video qualities from different sources
9868
9771
  */
9869
9772
  private detectAvailableQualities(): void {
9870
- // Check if we're using YouTube and have detected qualities
9871
- const isYouTube = this.youtubePlayer && this.youtubePlayerReady && this.youtubeAvailableQualities.length > 0;
9872
- this.availableQualities = [];
9773
+ this.availableQualities = [{ value: 'auto', label: 'Auto' }];
9873
9774
  let detectedQualities: Array<{ value: string; label: string; height?: number }> = [];
9874
9775
 
9875
- // YouTube qualities
9876
- if (isYouTube) {
9877
- detectedQualities = this.youtubeAvailableQualities.map(q => ({
9878
- value: q.value,
9879
- label: q.label,
9880
- height: q.height
9881
- }));
9882
- this.debugLog('Using YouTube qualities:', detectedQualities);
9883
- this.availableQualities = detectedQualities;
9884
- return; // Early return for YouTube
9885
- } else if (this.hls && this.hls.levels) {
9776
+ if (this.hls && this.hls.levels) {
9886
9777
  // HLS qualities
9887
9778
  this.hls.levels.forEach((level: any, index: number) => {
9888
9779
  if (level.height) {
@@ -10254,13 +10145,6 @@ export class WebPlayer extends BasePlayer {
10254
10145
  private setQualityFromSettings(quality: string): void {
10255
10146
  this.currentQuality = quality;
10256
10147
 
10257
- // Handle YouTube quality
10258
- if (this.youtubePlayer && this.youtubePlayerReady) {
10259
- this.setYouTubeQuality(quality);
10260
- this.debugLog(`YouTube quality set to ${quality}`);
10261
- return;
10262
- }
10263
-
10264
10148
  if (quality === 'auto') {
10265
10149
  // Enable auto quality with filter consideration
10266
10150
  if (this.hls) {