// ==UserScript== // @name 陈天翊抖音自动刷视频脚本 // @namespace https://www.douyin.com/ // @version 12.0 // @description 抖音自动刷视频脚本 - 随机时间 + 随机方向 + 红色圆形箭头按钮识别 // @author ChatGPT // @match *://*.douyin.com/* // @match *://*.iesdouyin.com/* // @grant none // @run-at document-end // @license MIT // ==/UserScript== (function() { 'use strict'; console.log('🎯 陈天翊抖音自动刷视频脚本加载中...'); // 等待页面加载完成 setTimeout(() => { initSmartSwitcher(); }, 3000); function initSmartSwitcher() { // 创建控制面板 createSwitcherUI(); // 初始化变量 let isRunning = false; let isPaused = false; let currentDirection = 'down'; let clickCount = 0; let upCount = 0; let downCount = 0; let startTime = Date.now(); let switchHistory = []; let currentTimeout = null; // 精确的JS路径 const DOWN_BUTTON_SELECTOR = "#douyin-right-container > div.parent-route-container.route-scroll-container.IhmVuo1S > div.xgplayer-playswitch.jLGIrBFY.BEL49lJv.recommend-out-switch-btn > div > div > div.xgplayer-playswitch-next"; const UP_BUTTON_SELECTOR = "#douyin-right-container > div.parent-route-container.route-scroll-container.IhmVuo1S > div.xgplayer-playswitch.jLGIrBFY.BEL49lJv.recommend-out-switch-btn > div > div > div.xgplayer-playswitch-prev"; // 红色圆形向上箭头检测 function findRedUpArrow() { console.log('🔍 查找红色圆形向上箭头...'); // 首先尝试精确路径 const upButton = document.querySelector(UP_BUTTON_SELECTOR); if (upButton && isElementVisible(upButton) && isRedRoundButton(upButton)) { log('🎯 找到红色圆形向上箭头按钮'); highlightElement(upButton, '#FF0000'); return upButton; } // 搜索所有可能的红色圆形按钮 const allButtons = document.querySelectorAll('div, button, span, a'); for (let element of allButtons) { if (isElementVisible(element) && isRedRoundButton(element) && containsUpArrow(element)) { log('🎯 找到红色圆形向上箭头按钮'); highlightElement(element, '#FF0000'); return element; } } // 如果没有红色圆形,尝试查找任何向上箭头 const upSelectors = [ 'button[aria-label*="上"]', 'button[aria-label*="up"]', 'button[aria-label*="prev"]', 'button[title*="上"]', 'button[title*="up"]', 'div[class*="prev"]', 'div[class*="up"]', '[data-e2e*="prev"]', '[data-e2e*="up"]', '[data-testid*="prev"]', '[data-testid*="up"]', 'button:has(> svg > path[d*="m12 4"])', // 常见向上箭头路径 'div:has(> svg > path[d*="m12 4"])', 'button:has(> span:contains("↑"))', 'div:has(> span:contains("↑"))' ]; for (let selector of upSelectors) { try { const elements = document.querySelectorAll(selector); for (let element of elements) { if (isElementVisible(element)) { log('🔍 找到向上箭头元素'); highlightElement(element, '#FF0000'); return element; } } } catch (e) {} } return null; } // 查找向下箭头 function findDownArrow() { console.log('🔍 查找向下箭头...'); // 首先尝试精确路径 const downButton = document.querySelector(DOWN_BUTTON_SELECTOR); if (downButton && isElementVisible(downButton)) { log('🔍 找到向下箭头按钮'); highlightElement(downButton, '#2196F3'); return downButton; } // 备用选择器 const downSelectors = [ 'button[aria-label*="下"]', 'button[aria-label*="down"]', 'button[aria-label*="next"]', 'button[title*="下"]', 'button[title*="down"]', 'div[class*="next"]', 'div[class*="down"]', '[data-e2e*="next"]', '[data-e2e*="down"]', '[data-testid*="next"]', '[data-testid*="down"]', 'button:has(> svg > path[d*="m12 20"])', // 常见向下箭头路径 'div:has(> svg > path[d*="m12 20"])', 'button:has(> span:contains("↓"))', 'div:has(> span:contains("↓"))' ]; for (let selector of downSelectors) { try { const elements = document.querySelectorAll(selector); for (let element of elements) { if (isElementVisible(element)) { log('🔍 找到向下箭头元素'); highlightElement(element, '#2196F3'); return element; } } } catch (e) {} } return null; } // 检查是否是红色圆形按钮 function isRedRoundButton(element) { if (!element) return false; const style = window.getComputedStyle(element); const bgColor = style.backgroundColor.toLowerCase(); const borderRadius = parseInt(style.borderRadius) || 0; const rect = element.getBoundingClientRect(); // 检查是否红色 const isRed = bgColor.includes('rgb(255, 0, 0)') || bgColor.includes('rgba(255, 0, 0') || bgColor.includes('#ff0000') || bgColor.includes('#f00') || bgColor.includes('red'); // 检查是否圆形 const width = rect.width; const height = rect.height; const isRound = Math.abs(width - height) <= 5 && borderRadius >= width / 2; // 检查是否包含向上箭头 const hasUpArrow = containsUpArrow(element); return isRed && isRound && hasUpArrow; } // 检查是否包含向上箭头 function containsUpArrow(element) { if (!element) return false; // 检查SVG路径 const svgs = element.querySelectorAll('svg'); for (let svg of svgs) { const paths = svg.querySelectorAll('path'); for (let path of paths) { const d = path.getAttribute('d') || ''; if (d.includes('m12 4') || // 常见的向上箭头路径 d.includes('m19 9') || d.includes('m5 9')) { return true; } } } // 检查文本内容 const text = (element.textContent || element.innerText || '').trim(); if (text.includes('↑') || text.includes('上')) { return true; } // 检查背景图片 const bgImage = element.style.backgroundImage; if (bgImage && (bgImage.includes('arrow') || bgImage.includes('up'))) { return true; } return false; } // 检查元素是否可见 function isElementVisible(element) { if (!element || !element.tagName) return false; const rect = element.getBoundingClientRect(); const style = window.getComputedStyle(element); return style.display !== 'none' && style.visibility !== 'hidden' && style.opacity !== '0' && element.offsetParent !== null && rect.width > 0 && rect.height > 0 && rect.top >= 0 && rect.left >= 0 && rect.bottom <= window.innerHeight && rect.right <= window.innerWidth; } // 高亮显示元素 function highlightElement(element, color = '#00ff00') { const originalBorder = element.style.border; const originalBoxShadow = element.style.boxShadow; const originalOutline = element.style.outline; element.style.border = `3px solid ${color}`; element.style.boxShadow = `0 0 20px ${color}`; element.style.outline = 'none'; element.style.zIndex = '9999'; element.style.position = 'relative'; setTimeout(() => { element.style.border = originalBorder; element.style.boxShadow = originalBoxShadow; element.style.outline = originalOutline; element.style.zIndex = ''; element.style.position = ''; }, 2000); return element; } // 获取随机时间间隔 function getRandomInterval() { const minTime = parseInt(document.getElementById('minTime').value) * 1000; const maxTime = parseInt(document.getElementById('maxTime').value) * 1000; if (minTime >= maxTime) { return minTime; } return Math.floor(Math.random() * (maxTime - minTime + 1)) + minTime; } // 智能点击 function smartClick(element) { if (!element) return false; try { // 检查元素是否可点击 if (element.disabled) { log('⚠️ 元素被禁用'); return false; } // 添加点击效果 const originalTransform = element.style.transform; element.style.transform = 'scale(0.9)'; element.style.transition = 'transform 0.2s'; // 触发点击事件 const rect = element.getBoundingClientRect(); const events = ['mousedown', 'mouseup', 'click']; events.forEach(eventType => { const event = new MouseEvent(eventType, { view: window, bubbles: true, cancelable: true, clientX: rect.left + rect.width / 2, clientY: rect.top + rect.height / 2 }); element.dispatchEvent(event); }); // 恢复样式 setTimeout(() => { element.style.transform = originalTransform; }, 200); return true; } catch (error) { console.error('点击失败:', error); return false; } } // 向下翻页 function switchToNext() { const downButton = findDownArrow(); if (!downButton) { log('❌ 未找到向下按钮'); return false; } if (smartClick(downButton)) { downCount++; clickCount++; switchHistory.unshift({ time: new Date().toLocaleTimeString(), action: '⬇️ 下一视频', success: true }); updateStats(); showEffect('下一视频 ✅', '#2196F3'); log('⬇️ 下一视频成功'); return true; } log('❌ 点击向下按钮失败'); return false; } // 向上翻页 function switchToPrev() { const upButton = findRedUpArrow(); if (!upButton) { log('❌ 未找到红色向上箭头'); return false; } if (smartClick(upButton)) { upCount++; clickCount++; switchHistory.unshift({ time: new Date().toLocaleTimeString(), action: '⬆️ 上一视频', success: true }); updateStats(); showEffect('上一视频 ✅', '#FF0000'); log('⬆️ 上一视频成功'); return true; } log('❌ 点击向上按钮失败'); return false; } // 显示效果 function showEffect(text, color) { const effect = document.createElement('div'); effect.textContent = text; effect.style.cssText = ` position: fixed; top: 50%; left: 50%; transform: translate(-50%, -50%); background: ${color}20; color: white; padding: 15px 30px; border-radius: 25px; font-size: 20px; font-weight: bold; z-index: 999999; animation: popIn 0.3s ease-out, fadeOut 0.5s ease-in 1.5s forwards; box-shadow: 0 0 30px ${color}40; backdrop-filter: blur(10px); border: 2px solid ${color}80; text-shadow: 1px 1px 2px rgba(0,0,0,0.5); `; document.body.appendChild(effect); setTimeout(() => { if (effect.parentNode) { effect.remove(); } }, 2000); } // 计算下次切换时间 function getNextSwitchTime() { const minTime = parseInt(document.getElementById('minTime').value) * 1000; const maxTime = parseInt(document.getElementById('maxTime').value) * 1000; if (minTime >= maxTime) { return minTime; } const randomTime = Math.floor(Math.random() * (maxTime - minTime + 1)) + minTime; // 更新显示 document.getElementById('nextSwitchTime').textContent = `${randomTime/1000}s`; document.getElementById('nextSwitchTime').style.color = '#FF9800'; document.getElementById('nextSwitchTime').style.fontWeight = 'bold'; return randomTime; } // 自动切换 function autoSwitch() { if (isPaused || !isRunning) return; // 随机选择方向 if (document.getElementById('randomDirection').checked) { currentDirection = Math.random() > 0.5 ? 'up' : 'down'; updateDirectionDisplay(); } // 执行切换 if (currentDirection === 'down') { switchToNext(); } else { switchToPrev(); } // 计算下次切换时间 const nextTime = getNextSwitchTime(); log(`⏱️ 下次切换: ${nextTime/1000}秒后`); // 设置下次切换 if (currentTimeout) { clearTimeout(currentTimeout); } currentTimeout = setTimeout(() => { if (isRunning && !isPaused) { autoSwitch(); } }, nextTime); } // 开始自动切换 function startAutoSwitch() { if (!isRunning) { isRunning = true; isPaused = false; startTime = Date.now(); updateStatus('运行中', '#00ff00'); document.getElementById('startBtn').textContent = '⏸️ 暂停'; document.getElementById('startBtn').style.background = '#ff4444'; log('🚀 开始自动视频切换'); // 计算并显示首次切换时间 const firstDelay = getNextSwitchTime(); log(`⏱️ 首次切换: ${firstDelay/1000}秒后`); // 设置首次切换 if (currentTimeout) { clearTimeout(currentTimeout); } currentTimeout = setTimeout(() => { if (isRunning && !isPaused) { autoSwitch(); } }, firstDelay); } } // 暂停自动切换 function pauseAutoSwitch() { isPaused = !isPaused; if (isPaused) { updateStatus('已暂停', '#ffff00'); document.getElementById('startBtn').textContent = '▶️ 继续'; document.getElementById('startBtn').style.background = '#00aa00'; log('⏸️ 已暂停'); if (currentTimeout) { clearTimeout(currentTimeout); } } else { updateStatus('运行中', '#00ff00'); document.getElementById('startBtn').textContent = '⏸️ 暂停'; document.getElementById('startBtn').style.background = '#ff4444'; log('▶️ 继续运行'); // 重新开始 const nextTime = getNextSwitchTime(); currentTimeout = setTimeout(() => { if (isRunning && !isPaused) { autoSwitch(); } }, nextTime); } } // 停止自动切换 function stopAutoSwitch() { isRunning = false; isPaused = false; if (currentTimeout) { clearTimeout(currentTimeout); currentTimeout = null; } updateStatus('已停止', '#ff4444'); document.getElementById('startBtn').textContent = '▶️ 开始'; document.getElementById('startBtn').style.background = '#00aa00'; log('⏹️ 已停止'); } // 测试红色向上箭头 function testRedArrow() { log('🔍 检测红色圆形向上箭头...'); const upButton = findRedUpArrow(); if (upButton) { log('✅ 找到红色圆形向上箭头'); showEffect('✅ 找到红色向上箭头', '#FF0000'); } else { log('❌ 未找到红色圆形向上箭头'); showEffect('❌ 未找到红色向上箭头', '#f44336'); } const downButton = findDownArrow(); if (downButton) { log('✅ 找到向下箭头按钮'); } else { log('❌ 未找到向下箭头按钮'); } } // 测试向上按钮 function testUp() { if (switchToPrev()) { log('✅ 向上按钮测试成功'); } else { log('❌ 向上按钮测试失败'); } } // 测试向下按钮 function testDown() { if (switchToNext()) { log('✅ 向下按钮测试成功'); } else { log('❌ 向下按钮测试失败'); } } // 设置方向 function setDirection(direction) { currentDirection = direction; updateDirectionDisplay(); log(`🎯 设置为${direction === 'up' ? '向上' : '向下'}切换`); } // 更新方向显示 function updateDirectionDisplay() { const directionDisplay = document.getElementById('directionDisplay'); if (directionDisplay) { directionDisplay.textContent = currentDirection === 'up' ? '⬆️ 向上' : '⬇️ 向下'; directionDisplay.style.color = currentDirection === 'up' ? '#FF0000' : '#2196F3'; } } // 重置统计 function resetStats() { clickCount = 0; upCount = 0; downCount = 0; switchHistory = []; updateStats(); log('🔄 统计已重置'); } // 更新统计 function updateStats() { document.getElementById('clickCount').textContent = clickCount; document.getElementById('upCount').textContent = upCount; document.getElementById('downCount').textContent = downCount; const elapsed = Math.floor((Date.now() - startTime) / 1000); const minutes = Math.floor(elapsed / 60); const seconds = elapsed % 60; document.getElementById('elapsedTime').textContent = minutes > 0 ? `${minutes}m ${seconds}s` : `${seconds}s`; // 更新频率 if (elapsed > 0) { const frequency = (clickCount / elapsed).toFixed(2); document.getElementById('frequency').textContent = frequency + '/秒'; } // 更新历史记录 updateHistory(); } // 更新历史记录 function updateHistory() { const historyList = document.getElementById('switchHistory'); if (!historyList) return; historyList.innerHTML = ''; switchHistory.slice(0, 10).forEach((item, index) => { const li = document.createElement('li'); li.textContent = `${item.time}: ${item.action}`; li.style.color = item.success ? '#4CAF50' : '#f44336'; li.style.padding = '3px 0'; li.style.borderBottom = '1px solid #333'; historyList.appendChild(li); }); } // 更新状态 function updateStatus(text, color) { const statusText = document.getElementById('statusText'); const statusLed = document.getElementById('statusLed'); if (statusText) statusText.textContent = text; if (statusLed) statusLed.style.background = color; } // 日志 function log(message) { const logElement = document.getElementById('logContent'); if (logElement) { const time = new Date().toLocaleTimeString(); const logMessage = `[${time}] ${message}`; const p = document.createElement('p'); p.textContent = logMessage; p.style.margin = '5px 0'; p.style.fontSize = '12px'; p.style.color = getMessageColor(message); logElement.appendChild(p); // 限制日志数量 if (logElement.children.length > 20) { logElement.removeChild(logElement.firstChild); } // 自动滚动到底部 logElement.scrollTop = logElement.scrollHeight; } console.log(message); } // 获取消息颜色 function getMessageColor(message) { if (message.includes('✅')) return '#4CAF50'; if (message.includes('❌')) return '#f44336'; if (message.includes('🔄')) return '#ff9800'; if (message.includes('🚀')) return '#2196F3'; if (message.includes('⏸️')) return '#ff9800'; if (message.includes('⏹️')) return '#f44336'; if (message.includes('▶️')) return '#4CAF50'; if (message.includes('⬆️')) return '#FF0000'; if (message.includes('⬇️')) return '#2196F3'; if (message.includes('🔍')) return '#9C27B0'; if (message.includes('🎯')) return '#FF9800'; if (message.includes('⏱️')) return '#00BCD4'; if (message.includes('⚠️')) return '#FFC107'; return '#ddd'; } // 添加CSS样式 const style = document.createElement('style'); style.textContent = ` @keyframes popIn { 0% { transform: translate(-50%, -50%) scale(0.5); opacity: 0; } 70% { transform: translate(-50%, -50%) scale(1.1); opacity: 1; } 100% { transform: translate(-50%, -50%) scale(1); opacity: 1; } } @keyframes fadeOut { to { opacity: 0; } } @keyframes pulse { 0% { opacity: 1; } 50% { opacity: 0.5; } 100% { opacity: 1; } } .panel-collapsed { height: 60px !important; overflow: hidden !important; } .panel-content { transition: all 0.3s ease-in-out; } .collapse-icon { transition: transform 0.3s ease-in-out; } .panel-collapsed .collapse-icon { transform: rotate(-90deg); } `; document.head.appendChild(style); // 初始化事件监听 document.getElementById('startBtn').addEventListener('click', startAutoSwitch); document.getElementById('pauseBtn').addEventListener('click', pauseAutoSwitch); document.getElementById('stopBtn').addEventListener('click', stopAutoSwitch); document.getElementById('testBtn').addEventListener('click', testRedArrow); document.getElementById('upBtn').addEventListener('click', () => { setDirection('up'); testUp(); }); document.getElementById('downBtn').addEventListener('click', () => { setDirection('down'); testDown(); }); document.getElementById('toggleBtn').addEventListener('click', () => { currentDirection = currentDirection === 'up' ? 'down' : 'up'; updateDirectionDisplay(); log(`🔄 切换方向为: ${currentDirection === 'up' ? '向上' : '向下'}`); }); document.getElementById('resetBtn').addEventListener('click', resetStats); // 折叠按钮事件 document.getElementById('collapseBtn').addEventListener('click', togglePanel); // 时间配置事件 document.getElementById('minTime').addEventListener('input', function() { document.getElementById('minTimeValue').textContent = this.value + 's'; }); document.getElementById('maxTime').addEventListener('input', function() { document.getElementById('maxTimeValue').textContent = this.value + 's'; }); // 初始方向显示 updateDirectionDisplay(); log('🎯 陈天翊抖音自动刷视频脚本已加载完成'); log('🔴 已启用红色圆形箭头按钮识别'); log('⏱️ 支持随机时间间隔'); log('🔄 已启用随机方向模式'); log('📁 点击标题栏折叠按钮可最小化面板'); } // 切换面板折叠状态 function togglePanel() { const panel = document.getElementById('douyinSwitcherUI'); const content = document.getElementById('panelContent'); const collapseIcon = document.getElementById('collapseIcon'); panel.classList.toggle('panel-collapsed'); if (panel.classList.contains('panel-collapsed')) { content.style.display = 'none'; collapseIcon.textContent = '▶'; } else { content.style.display = 'block'; collapseIcon.textContent = '▼'; } } // 创建控制面板UI function createSwitcherUI() { if (document.getElementById('douyinSwitcherUI')) return; const panel = document.createElement('div'); panel.id = 'douyinSwitcherUI'; panel.style.cssText = ` position: fixed; top: 100px; right: 20px; width: 400px; min-height: 60px; background: rgba(0, 0, 0, 0.95); border: 2px solid #ff0000; border-radius: 15px; color: white; font-family: Arial, sans-serif; z-index: 999999; box-shadow: 0 8px 32px rgba(255, 0, 0, 0.4); backdrop-filter: blur(10px); transition: height 0.3s ease-in-out; overflow: hidden; `; panel.innerHTML = `

🎯 视频切换天翊测试版

已停止
当前方向
⬆️ 向上
随机时间配置
最小时间
2s
~
最大时间
10s
下次切换: -
切换模式
切换次数
0
向上次数
0
向下次数
0
运行时间: 0s
频率: 0/秒
切换历史:
运行日志
`; document.body.appendChild(panel); // 添加拖拽功能 let isDragging = false; let offsetX, offsetY; // 标题栏拖拽 const titleBar = panel.querySelector('div[style*="background: linear-gradient"]'); titleBar.addEventListener('mousedown', (e) => { if (e.target.tagName === 'BUTTON' || e.target.tagName === 'INPUT' || e.target.tagName === 'LABEL') { return; } isDragging = true; offsetX = e.offsetX; offsetY = e.offsetY; }); document.addEventListener('mousemove', (e) => { if (!isDragging) return; panel.style.left = (e.clientX - offsetX) + 'px'; panel.style.top = (e.clientY - offsetY) + 'px'; panel.style.right = 'auto'; }); document.addEventListener('mouseup', () => { isDragging = false; }); } })();