YouTube Thumbnails Fix

Controls the width of the video thumbnails grid and centers items on the YouTube homepage

当前为 2025-04-16 提交的版本,查看 最新版本

  1. // ==UserScript==
  2. // @name YouTube Thumbnails Fix
  3. // @namespace http://tampermonkey.net/
  4. // @version 1.4
  5. // @description Controls the width of the video thumbnails grid and centers items on the YouTube homepage
  6. // @author Anixty
  7. // @match https://www.youtube.com/*
  8. // @grant GM_getValue
  9. // @grant GM_setValue
  10. // @license MIT
  11. // ==/UserScript==
  12. (function() {
  13. 'use strict';
  14.  
  15. const STORAGE_KEY = 'itemWidth';
  16. const CONTROL_ID = 'tm-width-control';
  17. const defaultWidth = GM_getValue(STORAGE_KEY, '300px');
  18.  
  19. const styleTag = document.createElement('style');
  20. document.head.appendChild(styleTag);
  21.  
  22. function updateWidthStyle(width) {
  23. styleTag.textContent = `
  24. ytd-rich-grid-renderer #contents {
  25. display: flex !important;
  26. flex-wrap: wrap !important;
  27. justify-content: center !important;
  28. }
  29. ytd-rich-grid-renderer > #contents > ytd-rich-item-renderer {
  30. width: ${width} !important;
  31. margin: 5px !important;
  32. box-sizing: border-box !important;
  33. }
  34. ytd-continuation-item-renderer > #ghost-cards {
  35. display: none !important;
  36. }
  37. ytd-rich-grid-renderer #contents > ytd-continuation-item-renderer {
  38. flex: 0 0 100% !important;
  39. max-width: 100% !important;
  40. width: 100% !important;
  41. white-space: nowrap !important;
  42. box-sizing: border-box !important;
  43. }
  44. `;
  45. }
  46.  
  47. function createWidthControl() {
  48. if (document.getElementById(CONTROL_ID)) return null;
  49. const div = document.createElement('div');
  50. div.id = CONTROL_ID;
  51. div.style.cssText = 'display:flex;align-items:center;margin-left:12px;';
  52. const label = document.createElement('span');
  53. label.textContent = '';
  54. label.style.cssText = 'font-size:14px;font-family:Arial,sans-serif;color:#fff;margin-right:4px;';
  55. const input = document.createElement('input');
  56. input.id = 'tm-width-input';
  57. input.value = defaultWidth;
  58. input.style.cssText = 'width:60px;font-size:12px;padding:2px 4px;background:var(--yt-spec-brand-background-primary);border:1px solid var(--yt-spec-text-disabled);color:var(--yt-spec-text-primary);border-radius:2px;';
  59. input.title = 'e.g., 300px or 25%';
  60. input.addEventListener('change', () => {
  61. const w = input.value.trim();
  62. GM_setValue(STORAGE_KEY, w);
  63. updateWidthStyle(w);
  64. });
  65. div.appendChild(label);
  66. div.appendChild(input);
  67. return div;
  68. }
  69.  
  70. function insertControl() {
  71. const logoEl = document.querySelector('ytd-masthead ytd-topbar-logo-renderer');
  72. if (!logoEl) return false;
  73. const control = createWidthControl();
  74. if (!control) return true;
  75. logoEl.insertAdjacentElement('afterend', control);
  76. return true;
  77. }
  78.  
  79. const interval = setInterval(() => {
  80. if (insertControl()) clearInterval(interval);
  81. }, 500);
  82.  
  83. updateWidthStyle(GM_getValue(STORAGE_KEY, defaultWidth));
  84. })();