// ==UserScript== // @name 极简小说阅读模式 // @namespace http://tampermonkey.net/ // @version 0.5.5 // @description 极简移动端小说阅读模式,自动加载下一章 // @author You // @run-at document-start // @grant GM_xmlhttpRequest // @grant GM_registerMenuCommand // @match *://*/* // ==/UserScript== (function() { 'use strict'; // 2. 创建纯净的HTML结构 const cleanHTML = `
未能提取正文内容
', url: window.location.href, nextUrl: nextBtn?.href }; } let iframe; function extractContentByIframe(srcDoc){ // 2. 创建 iframe 沙盒 return new Promise((resolve, reject) => { iframe = document._createElement('iframe'); iframe.style.display = 'none'; iframe.name = 'sandbox-iframe'; iframe.sandbox = 'allow-same-origin allow-scripts'; document.body.appendChild(iframe); iframe.onload = function() { resolve(extractContent(iframe.contentDocument)); } iframe.srcdoc = srcDoc; }); } // 加载章节内容 async function loadChapter(url) { if (isLoading) return; isLoading = true; const loadingEl = document.getElementById('simple-reader-loading') loadingEl.style.display = 'block'; try { //const response = await fetch(url, { headers:{ "Content-Type": "text/html" } }); function GM_xhr(options) { return new Promise((resolve, reject) => { GM_xmlhttpRequest({ ...options, onload: (response) => resolve(response), onerror: (error) => reject(error), ontimeout: () => reject(new Error("Request timeout")), }); }); } const response = await GM_xhr({ method: 'GET', url: url.includes('http') ? url : location.origin + url, headers: { 'User-Agent': "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36" || navigator.userAgent, "Response-Type": "text/html", }, onload: function(response) { /* ... */ } }); if(response.responseText.includes('document.writeln')){ console.log('iframe获取') currentChapter = await extractContentByIframe(response.responseText) }else{ // 创建临时DOM解析 const parser = new DOMParser(); const doc = parser.parseFromString(response.responseText, 'text/html'); currentChapter = extractContent(doc) } showChapter(); } catch (error) { console.error('加载失败:', error); const textEl = document.getElementById('simple-reader-text'); // 获取所有属性(包括不可枚举的) const errorDetails = {}; Object.getOwnPropertyNames(error).forEach(key => { errorDetails[key] = error[key]; }); textEl.innerHTML += `章节加载失败
${JSON.stringify(errorDetails)}
`; } finally { isLoading = false; loadingEl.style.display = 'none'; } } // 显示章节内容 function showChapter() { const textEl = document.getElementById('simple-reader-text'); cacheChapter.push(currentChapter); textEl.appendChild(currentChapter.content); if(cacheChapter.length > 5) { const oldChapter = cacheChapter.shift(); oldChapter.content.remove(); } // 自动检查是否需要加载下一章 checkAutoLoad(); } // 检查是否需要自动加载下一章 function checkAutoLoad() { if (isLoading || !currentChapter.nextUrl) return; const reader = document.getElementById('simple-reader'); const { scrollTop, scrollHeight, clientHeight } = reader; const distanceToBottom = scrollHeight - (scrollTop + clientHeight); // 距离底部小于300px时加载下一章 if (distanceToBottom < 500) { loadChapter(currentChapter.nextUrl); } } function initNovelReader(event){ window.stop(); document.open('text/html', 'replace'); document.write(cleanHTML); document.close(); document._createElement = document.createElement; document.createElement = function(tagName) { console.log('createElement:', tagName) }; // 保存原始方法 if (window.navigation) { window.navigation.addEventListener('navigate', (event) => { console.log('导航尝试:', event.destination.url); event.preventDefault(); // 阻止导航 }); } loadChapter(window.location.href) const reader = document.getElementById('simple-reader'); reader.style.display = 'block'; reader.addEventListener('scroll', checkAutoLoad); try{ // 注销所有 Service Worker navigator.serviceWorker.getRegistrations().then(registrations => { console.log('清理:', registrations) registrations.forEach(registration => registration.unregister()); }); }catch(err){} } GM_registerMenuCommand('启动小说阅读模式', initNovelReader); // 页面加载完成后添加按钮 //if (document.readyState === 'complete') { // addLaunchButton(); //} else { // window.addEventListener('load', addLaunchButton); //} })();