Greasy Fork is available in English.

YouTube Avatar Decorations

YouTube Avatars enhances the visual experience on YouTube by allowing users to customize their avatars on both channel and video pages.

  1. // ==UserScript==
  2. // @name YouTube Avatar Decorations
  3. // @name:tr YouTube Avatar Dekorasyonları
  4. // @name:de YouTube-Avatar-Dekorationen
  5. // @name:ru Украшения для аватаров YouTube
  6. // @name:es Decoraciones de avatares de YouTube
  7. // @name:zh-CN YouTube 头像装饰
  8. // @name:hi यूट्यूब अवतार सजावट
  9. // @name:fr Décorations d'avatar YouTube
  10. // @name:pt Decorações de avatar do YouTube
  11. // @name:ja YouTube アバターのデコレーション
  12. // @name:ko YouTube 아바타 장식
  13. // @name:ta YouTube அவதார் அலங்காரங்கள்
  14. // @name:hr Dekoracije YouTube avatara
  15. // @name:it Decorazioni per avatar di YouTube
  16. // @name:id Dekorasi Avatar YouTube
  17. // @name:tk YouTube Awatar bezegleri
  18. // @name:az YouTube Avatar Dekorasiyaları
  19. // @license MIT
  20. // @namespace http://tampermonkey.net/
  21. // @version 1.5
  22. // @description YouTube Avatars enhances the visual experience on YouTube by allowing users to customize their avatars on both channel and video pages.
  23. // @description:tr YouTube Avatarları, kullanıcıların hem kanal hem de video sayfalarında avatarlarını özelleştirmelerine olanak tanıyarak YouTube'daki görsel deneyimi geliştirir.
  24. // @description:de YouTube-Avatare verbessern das visuelle Erlebnis auf YouTube, indem sie es Benutzern ermöglichen, ihre Avatare sowohl auf Kanal- als auch auf Videoseiten anzupassen.
  25. // @description:ru Аватары YouTube улучшают визуальное восприятие YouTube, позволяя пользователям настраивать свои аватары как на страницах канала, так и на страницах видео.
  26. // @description:es YouTube Avatars mejora la experiencia visual en YouTube al permitir a los usuarios personalizar sus avatares tanto en el canal como en las páginas de video.
  27. // @description:zh-CN YouTube Avatars 允许用户在频道和视频页面上自定义自己的头像,从而增强了 YouTube 上的视觉体验。
  28. // @description:hi YouTube अवतार उपयोगकर्ताओं को चैनल और वीडियो पेज दोनों पर अपने अवतारों को अनुकूलित करने की अनुमति देकर YouTube पर दृश्य अनुभव को बढ़ाता है।
  29. // @description:fr YouTube Avatars améliore l'expérience visuelle sur YouTube en permettant aux utilisateurs de personnaliser leurs avatars sur les pages de la chaîne et des vidéos.
  30. // @description:pt Os Avatares do YouTube aprimoram a experiência visual no YouTube, permitindo que os usuários personalizem seus avatares nas páginas do canal e do vídeo.
  31. // @description:ja YouTube アバターは、ユーザーがチャンネルとビデオ ページの両方でアバターをカスタマイズできるようにすることで、YouTube でのビジュアル エクスペリエンスを強化します。
  32. // @description:ko YouTube 아바타는 사용자가 채널과 동영상 페이지 모두에서 아바타를 맞춤설정할 수 있도록 하여 YouTube의 시각적 경험을 향상시킵니다.
  33. // @description:ta சேனல் மற்றும் வீடியோ பக்கங்களில் பயனர்கள் தங்கள் அவதாரங்களைத் தனிப்பயனாக்க அனுமதிப்பதன் மூலம் YouTube அவதாரங்கள் YouTube இல் காட்சி அனுபவத்தை மேம்படுத்துகிறது.
  34. // @description:hr YouTube Avatari poboljšavaju vizualno iskustvo na YouTubeu dopuštajući korisnicima da prilagode svoje avatare na stranicama kanala i videozapisa.
  35. // @description:it Gli avatar di YouTube migliorano l'esperienza visiva su YouTube consentendo agli utenti di personalizzare i propri avatar sia sul canale che sulle pagine video.
  36. // @description:id Avatar YouTube meningkatkan pengalaman visual di YouTube dengan memungkinkan pengguna menyesuaikan avatar mereka di saluran dan laman video.
  37. // @description:tk “YouTube Avatars”, ulanyjylara awatarlaryny iki kanalda we wideo sahypalarynda sazlamaga mümkinçilik bermek bilen, YouTube-da görüş tejribesini ýokarlandyrýar.
  38. // @description:az YouTube Avatarları istifadəçilərə həm kanal, həm də video səhifələrində öz avatarlarını fərdiləşdirməyə imkan verməklə YouTube-da vizual təcrübəni artırır.
  39. // @author Phaticusthiccy
  40. // @icon https://i.hizliresim.com/723p62n.png
  41. // @match https://www.youtube.com/*
  42. // @supportURL https://github.com/phaticusthiccy/YoutubeAvatars/issues/new
  43. // @homepageURL https://github.com/phaticusthiccy/YoutubeAvatars
  44. // @grant none
  45. // ==/UserScript==
  46.  
  47. (function() {
  48. 'use strict';
  49.  
  50. const avatarCategories = {
  51. "General": [
  52. { name: "Glitch", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_e90ebc0114e7bdc30353c8b11953ea41.png?size=96&passthrough=true" },
  53. { name: "Cybernetics", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c6b3bc1dc49e5b284dca0b6437831004.png?size=96&passthrough=true" },
  54. { name: "Golden Crown", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_65db91cee351e36150a2b506b26eba71.png?size=96&passthrough=true" },
  55. { name: "Evil Crown", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_d1ea7b8650bf3d64a03304c2ceb7d089.png?size=96&passthrough=true" },
  56. { name: "Color Wave", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_49c479e15533fb4c02eb320c9c137433.png?size=96&passthrough=true" },
  57. { name: "Oasis", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_f740031cc97d1b7eb73c0d0ac1dd09f3.png?size=96&passthrough=true" },
  58. { name: "Rainy Mood", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_e8c11f139e55dac538cdaafb3caa2317.png?size=96&passthrough=true" },
  59. { name: "Doodle", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_5873ecaa76fb549654b40095293f902e.png?size=96&passthrough=true" },
  60. { name: "Green Smoke", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_10b9f886b513b77ccdd67c8784f1a496.png?size=96&passthrough=true" },
  61. { name: "Victory", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/Animation-1723308469539-ezgif.com-optipng.png", scale: 1.21 },
  62. { name: "Strings", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/strings.png", scale: 1.5 },
  63. { name: "Sketch Hat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/hat.png" },
  64. { name: "Robin Hood Hat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/robin_hood.png?raw=true" },
  65. { name: "Devil Horns", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/devil_horn.png" },
  66. { name: "Light Bulbs", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_88f42fb7360d8224a670a50c3496f315.png?size=96&passthrough=true" },
  67. ],
  68. "Valentine": [
  69. { name: "Angel", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c86b11a49bb8057ce9c974a6f7ad658a.png?size=96&passthrough=true" },
  70. { name: "In Love", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_7f44d538ec830f479605f7bf8720afda.png?size=96&passthrough=true" },
  71. { name: "Hearts", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_3e1fc3c7ee2e34e8176f4737427e8f4f.png?size=96&passthrough=true" },
  72. { name: "Sakura", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_13913a00bd9990ab4102a3bf069f0f3f.png?size=96&passthrough=true" },
  73. { name: "Sakura Warrior", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_7cf09c7e78d6eb35ae354acc1d5cc676.png?size=96&passthrough=true" },
  74. { name: "Fallen Leaves", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_7fecc9d20cbbf54644c9a532f7db4664.png?size=96&passthrough=true", left: "-1.8px" },
  75. { name: "Heart Lamps (Blue)", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_42cc3fe7133523096466102e7a222003.png?size=96&passthrough=true" },
  76. { name: "Heart Lamps (Red)", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_63a69109db554a66764cbe61c6e556ef.png?size=96&passthrough=true" },
  77. { name: "Fluffy Teddy Bear", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_555ad9b90a13534180b9274d013e3651.png?size=96&passthrough=true" },
  78. { name: "Heart Ring", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_a1c0581971d4a296908829289fea2c47.png?size=96&passthrough=true", scale: 1.09 },
  79.  
  80. ],
  81. "Animals": [
  82. { name: "Cat Ears", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c3cffc19e9784f7d0b005eecdf1b566e.png?size=96&passthrough=true" },
  83. { name: "Sleepy Cat", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_77b7b6a740a9451e1ef39c0252154ef8.png?size=96&passthrough=true" },
  84. { name: "Blob Cat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/blobcat.gif" },
  85. { name: "Space Whale", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/spcae_whale.gif", scale: 1.03 },
  86. ],
  87. "Anime": [
  88. { name: "Flying Hearts", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_8ffa2ba9bff18e96b76c2e66fd0d7fa3.png?size=96&passthrough=true" },
  89. { name: "Ki Energy", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_f3af281c65cf0cf590e9e1f59e9c6cf6.png?size=96&passthrough=true" },
  90. { name: "Gushing Energy", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c7e1751e8122f1b475cb3006966fb28c.png?size=96&passthrough=true" },
  91. { name: "Shocked", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_b98e8b204d59882fb7f9f7c86922c0bf.png?size=96&passthrough=true" },
  92. { name: 'Anger', url: 'https://cdn.discordapp.com/avatar-decoration-presets/a_3c97a2d37f433a7913a1c7b7a735d000.png?size=96&passthrough=true' },
  93. { name: "Starts", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_d72066b8cecbadd9fc951913ebcc384f.png?size=96&passthrough=true" },
  94. { name: "Soul", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c3c09bd122898be35093d0d59850f627.png?size=96&passthrough=true" },
  95. { name: "Cute Radish", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_89cd445201a0c6c64d46876503d0e90e.png?size=96&passthrough=true" },
  96. { name: "Sweat Drops", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_55c9d0354290afa8b7fe47ea9bd7dbcf.png?size=96&passthrough=true" },
  97. { name: "Cat Hat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/cat_hat.png?raw=true" },
  98. ],
  99. "Nature": [
  100. { name: "Flower Clouds", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_d9ff5ff133ed9176895a4a2b5e58f1b8.png?size=96&passthrough=true" },
  101. { name: "Rainbow", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_bba669bfb28f492b64852e00fde4989d.png?size=96&passthrough=true" },
  102. { name: "Patrick the Starfish", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_0f7fa66bc185c858f92a7918ea4dd47a.png?size=96&passthrough=true" },
  103. { name: "Gary the Snail", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_4db5b8518672197225c69fe72f07a945.png?size=96&passthrough=true" },
  104. { name: "Wind", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_554b7c34f7b6c709f19535aacb128e7b.png?size=96&passthrough=true" },
  105. { name: "Water", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_250640ab00a8837a1d56f35879138177.png?size=96&passthrough=true" },
  106. { name: "Butterfly", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_4cd9ae5a8d103c219eacd3674d7730cd.png?size=96&passthrough=true" },
  107. { name: "Lightening", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_365eed4178528fe8293c4212e8e2d5cb.png?size=96&passthrough=true" },
  108. { name: "Constellations", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_8552f9857793aed0cf816f370e2df3be.png?size=96&passthrough=true" },
  109. { name: "Blackhole", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_6d16b27d9415cafe3b289053644337c4.png?size=96&passthrough=true" },
  110. { name: "UFO", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_6fdbddb6229453eac3bbb212edf5cd1c.png?size=96&passthrough=true" },
  111. { name: "Neon Star", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/rotating_star.png?raw=true" },
  112. { name: "Daisy Ring", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/daisy_ring.png?raw=true" },
  113. { name: "Fire", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/circle_fire.gif?raw=true", scale: 1.7 },
  114. { name: "Roses", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/roses.gif?raw=true" },
  115. { name: "Fluid Silver", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/fluid_silver.gif?raw=true", scale: 1.21 },
  116. { name: "Acid", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/acid.webp?raw=true", scale: 1.45, top: "10px", left: "-2.5px", videoTop: "-5.7px", videoLeft: "-10.9px", videoScale: 1.3 },
  117. { name: "Falling Star", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/falling%20star.gif", scale: 1.45, top: "-5px", left: "-5px", videoTop: "-11px", videoLeft: "-10.9px", videoScale: 1.3 },
  118. { name: "Space Helmet", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_bb31faaec1be1ef5ff32dcdc5f37efbf.png?size=96&passthrough=true" },
  119. { name: "Snow Globe", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_85a8f9ca60cb4328378270a7f13ed7fd.png?size=96&passthrough=true" },
  120. ],
  121. "Mystic": [
  122. { name: "Spirit Sparks", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_1005898c6acf56a9ac5010baf444f6fd.png?size=96&passthrough=true" },
  123. { name: "Skull Medallion", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_9d67a1cbf81fe7197c871e94f619b04b.png?size=96&passthrough=true" },
  124. { name: "The Wand", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_db9baf0ba7cf449d2b027c06309dbe8d.png?size=96&passthrough=true" },
  125. { name: "Fairies", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_fe3c76cac2adf426832a7e495e8329d3.png?size=96&passthrough=true" },
  126. { name: "Blue Yonder", url: "https://cdn.cloudflare.steamstatic.com/steamcommunity/public/images/items/917950/9155ed2050954e8bd0e74f0f0dcfa0e96b37ec34.png" },
  127. { name: "Sparkles", url: "https://cdn.akamai.steamstatic.com/steamcommunity/public/images/items/1192640/6b555763a9ff0815cff7d45480f03ff4d1ca4ab3.png" },
  128. { name: "Divination", url: "https://cdn.akamai.steamstatic.com/steamcommunity/public/images/items/2271980/2727a0bbab23f6ecc60b86b2f4946bd31d986165.png" },
  129. { name: "Energy Ball", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/energy_ball.png" },
  130. { name: "Eyes", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/eyes.png?raw=true" },
  131. { name: "Devil", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/devil.png?raw=true" },
  132. { name: "Shining Star", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/final_light.png?raw=true" },
  133. { name: "Aetheria", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/aetheria2.gif?raw=true", scale: 1.4, videoScale: 1.2 },
  134. { name: "Shining Star 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/stars2.gif?raw=true" },
  135. ],
  136. "Games": [
  137. { name: "Valorant - Viper", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_62cd9d7c0031a7c1eb5ad5cc96992189.png?size=96&passthrough=true" },
  138. { name: "Valorant - Death", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_09de63526a45be1ddac70e84718ee04a.png?size=96&passthrough=true" },
  139. { name: "Valorant - Yoru", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_da532f804b47f1681006c2996eb07b2a.png?size=96&passthrough=true" },
  140. { name: "Valorant - Cypher", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_b1efe77f379c6c9c6e47e6b6299d5a7d.png?size=96&passthrough=true" },
  141. { name: "Valorant - Clove", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_98555e40cc6802bd3a4fed906af1d992.png?size=96&passthrough=true" },
  142. { name: "Valorant - Omen", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_c45abe8c7585fdb41b8d8d4d666f1588.png?size=96&passthrough=true" },
  143. { name: "Valorant - Reyna", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_a87e3efa4de2956331831681231ce63b.png?size=96&passthrough=true" },
  144. { name: "Valorant - Jett", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_904b1989077c91fca1168d39bfcaa0a4.png?size=96&passthrough=true" },
  145. { name: "Palworld - Chillet", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_48b8411feb1e80a69048fc65b3275b75.png?size=96&passthrough=true" },
  146. { name: "Palworld - Cattiva", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_d260c70fa8f38c499fa452c3cbdc5a0c.png?size=96&passthrough=true" },
  147. { name: "Palworld - Lamball", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_949a575b693c81ced8f56a7579d0969f.png?size=96&passthrough=true" },
  148. { name: "Palworld - Depresso", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_b7e2813fb97fe05b0f9f29a1bb7fde41.png?size=96&passthrough=true" },
  149. { name: "Palworld - Selyne", url: "https://cdn.discordapp.com/avatar-decoration-presets/a_0830085f29712a6f3a23a123302050b4.png?size=96&passthrough=true" },
  150. { name: "Starfield - Grav Wave", url: "https://cdn.akamai.steamstatic.com/steamcommunity/public/images/items/1716740/ff0e84c4996b1c9cb299ba2ab1c6454c5d129b49.png" },
  151. { name: "Genshin - Little Matron", url: "https://upload-os-bbs.hoyolab.com/upload/2024/07/22/d070e73b57eebc782658856f83400c0f_4985728381431752077.webp?x-oss-process=image/auto-orient,0/interlace,1/format,webp/quality,q_70" },
  152. { name: "Genshin - Lumine", url: "https://fastcdn.hoyoverse.com/static-resource-v2/2024/04/10/e0c33a668dfe55c3d28c153fd26d2566_7549684827555419407.webp?x-oss-process=image/auto-orient,0/interlace,1/format,webp/quality,q_70" },
  153. { name: "Honkai - Zhu Yuan", url: "https://upload-os-bbs.hoyolab.com/upload/2024/07/23/1b34e54ec5ac3fbe67c079dd29c5f632_5221289561156079104.webp?x-oss-process=image/auto-orient,0/interlace,1/format,webp/quality,q_70" },
  154. { name: "Honkai - Ellen", url: "https://upload-os-bbs.hoyolab.com/upload/2024/07/04/98126629588606c7ed379693c30b8c6c_1697937515325313185.webp?x-oss-process=image/auto-orient,0/interlace,1/format,webp/quality,q_70" },
  155. { name: "Minecraft - Cave", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/mc_cave.gif", scale: 1.08 },
  156. ],
  157. "Static Frames": [
  158. { name: "Neon 1", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static1.png" },
  159. { name: "Neon 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static2.png", scale: 1.21 },
  160. { name: "Neon 3", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static3.png", top: "5px", scale: 1.1, onlyChannel: true, videoTop: "-8px" },
  161. { name: "DTCQ", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static5.png", top: "5px", scale: 1.1, onlyChannel: true, videoTop: "-8px" },
  162. { name: "Lilith", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static6.png" },
  163. { name: "Valentine", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/static7.png", scale: 1.1 },
  164. { name: "Jellyfish", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/jelly.png" },
  165. { name: "Burger", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/burger.png", scale: 1.19, dontScaleVideos: true },
  166. { name: "Glitch 1", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/glitch.png", scale: 1.3 },
  167. { name: "Glitch 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/glitch2.png", scale: 1.3 },
  168. { name: "Cute Doodles", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/cute_doodles.png", scale: 1.4 },
  169. { name: "Love Letter", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/love_letter.png", scale: 1.4 },
  170. { name: "Pink Ribbon", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/ribbon.png", scale: 1.1 },
  171. { name: "Arrival Movie 1", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/arrival.png", scale: 1.2, onlyChannel: true, top: "4px", left: "4px", darkMode: true },
  172. { name: "Arrival Movie 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/arrival2.png", scale: 1.1, onlyChannel: true, top: "7px", darkMode: true },
  173. { name: "Arrival Movie 3", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/arrival3.png", scale: 1.2, left: "5px", darkMode: true },
  174. { name: "Valentine 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/val2.png", scale: 1.1 },
  175. { name: "Halloween", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/halloween.png", scale: 1.1 },
  176. { name: "Halloween 2", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/halloween2.png", scale: 1.1 },
  177. { name: "Valentine 3", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/val3.png", scale: 1.1 },
  178. { name: "Pink Sea", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/pink_sea.gif", scale: 1.21 },
  179. { name: "Saturn", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/saturn.png", scale: 1.5 },
  180. { name: "Ghost Cat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/ghost_cat.gif" },
  181. { name: "Fantasy Nature", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/fantasy_nature.png" },
  182. { name: "Fantasy Fire", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/fantasy_fire.png" },
  183. { name: "Fantasy Sea", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/fantasy_sea.png" },
  184. { name: "Fantasy Dark", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/fantasy_dark.png" },
  185. { name: "Dark Cat", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/dark_cat.png", top: "5px", scale: 1.1 },
  186. { name: "Headset", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/headset.png" },
  187. { name: "Detective", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/detective.png", scale: 1.1 },
  188. { name: "Lying Figures", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lying_figures.png?raw=true", top: "-2px", scale: 1.03 },
  189. { name: "Unicorn", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/unicorn.png?raw=true" },
  190. { name: "Panda", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/panda.png?raw=true", top: "-3px" },
  191. { name: "LGBT Transsexual", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgbt_trans.png", scale: 0.9 },
  192. { name: "LGBT Lesbian", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgnt_les.png", scale: 1.04 },
  193. { name: "LGBT Femboy", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgbt_femboy.png", scale: 0.9 },
  194. { name: "LGBT Non-Binary", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgbt_nonb.png", scale: 0.9 },
  195. { name: "LGBT Pride", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgbt_pride.png", scale: 0.9 },
  196. { name: "LGBT Gay", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/lgbt_gay.png", scale: 0.9 },
  197. ],
  198. "AI Static": [
  199. { name: "AI Flowers", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/flowers.png", videoLeft: "-11.3px", left: "-6px", scale:1.12 },
  200. { name: "Pikachu", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/pikachu.png", scale: 1.21, left: "-2px" },
  201. ],
  202. "Experimental": [
  203. { name: "Valorant - Clove HQ", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/clove_2.gif", top: "-10px" },
  204. { name: "Magic HQ", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/magic.gif", top: "-12px", scale: 1.3 },
  205. { name: "Cute Anime", url: "https://raw.githubusercontent.com/phaticusthiccy/phaticusthiccy/main/youtube_animated_avatars/cute_anime.gif", top: "-8px", scale: 1.4, left: "-8px", videoTop: "-11.2px" },
  206. ]
  207. };
  208.  
  209. for (let _category in avatarCategories) {
  210. avatarCategories[_category].sort((a, b) => a.name.localeCompare(b.name));
  211. }
  212.  
  213. let selectedAvatarUrl = localStorage.getItem('selectedAvatar') || '';
  214. let selectedCategory = ""
  215.  
  216. function saveSelectedAvatar(url, category) {
  217. localStorage.setItem('selectedAvatar', url);
  218. localStorage.setItem('selectedMenu', category);
  219. selectedAvatarUrl = url;
  220. selectedCategory = category;
  221. }
  222.  
  223. function getSelectedAvatar() {
  224. return localStorage.getItem('selectedAvatar') || '';
  225. }
  226.  
  227. function getSelectedMenu() {
  228. return localStorage.getItem('selectedMenu');
  229. }
  230.  
  231. function categoryContainsSelectedAvatar(category, selectedAvatar) {
  232. return avatarCategories[category].some(avatar => avatar.url === selectedAvatar);
  233. }
  234.  
  235. function isValidUrl() {
  236. const currentUrl = document.location.href.split(".com/")[1];
  237. return currentUrl.startsWith("@") || currentUrl.startsWith("watch") || currentUrl.startsWith("c/") || currentUrl.startsWith("channel/");
  238. }
  239.  
  240. function isChannel() {
  241. const currentUrl = document.location.href.split(".com/")[1];
  242. return currentUrl.startsWith("@") || currentUrl.startsWith("c/") || currentUrl.startsWith("channel/");
  243. }
  244.  
  245. function isYouTubeDarkMode() {
  246. try {
  247. function isDarkColor(color) {
  248. const rgb = color.match(/\d+/g);
  249. if (rgb) {
  250. const [r, g, b] = rgb.map(Number);
  251. const brightness = (r * 299 + g * 587 + b * 114) / 1000;
  252. return brightness < 128;
  253. }
  254. return false;
  255. }
  256.  
  257. const appContainer = document.querySelector('ytd-app');
  258. if (appContainer) {
  259. const bgColor = window.getComputedStyle(appContainer).backgroundColor;
  260. return isDarkColor(bgColor);
  261. }
  262.  
  263. const bodyBgColor = window.getComputedStyle(document.body).backgroundColor;
  264. return isDarkColor(bodyBgColor);
  265. } catch {
  266. return false
  267. }
  268. }
  269.  
  270. var searchTerm = ""
  271.  
  272. function createMenu(idName = "") {
  273. /*if (document.getElementById('avatar-menu2')) {
  274. return;
  275. }*/
  276.  
  277. var menu;
  278. if (document.getElementById('avatar-menu2')) {
  279. menu = document.getElementById('avatar-menu2')
  280. return menu
  281. } else {
  282. menu = document.createElement('div');
  283. };
  284.  
  285. menu.id = idName == "" ? 'avatar-menu' : idName;
  286. menu.style.position = 'absolute';
  287. menu.style.backgroundColor = '#fff';
  288. menu.style.border = '1px solid #ccc';
  289. menu.style.padding = '23px';
  290. menu.style.boxShadow = '0 4px 12px rgba(0,0,0,0.2)';
  291. menu.style.borderRadius = '8px';
  292. menu.style.zIndex = '9999';
  293. menu.style.display = 'none';
  294. menu.style.transition = 'opacity 0.3s ease';
  295. menu.style.opacity = '0';
  296. menu.style.maxHeight = '500px';
  297. menu.style.overflowY = 'auto';
  298. menu.style.overflowX = 'hidden';
  299. menu.style.minWidth = '250px';
  300. menu.style.fontSize = '14px';
  301. menu.style.userSelect = 'none';
  302.  
  303.  
  304. const searchInput = document.createElement('input');
  305. searchInput.type = 'text';
  306. searchInput.placeholder = 'Search Effect...';
  307. searchInput.style.width = '100%';
  308. searchInput.style.padding = '10px';
  309. searchInput.style.marginBottom = '10px';
  310. searchInput.style.minWidth = '250px';
  311. searchInput.style.border = 'none';
  312. searchInput.style.outline = 'none';
  313. searchInput.style.boxShadow = 'none';
  314.  
  315. searchInput.addEventListener('focus', () => {
  316. searchInput.style.border = 'none';
  317. searchInput.style.outline = 'none';
  318. searchInput.style.boxShadow = 'none';
  319. });
  320.  
  321. searchInput.addEventListener('blur', () => {
  322. searchInput.style.border = 'none';
  323. searchInput.style.outline = 'none';
  324. searchInput.style.boxShadow = 'none';
  325. });
  326.  
  327.  
  328. searchInput.addEventListener('input', (event) => {
  329. const searchTerm = event.target.value.toLowerCase();
  330. menu.querySelectorAll('div > div > div').forEach((item) => {
  331. if (searchTerm === '') {
  332. item.style.display = '';
  333. item.parentElement.style.display = 'none';
  334. item.parentElement.parentElement.style.display = 'block';
  335. //item.parentElement.parentElement.children[1].style.display = 'none';
  336. } else if (item.textContent.toLowerCase().includes(searchTerm)) {
  337. item.style.display = "block"
  338. item.parentElement.style.display = 'block';
  339. item.parentElement.parentElement.style.display = 'block';
  340. item.parentElement.parentElement.children[1].style.display = 'block';
  341. } else {
  342. item.style.display = 'none';
  343. }
  344. });
  345. });
  346.  
  347. menu.insertBefore(searchInput, menu.firstChild);
  348.  
  349. const selectedAvatar = getSelectedAvatar();
  350. const selectedCategory = getSelectedMenu();
  351.  
  352. for (const [category, avatars] of Object.entries(avatarCategories)) {
  353. const categoryDiv = document.createElement('div');
  354. categoryDiv.style.marginBottom = '15px';
  355.  
  356. const categoryTitle = document.createElement('div');
  357. categoryTitle.textContent = category;
  358. categoryTitle.style.fontWeight = 'bold';
  359. categoryTitle.style.marginBottom = '8px';
  360. categoryTitle.style.cursor = 'pointer';
  361. categoryTitle.style.padding = '8px';
  362. categoryTitle.style.backgroundColor = '#f0f0f0';
  363. categoryTitle.style.borderRadius = '4px';
  364.  
  365.  
  366. if (categoryContainsSelectedAvatar(category, selectedAvatar) == true) {
  367. categoryTitle.style.color = '#369626';
  368. }
  369.  
  370. const avatarList = document.createElement('div');
  371. avatarList.style.display = 'none';
  372. avatarList.style.paddingLeft = '15px';
  373.  
  374. categoryTitle.addEventListener('click', (event) => {
  375. avatarList.style.display = avatarList.style.display === 'none' ? 'block' : 'none';
  376. event.stopPropagation();
  377. });
  378.  
  379. avatars.forEach(avatar => {
  380. const item = document.createElement('div');
  381. item.style.padding = '10px';
  382. item.style.cursor = 'pointer';
  383. item.style.borderBottom = '1px solid #eee';
  384. item.style.transition = 'background-color 0.2s';
  385. item.style.display = 'flex';
  386. item.style.alignItems = 'center';
  387. item.style.position = 'relative';
  388.  
  389. const avatarName = document.createElement('span');
  390. avatarName.textContent = avatar.name;
  391. avatarName.style.flexGrow = '1';
  392.  
  393.  
  394. const previewImg = document.createElement('img');
  395. previewImg.style.width = '30px';
  396. previewImg.style.height = '30px';
  397. previewImg.style.marginLeft = '20px';
  398. previewImg.style.marginRight = '25px';
  399. previewImg.style.display = 'none';
  400. previewImg.style.position = 'absolute';
  401. previewImg.style.right = '0';
  402. previewImg.style.top = '50%';
  403. previewImg.style.transform = 'translateY(-50%)';
  404.  
  405. item.appendChild(avatarName);
  406. item.appendChild(previewImg);
  407.  
  408. item.addEventListener('mouseenter', () => {
  409. item.style.backgroundColor = '#f5f5f5';
  410. item.style.transform = 'scale(1.2)';
  411. item.style.transition = 'transform 0.2s ease';
  412. item.style.zIndex = '100';
  413. previewImg.style.display = 'block';
  414.  
  415. if (!previewImg.src) {
  416. previewImg.src = avatar.url;
  417. }
  418. previewImg.style.display = 'block';
  419.  
  420. });
  421. item.addEventListener('mouseleave', () => {
  422. item.style.backgroundColor = '#fff';
  423. item.style.transform = 'scale(1)';
  424. item.style.transition = 'transform 0.2s ease';
  425. item.style.zIndex = '0';
  426. previewImg.style.display = 'none';
  427. });
  428.  
  429. item.addEventListener('click', () => {
  430.  
  431. var selectedAvatar2 = avatar.url
  432. var selectedCategory2 = findCategoryByUrl(selectedAvatar2, avatarCategories)
  433.  
  434. if (selectedAvatar2 && selectedCategory2) {
  435. var effectName = document.querySelector("#selectedEffectName")
  436. if (effectName) {
  437. let findAvatarName = avatarCategories[selectedCategory2].find((avatar3) => avatar3.url == selectedAvatar2)
  438. effectName.textContent = `${selectedCategory2} ${findAvatarName.name}`
  439. } else {
  440. let selectedAvatarInfo = document.createElement('div');
  441. selectedAvatarInfo.style.fontWeight = 'bold';
  442. selectedAvatarInfo.style.marginBottom = '10px';
  443. selectedAvatarInfo.style.textAlign = "center"
  444. selectedAvatarInfo.style.color = "#369626"
  445. selectedAvatarInfo.id = "selectedEffectName"
  446. let findAvatarName = avatarCategories[selectedCategory2].find((avatar3) => avatar3.url == selectedAvatar2)
  447. selectedAvatarInfo.textContent = `${selectedCategory2} ${findAvatarName.name}`
  448. menu.insertBefore(selectedAvatarInfo, menu.firstChild);
  449. }
  450. }
  451.  
  452. applyAvatar(avatar.url);
  453. saveSelectedAvatar(avatar.url, category);
  454. updateMenu(menu);
  455. //menu.style.opacity = '0';
  456. //setTimeout(() => menu.style.display = 'none', 300);
  457. });
  458. item.addEventListener('mouseover', () => {
  459. item.style.backgroundColor = '#f5f5f5';
  460. });
  461. item.addEventListener('mouseout', () => {
  462. item.style.backgroundColor = '#fff';
  463. });
  464. avatarList.appendChild(item);
  465. });
  466.  
  467. categoryDiv.appendChild(categoryTitle);
  468. categoryDiv.appendChild(avatarList);
  469. menu.appendChild(categoryDiv);
  470. }
  471.  
  472. const removeItem = document.createElement('div');
  473. removeItem.style.padding = '10px';
  474. removeItem.style.cursor = 'pointer';
  475. removeItem.style.borderTop = '1px solid #eee';
  476. removeItem.style.color = '#ff4d4d';
  477. removeItem.style.fontWeight = 'bold';
  478. removeItem.textContent = 'Remove';
  479. removeItem.style.textAlign = "center"
  480. removeItem.addEventListener('click', () => {
  481. var effectName = document.querySelector("#selectedEffectName")
  482. if (effectName) effectName.remove()
  483. removeAvatar();
  484. saveSelectedAvatar('', '');
  485. updateMenu(menu);
  486. menu.style.opacity = '0';
  487. setTimeout(() => menu.style.display = 'none', 300);
  488. });
  489. removeItem.addEventListener('mouseover', () => {
  490. removeItem.style.backgroundColor = '#f5f5f5';
  491. });
  492. removeItem.addEventListener('mouseout', () => {
  493. removeItem.style.backgroundColor = '#fff';
  494. });
  495. menu.appendChild(removeItem);
  496.  
  497. removeItem.addEventListener('mouseenter', () => {
  498. removeItem.style.backgroundColor = '#f5f5f5';
  499. removeItem.style.transform = 'scale(1.2)';
  500. removeItem.style.transition = 'transform 0.2s ease';
  501. removeItem.style.zIndex = '100';
  502. });
  503. removeItem.addEventListener('mouseleave', () => {
  504. removeItem.style.backgroundColor = '#fff';
  505. removeItem.style.transform = 'scale(1)';
  506. removeItem.style.transition = 'transform 0.2s ease';
  507. removeItem.style.zIndex = '0';
  508. });
  509.  
  510. document.body.appendChild(menu);
  511.  
  512. document.addEventListener('click', (event) => {
  513. if (menu.style.display === 'block' && !menu.contains(event.target) && event.target.id !== 'avatar-icon') {
  514. menu.style.opacity = '0';
  515. setTimeout(() => menu.style.display = 'none', 300);
  516. }
  517. });
  518.  
  519. try {
  520. if (selectedAvatar && selectedCategory) {
  521. const selectedAvatarInfo = document.createElement('div');
  522. selectedAvatarInfo.style.fontWeight = 'bold';
  523. selectedAvatarInfo.style.marginBottom = '10px';
  524. selectedAvatarInfo.style.textAlign = "center"
  525. selectedAvatarInfo.style.color = "#369626"
  526. selectedAvatarInfo.id = "selectedEffectName"
  527. var findAvatarName = avatarCategories[selectedCategory].find((avatar) => avatar.url == selectedAvatar)
  528. selectedAvatarInfo.textContent = `${selectedCategory} ${findAvatarName.name}`;
  529. menu.insertBefore(selectedAvatarInfo, menu.firstChild);
  530. }
  531. } catch {}
  532.  
  533. return menu;
  534. }
  535.  
  536. function updateMenu(menu) {
  537. const selectedAvatar = getSelectedAvatar();
  538. menu.querySelectorAll('div > div').forEach((item) => {
  539. if (item.style.padding === '8px') {
  540. item.style.color = '';
  541. }
  542. });
  543. }
  544.  
  545. function findCategoryByUrl(url, avatarCategories) {
  546. for (let category in avatarCategories) {
  547. for (let item of avatarCategories[category]) {
  548. if (item.url === url) {
  549. return category;
  550. }
  551. }
  552. }
  553. return null;
  554. }
  555.  
  556. function applyAvatar(url) {
  557. if (!isValidUrl() || !url) return;
  558.  
  559. if (isChannel()) {
  560. applyChannelAvatar(url);
  561. } else {
  562. applyVideoAvatar(url);
  563. }
  564. }
  565.  
  566. function applyChannelAvatar(url) {
  567. const avatarShape = document.querySelector('yt-avatar-shape');
  568. const findAvatarByURL = (url) => {
  569. for (const category in avatarCategories) {
  570. const avatar = avatarCategories[category].find((avatar) => avatar.url === url);
  571. if (avatar) return avatar;
  572. }
  573. return {};
  574. };
  575. if (avatarShape) {
  576.  
  577. var channelFind = findAvatarByURL(url)
  578. var channelTop = channelFind.top == undefined ? "0" : String(channelFind.top);
  579. var channelScale = channelFind.scale == undefined ? 'none' : String(channelFind.scale);
  580. var channelFilter = channelFind.darkMode == true ? isYouTubeDarkMode() == true ? "invert(1)" : "none" : "none"
  581. var channelLeft = channelFind.left == undefined ? '0' : String(channelFind.left);
  582.  
  583. let gifWrapper = avatarShape.querySelector('#gif-wrapper');
  584. if (!gifWrapper) {
  585. gifWrapper = document.createElement('div');
  586. gifWrapper.id = 'gif-wrapper';
  587. gifWrapper.style.position = 'absolute';
  588. gifWrapper.style.width = '160px';
  589. gifWrapper.style.height = '160px';
  590. gifWrapper.style.zIndex = '10';
  591. gifWrapper.style.scale = '1.21';
  592.  
  593. const gifElement = document.createElement('img');
  594. gifElement.id = 'gif-element';
  595. gifElement.style.position = 'absolute';
  596. gifElement.style.top = channelTop
  597. gifElement.style.left = channelLeft
  598. gifElement.style.width = '100%';
  599. gifElement.style.height = '100%';
  600. gifElement.style.zIndex = '10';
  601. gifElement.style.scale = channelScale
  602. gifElement.style.filter = channelFilter
  603.  
  604. gifWrapper.appendChild(gifElement);
  605. avatarShape.insertBefore(gifWrapper, avatarShape.firstChild);
  606. }
  607. const gifElement = gifWrapper.querySelector('#gif-element');
  608. if (gifElement.src !== url) {
  609. gifElement.src = url;
  610. gifElement.style.scale = channelScale
  611. gifElement.style.top = channelTop
  612. gifElement.style.filter = channelFilter
  613. gifElement.style.left = channelLeft
  614. }
  615. }
  616. }
  617.  
  618. function applyVideoAvatar(url) {
  619. const findAvatarByURL = (url) => {
  620. for (const category in avatarCategories) {
  621. const avatar = avatarCategories[category].find((avatar) => avatar.url === url);
  622. if (avatar) return avatar;
  623. }
  624. return {};
  625. };
  626. const avatar = document.querySelector('#avatar');
  627.  
  628. var objectAvatar = findAvatarByURL(url)
  629. var videoTop = objectAvatar.videoTop == undefined ? objectAvatar.top == undefined ? "-10px" : objectAvatar.onlyChannel == true ? objectAvatar.videoTop == undefined ? "-10px" : objectAvatar.videoTop : String(objectAvatar.top) : objectAvatar.videoTop;
  630. var videoScale = objectAvatar.videoScale == undefined ? objectAvatar.scale == undefined ? 'none' : objectAvatar.dontScaleVideos == true ? 'none' : String(objectAvatar.scale) : String(objectAvatar.videoScale);
  631. var videoFilter = objectAvatar.darkMode == true ? isYouTubeDarkMode() == true ? "invert(1)" : "none" : "none"
  632. var videoLeft = objectAvatar.videoLeft == undefined ? '-10px' : String(objectAvatar.videoLeft);
  633.  
  634. if (avatar) {
  635. let uploadInfo = document.querySelector('#upload-info');
  636. if (uploadInfo) {
  637. uploadInfo.style.position = 'relative';
  638. uploadInfo.style.left = '10px';
  639. }
  640.  
  641. let gifWrapper = document.querySelector('#gif-wrapper');
  642. if (!gifWrapper) {
  643. gifWrapper = document.createElement('div');
  644. gifWrapper.id = 'gif-wrapper';
  645. gifWrapper.style.position = 'relative';
  646. gifWrapper.style.width = '40px';
  647. gifWrapper.style.height = '40px';
  648. gifWrapper.style.zIndex = '10';
  649.  
  650. let gifElement = document.createElement('img');
  651. gifElement.id = 'gif-element';
  652. gifElement.style.position = 'absolute';
  653. gifElement.style.left = videoLeft
  654. gifElement.style.width = '60px';
  655. gifElement.style.height = '60px';
  656. gifElement.style.zIndex = '10';
  657. gifElement.style.scale = videoScale
  658. gifElement.style.top = videoTop
  659. gifElement.style.filter = videoFilter
  660.  
  661. gifWrapper.appendChild(gifElement);
  662. avatar.parentElement.insertBefore(gifWrapper, avatar);
  663. gifWrapper.appendChild(avatar);
  664. }
  665. let gifElement = document.querySelector('#gif-element');
  666. if (gifElement.src !== url) {
  667. gifElement.src = url;
  668. gifElement.style.scale = videoScale
  669. gifElement.style.top = videoTop
  670. gifElement.style.filter = videoFilter
  671. gifElement.style.left = videoLeft
  672. }
  673. }
  674.  
  675. const avatar2 = document.querySelector('a.yt-simple-endpoint.style-scope.ytd-video-owner-renderer #avatar');
  676. if (avatar2) {
  677. let uploadInfo = document.querySelector('#upload-info');
  678. if (uploadInfo) {
  679. uploadInfo.style.position = 'relative';
  680. uploadInfo.style.left = '10px';
  681. }
  682.  
  683. let gifWrapper = document.querySelector('#gif-wrapper');
  684. if (!gifWrapper) {
  685. gifWrapper = document.createElement('div');
  686. gifWrapper.id = 'gif-wrapper';
  687. gifWrapper.style.position = 'relative';
  688. gifWrapper.style.width = '40px';
  689. gifWrapper.style.height = '40px';
  690. gifWrapper.style.zIndex = '10';
  691.  
  692. let gifElement = document.createElement('img');
  693. gifElement.id = 'gif-element';
  694. gifElement.style.position = 'absolute';
  695. gifElement.style.left = videoLeft
  696. gifElement.style.width = '60px';
  697. gifElement.style.height = '60px';
  698. gifElement.style.zIndex = '10';
  699. gifElement.style.scale = videoScale
  700. gifElement.style.top = videoTop
  701. gifElement.style.filter = videoFilter
  702.  
  703. gifWrapper.appendChild(gifElement);
  704. avatar2.parentElement.insertBefore(gifWrapper, avatar2);
  705. gifWrapper.appendChild(avatar2);
  706. }
  707. let gifElement = document.querySelector('#gif-element');
  708. if (gifElement.src !== url) {
  709. gifElement.src = url;
  710. gifElement.style.scale = videoScale
  711. gifElement.style.top = videoTop
  712. gifElement.style.filter = videoFilter
  713. gifElement.style.left = videoLeft
  714. }
  715. }
  716.  
  717. const avatar3 = document.querySelector("ytd-watch-flexy a.yt-simple-endpoint.style-scope.ytd-video-owner-renderer #avatar")
  718. if (avatar3) {
  719. let uploadInfo = document.querySelector('#upload-info');
  720. if (uploadInfo) {
  721. uploadInfo.style.position = 'relative';
  722. uploadInfo.style.left = '10px';
  723. }
  724.  
  725. let gifWrapper = document.querySelector('#gif-wrapper');
  726. if (!gifWrapper) {
  727. gifWrapper = document.createElement('div');
  728. gifWrapper.id = 'gif-wrapper';
  729. gifWrapper.style.position = 'relative';
  730. gifWrapper.style.width = '40px';
  731. gifWrapper.style.height = '40px';
  732. gifWrapper.style.zIndex = '10';
  733.  
  734. let gifElement = document.createElement('img');
  735. gifElement.id = 'gif-element';
  736. gifElement.style.position = 'absolute';
  737. gifElement.style.left = videoLeft
  738. gifElement.style.width = '60px';
  739. gifElement.style.height = '60px';
  740. gifElement.style.zIndex = '10';
  741. gifElement.style.scale = videoScale
  742. gifElement.style.top = videoTop
  743. gifElement.style.filter = videoFilter
  744.  
  745. gifWrapper.appendChild(gifElement);
  746. avatar3.parentElement.insertBefore(gifWrapper, avatar3);
  747. gifWrapper.appendChild(avatar3);
  748. }
  749. let gifElement = document.querySelector('#gif-element');
  750. if (gifElement.src !== url) {
  751. gifElement.src = url;
  752. gifElement.style.scale = videoScale
  753. gifElement.style.top = videoTop
  754. gifElement.style.filter = videoFilter
  755. gifElement.style.left = videoLeft
  756. }
  757. }
  758. }
  759.  
  760. function removeAvatar() {
  761. if (isChannel()) {
  762. const gifWrapper = document.querySelector('yt-avatar-shape #gif-wrapper');
  763. if (gifWrapper) {
  764. gifWrapper.remove();
  765. }
  766. } else {
  767. const gifWrapper = document.querySelector('#gif-wrapper');
  768. if (gifWrapper) {
  769. const uploadInfo = document.querySelector('#upload-info');
  770. if (uploadInfo) {
  771. uploadInfo.style.position = 'relative';
  772. uploadInfo.style.left = '0px';
  773. }
  774. const avatar = gifWrapper.querySelector('#avatar');
  775. gifWrapper.parentElement.insertBefore(avatar, gifWrapper);
  776. gifWrapper.remove();
  777. }
  778. }
  779. }
  780.  
  781. function addIcon() {
  782. const topBar = document.querySelector('ytd-topbar-menu-button-renderer');
  783. if (topBar && !document.querySelector('#avatar-icon')) {
  784. const iconWrapper = document.createElement('div');
  785. iconWrapper.style.display = 'flex';
  786. iconWrapper.style.alignItems = 'center';
  787.  
  788. const icon = document.createElement('img');
  789. icon.id = 'avatar-icon';
  790. icon.src = 'https://cdn.iconscout.com/icon/free/png-512/free-settings-2856913-2377697.png?f=webp&w=256';
  791. icon.style.width = '24px';
  792. icon.style.height = '24px';
  793. icon.style.cursor = 'pointer';
  794. icon.style.marginRight = '10px';
  795. icon.style.userSelect = 'none';
  796.  
  797. icon.addEventListener('click', () => {
  798. const menu = createMenu("avatar-menu2");
  799. function showToast(message) {
  800. const toast = document.createElement('div');
  801. toast.textContent = message;
  802. toast.style.position = 'fixed';
  803. toast.style["font-size"] = "larger";
  804. toast.style.top = '60px';
  805. toast.style.right = '20px';
  806. toast.style.backgroundColor = 'rgba(0, 0, 0, 0.7)';
  807. toast.style.color = 'white';
  808. toast.style.padding = '10px 20px';
  809. toast.style.borderRadius = '5px';
  810. toast.style.zIndex = '9999';
  811. toast.style.transition = 'opacity 0.5s';
  812.  
  813. document.body.appendChild(toast);
  814.  
  815. setTimeout(() => {
  816. toast.style.opacity = '0';
  817. setTimeout(() => {
  818. document.body.removeChild(toast);
  819. }, 500);
  820. }, 3000);
  821. }
  822.  
  823. if (!isValidUrl()) {
  824. showToast("You can only use this while watching a video or on a channel page");
  825. return;
  826. }
  827.  
  828. if (menu.style.display === 'none') {
  829. updateMenu(menu);
  830. menu.style.display = 'block';
  831. setTimeout(() => menu.style.opacity = '1', 0);
  832. const rect = icon.getBoundingClientRect();
  833.  
  834. const topOffset = rect.bottom + window.scrollY + (rect.height * 1.25);
  835. const leftOffset = rect.left + window.scrollX - (rect.width * 0.5);
  836.  
  837. menu.style.top = topOffset + "px"
  838. menu.style.left = `82%`;
  839. } else {
  840. menu.style.opacity = '0';
  841. setTimeout(() => menu.style.display = 'none', 300);
  842. }
  843. });
  844.  
  845. iconWrapper.appendChild(icon);
  846. topBar.parentElement.insertBefore(iconWrapper, topBar);
  847. }
  848. }
  849.  
  850. function applyStoredAvatar() {
  851. const selectedAvatar = getSelectedAvatar();
  852. if (selectedAvatar) {
  853. applyAvatar(selectedAvatar);
  854. }
  855. }
  856.  
  857. function keepAlive() {
  858. setInterval(() => {
  859. addIcon();
  860. //createMenu();
  861. }, 2000)
  862. }
  863.  
  864. function checkForTopBar() {
  865. const observer = new MutationObserver((mutations, obs) => {
  866. if (document.querySelector('ytd-topbar-menu-button-renderer')) {
  867. addIcon();
  868. applyStoredAvatar();
  869. obs.disconnect();
  870. }
  871. });
  872.  
  873. observer.observe(document, {
  874. childList: true,
  875. subtree: true
  876. });
  877. }
  878.  
  879. function checkForChannelAvatar() {
  880. const observer = new MutationObserver((mutations, obs) => {
  881. if (document.querySelector('yt-avatar-shape')) {
  882. applyStoredAvatar();
  883. obs.disconnect();
  884. }
  885. });
  886.  
  887. observer.observe(document, {
  888. childList: true,
  889. subtree: true
  890. });
  891. }
  892.  
  893. function observeUrlChange() {
  894. let lastUrl = location.href;
  895. new MutationObserver(() => {
  896. const url = location.href;
  897. if (url !== lastUrl) {
  898. lastUrl = url;
  899. onUrlChange();
  900. }
  901. }).observe(document, { subtree: true, childList: true });
  902. }
  903.  
  904. function onUrlChange() {
  905. if (!isValidUrl()) return;
  906. if (document.location.href.includes("index=") || document.location.href.includes("list=")) {
  907. true;
  908. } else {
  909. location.reload(true);
  910. }
  911. const selectedAvatar = getSelectedAvatar();
  912. if (selectedAvatar) {
  913. applyAvatar(selectedAvatar);
  914. }
  915. }
  916.  
  917. function init() {
  918. checkForTopBar();
  919. const selectedAvatar = getSelectedAvatar();
  920. if (selectedAvatar) {
  921. checkForChannelAvatar();
  922. }
  923. observeUrlChange();
  924. keepAlive();
  925. }
  926.  
  927. function checkAndApplyChannelAvatar() {
  928. if (!isValidUrl()) return;
  929. const selectedAvatar = getSelectedAvatar();
  930. if (selectedAvatar) {
  931. if (isChannel()) {
  932. const avatarShape = document.querySelector('yt-avatar-shape');
  933. if (avatarShape) {
  934. const gifElement = avatarShape.querySelector('#gif-element');
  935. if (!gifElement) {
  936. applyChannelAvatar(selectedAvatar);
  937. }
  938. }
  939. } else {
  940. applyVideoAvatar(selectedAvatar);
  941. }
  942. }
  943. }
  944.  
  945. //setInterval(checkAndApplyChannelAvatar, 500);
  946. init();
  947. window.addEventListener('load', init);
  948. })();