// ==UserScript== // @name 视频广告水印去除器 // @namespace https://example.com // @version 1.0 // @description 去除视频播放器的跑马灯广告、中间广告、左右下角水印广告 // @author You // @match *://*.iqiyi.com/* // @match *://*.youku.com/* // @match *://*.tencent.com/* // @match *://*.bilibili.com/* // @match *://*.douyin.com/* // @match *://*.baidu.com/* // @match *://v.qq.com/* // @match *://*.mgtv.com/* // @match *://*.toutiao.com/* // @match *://*.kuaishou.com/* // @grant none // @run-at document-idle // @license MIT // ==/UserScript== (function() { 'use strict'; // 配置区域 const CONFIG = { // 通用广告类名关键词 adKeywords: [ 'ad-', 'ad_', 'advert', 'ads-', 'ads_', 'watermark', 'logo-ad', 'marquee', 'scroll-ad', 'banner-ad', 'popup-ad', 'float-ad', 'drift-ad' ], // 水印类名关键词 watermarkKeywords: [ 'watermark', 'logo-watermark', 'video-logo', 'corner-logo', 'site-logo', 'brand-logo', 'qiyi-logo', 'youku-logo', 'tencent-logo', 'bilibili-logo' ], // 跑马灯广告类名关键词 marqueeKeywords: [ 'marquee', 'scroll-text', 'moving-text', 'drift-text', 'notice-scroll', 'promo-scroll', 'coupon-scroll' ], // 间隔检测时间(毫秒) checkInterval: 500, // 是否显示调试信息 debug: false }; // 日志函数 function log(message) { if (CONFIG.debug) { console.log('[广告去除器]', message); } } // 通用广告选择器 function getCommonAdSelectors() { return [ // 通用广告容器 '[class*="ad-container"]', '[class*="ad-wrap"]', '[class*="ad-wrapper"]', '[class*="advertisement"]', // 水印相关 '[class*="watermark"]', '[class*="logo-watermark"]', '[class*="corner-watermark"]', '[class*="video-watermark"]', // 跑马灯 '[class*="marquee"]', '[class*="drift-text"]', '[class*="scroll-text"]', '[class*="notice-marquee"]', // 浮窗广告 '[class*="float-ad"]', '[class*="popup-ad"]', '[class*="drift-ad"]', '[class*="banner-ad"]', // 角落广告 '[class*="corner-ad"]', '[class*="bottom-ad"]', '[class*="left-ad"]', '[class*="right-ad"]', // 品牌标识 '[class*="brand-logo"]', '[class*="site-logo"]', '[class*="platform-logo"]', // 特殊平台选择器 // 爱奇艺 '.qy-watermark', '.iqiyi-watermark', '[class*="qy-player"]', // 优酷 '.yk-watermark', '.youku-watermark', // 腾讯视频 '.tx-watermark', '.tencent-watermark', // B站 '.bilibili-watermark', '[class*="bili-watermark"]', // 通用视频平台 '.video-watermark', '.player-watermark', // 跳过按钮容器 '.skip-ad-container', '[class*="skip-ad"]', // 各种可疑的绝对定位元素 '.player-ad', '[class*="player-ad"]', '[class*="video-ad"]', // 贴片广告 '[class*="preroll"]', '[class*="midroll"]', '[class*="postroll"]', // 角标 '.corner-mark', '[class*="corner-tag"]' ]; } // 隐藏元素函数 function hideElement(element) { if (element && element.style) { element.style.display = 'none !important'; element.style.visibility = 'hidden !important'; element.style.opacity = '0 !important'; element.style.pointerEvents = 'none !important'; element.style.zIndex = '-1 !important'; } } // 检查元素是否应该隐藏 function shouldHide(element) { if (!element) return false; const className = (element.className || '').toLowerCase(); const id = (element.id || '').toLowerCase(); const tagName = (element.tagName || '').toLowerCase(); const style = window.getComputedStyle(element); // 检查是否为广告相关元素 const allText = (className + ' ' + id).toLowerCase(); for (const keyword of CONFIG.adKeywords) { if (allText.includes(keyword)) return true; } for (const keyword of CONFIG.watermarkKeywords) { if (allText.includes(keyword)) return true; } for (const keyword of CONFIG.marqueeKeywords) { if (allText.includes(keyword)) return true; } // 检查是否为移动的文字(跑马灯效果) if (style.animation && style.animation.includes('marquee')) { return true; } if (allText.includes('scroll') && tagName === 'marquee') { return true; } // 检查是否为广告图片或视频 if (allText.includes('ad') && (tagName === 'img' || tagName === 'video')) { return true; } return false; } // 隐藏所有广告元素 function hideAllAds() { try { // 使用选择器隐藏 const selectors = getCommonAdSelectors(); selectors.forEach(selector => { try { const elements = document.querySelectorAll(selector); elements.forEach(el => { if (shouldHide(el)) { hideElement(el); log(`已隐藏: ${selector}`); } }); } catch (e) { // 忽略无效选择器 } }); // 遍历所有元素查找可疑广告 const allElements = document.querySelectorAll('*'); allElements.forEach(element => { // 检查内联样式中的广告 const style = element.getAttribute('style') || ''; if (style.toLowerCase().includes('ad') || style.includes('watermark') || style.includes('marquee')) { hideElement(element); } // 检查类名和ID if (shouldHide(element)) { hideElement(element); } // 检查文字内容中的广告关键词 const text = element.textContent || ''; if ((text.includes('广告') || text.includes('AD') || text.includes('推广')) && element.children.length === 0 && text.trim().length < 100) { // 如果是纯文字且包含广告关键词,检查是否为漂浮元素 const rect = element.getBoundingClientRect(); const computedStyle = window.getComputedStyle(element); if (computedStyle.position === 'absolute' || computedStyle.position === 'fixed' || computedStyle.position === 'relative') { hideElement(element); } } }); // 特定平台处理 handleIqy(); handleYouku(); handleTencent(); handleBilibili(); handleDouyin(); handleMgtv(); } catch (error) { log('处理广告时出错: ' + error.message); } } // 爱奇艺特定处理 function handleIqy() { try { // 爱奇艺水印 const iqiyiWatermarks = document.querySelectorAll('.qy-watermark, .iqiyi-watermark, [class*="watermark"]'); iqiyiWatermarks.forEach(el => { if (el.offsetWidth < 200 && el.offsetHeight < 100) { hideElement(el); } }); // 爱奇艺跑马灯 const iqiyiMarquees = document.querySelectorAll('.qy-marquee, [class*="scroll-notice"]'); iqiyiMarquees.forEach(hideElement); } catch (e) { log('处理爱奇艺时出错'); } } // 优酷特定处理 function handleYouku() { try { const youkuWatermarks = document.querySelectorAll('.yk-watermark, .youku-watermark, [class*="youku-logo"]'); youkuWatermarks.forEach(el => { if (el.offsetWidth < 200 && el.offsetHeight < 100) { hideElement(el); } }); } catch (e) { log('处理优酷时出错'); } } // 腾讯视频特定处理 function handleTencent() { try { const txWatermarks = document.querySelectorAll('.tx-watermark, .tencent-watermark, [class*="tencent-logo"]'); txWatermarks.forEach(el => { if (el.offsetWidth < 200 && el.offsetHeight < 100) { hideElement(el); } }); } catch (e) { log('处理腾讯视频时出错'); } } // B站特定处理 function handleBilibili() { try { // B站右下角用户信息水印 const biliWatermarks = document.querySelectorAll('.bilibili-watermark, [class*="bili-watermark"]'); biliWatermarks.forEach(hideElement); // B站其他广告元素 const biliAds = document.querySelectorAll('[class*="bili-"]'); biliAds.forEach(el => { if (el.className.toLowerCase().includes('ad') || el.className.toLowerCase().includes('watermark')) { hideElement(el); } }); } catch (e) { log('处理B站时出错'); } } // 抖音特定处理 function handleDouyin() { try { const douyinAds = document.querySelectorAll('[class*="douyin"]'); douyinAds.forEach(el => { if (el.className.toLowerCase().includes('ad') || el.className.toLowerCase().includes('watermark')) { hideElement(el); } }); } catch (e) { log('处理抖音时出错'); } } // 芒果TV特定处理 function handleMgtv() { try { const mgtvWatermarks = document.querySelectorAll('[class*="mgtv"]'); mgtvWatermarks.forEach(el => { if (el.className.toLowerCase().includes('watermark') || el.className.toLowerCase().includes('logo')) { hideElement(el); } }); } catch (e) { log('处理芒果TV时出错'); } } // 创建观察者监视DOM变化 function createObserver() { const observer = new MutationObserver((mutations) => { let shouldProcess = false; mutations.forEach(mutation => { if (mutation.addedNodes.length > 0) { shouldProcess = true; } }); if (shouldProcess) { hideAllAds(); } }); observer.observe(document.body, { childList: true, subtree: true }); } // 初始化 function init() { log('视频广告水印去除器已启动'); // 立即执行一次 setTimeout(hideAllAds, 100); setTimeout(hideAllAds, 500); setTimeout(hideAllAds, 1000); // 定时检查 setInterval(hideAllAds, CONFIG.checkInterval); // 监听页面加载完成 if (document.readyState === 'complete') { hideAllAds(); } else { window.addEventListener('load', hideAllAds); } // 创建DOM观察者 createObserver(); // 监听页面可见性变化(标签页切换回来时重新检查) document.addEventListener('visibilitychange', () => { if (!document.hidden) { hideAllAds(); } }); } // 启动 if (document.body) { init(); } else { document.addEventListener('DOMContentLoaded', init); } })();