如何用Tampermonkey脚本实现Discord频道切换后自动滚动到底部?
Discord切换频道后自动滚动到底部的Tampermonkey脚本
问题根源
- 仅监听
popstate事件有局限:Discord切换频道时不一定触发该事件,它更多依赖pushState/replaceState这类History API方法,不会主动触发popstate。 - 元素选择器不稳定:Discord的动态类名(比如
scrollerContent-)会随版本更新变化,导致无法精准定位滚动容器。 - 延迟时间不足:500ms的等待时间可能赶不上频道内容的加载渲染速度。
修复后的可用脚本
(function() { 'use strict'; // 滚动到消息最底部的核心函数 function scrollToBottom() { // 用语义化属性定位滚动容器,比类名更稳定 const scroller = document.querySelector('[role="region"][aria-label^="Messages"]'); if (scroller) { // 双重确保滚动生效:先调用scrollTo方法,再直接赋值scrollTop scroller.scrollTo({ top: scroller.scrollHeight, behavior: 'auto' }); scroller.scrollTop = scroller.scrollHeight; } } // 劫持History API,覆盖所有URL变化场景 function watchURLChanges() { const originalPush = history.pushState; const originalReplace = history.replaceState; history.pushState = function(...args) { originalPush.apply(this, args); // 切换频道后等待5秒执行滚动 setTimeout(scrollToBottom, 5000); }; history.replaceState = function(...args) { originalReplace.apply(this, args); setTimeout(scrollToBottom, 5000); }; } // 监听DOM变化,确保内容加载完成后再滚动 function setupDOMWatcher() { const observer = new MutationObserver((mutations) => { mutations.forEach(mutation => { if (mutation.addedNodes.length > 0) { // 短延迟确保内容渲染完毕 setTimeout(scrollToBottom, 1000); } }); }); observer.observe(document.body, { childList: true, subtree: true }); } // 初始化脚本 watchURLChanges(); setupDOMWatcher(); // 页面首次加载后自动滚动一次 setTimeout(scrollToBottom, 1000); })();
核心优化点
- 稳定的容器定位:使用
role和aria-label语义化属性定位消息滚动容器,避免Discord类名更新导致的失效。 - 完整覆盖URL变化:劫持
pushState和replaceState,确保所有频道切换场景都能触发滚动逻辑。 - DOM变化兜底:通过MutationObserver监听内容渲染,避免因加载延迟导致滚动时机过早。
- 符合需求的延迟:严格按照要求设置5秒延迟,同时补充短延迟兜底逻辑。
内容的提问来源于stack exchange,提问作者QuantumPulse87
相关产品推荐
相关产品推荐

