<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="zh-Hans-CN">
	<id>https://new.pvzhe.wiki/w/%E7%94%A8%E6%88%B7:EditBot/console?action=history&amp;feed=atom</id>
	<title>用户:EditBot/console - 版本历史</title>
	<link rel="self" type="application/atom+xml" href="https://new.pvzhe.wiki/w/%E7%94%A8%E6%88%B7:EditBot/console?action=history&amp;feed=atom"/>
	<link rel="alternate" type="text/html" href="https://new.pvzhe.wiki/w/%E7%94%A8%E6%88%B7:EditBot/console?action=history"/>
	<updated>2026-07-26T16:37:51Z</updated>
	<subtitle>本wiki上该页面的版本历史</subtitle>
	<generator>MediaWiki 1.43.6</generator>
	<entry>
		<id>https://new.pvzhe.wiki/index.php?title=%E7%94%A8%E6%88%B7:EditBot/console&amp;diff=13191&amp;oldid=prev</id>
		<title>EditBot：​创建页面，内容为“&lt;div id=&quot;bot-console&quot; style=&quot;position:fixed;bottom:20px;right:20px;width:400px;max-height:500px;background:rgba(0,0,0,0.9);border-radius:12px;padding:16px;color:#00ff00;font-family:monospace;font-size:12px;z-index:999999;box-shadow:0 8px 30px rgba(0,0,0,0.8);overflow:hidden;border:2px solid #00ff00;resize:both;min-width:300px;&quot;&gt;     &lt;div style=&quot;display:flex;justify-content:space-between;align-items:center;margin-bottom:8px;cursor:move;&quot;&gt;         &lt;span style=&quot;fo…”</title>
		<link rel="alternate" type="text/html" href="https://new.pvzhe.wiki/index.php?title=%E7%94%A8%E6%88%B7:EditBot/console&amp;diff=13191&amp;oldid=prev"/>
		<updated>2026-07-20T02:06:47Z</updated>

		<summary type="html">&lt;p&gt;创建页面，内容为“&amp;lt;div id=&amp;quot;bot-console&amp;quot; style=&amp;quot;position:fixed;bottom:20px;right:20px;width:400px;max-height:500px;background:rgba(0,0,0,0.9);border-radius:12px;padding:16px;color:#00ff00;font-family:monospace;font-size:12px;z-index:999999;box-shadow:0 8px 30px rgba(0,0,0,0.8);overflow:hidden;border:2px solid #00ff00;resize:both;min-width:300px;&amp;quot;&amp;gt;     &amp;lt;div style=&amp;quot;display:flex;justify-content:space-between;align-items:center;margin-bottom:8px;cursor:move;&amp;quot;&amp;gt;         &amp;lt;span style=&amp;quot;fo…”&lt;/p&gt;
&lt;p&gt;&lt;b&gt;新页面&lt;/b&gt;&lt;/p&gt;&lt;div&gt;&amp;lt;div id=&amp;quot;bot-console&amp;quot; style=&amp;quot;position:fixed;bottom:20px;right:20px;width:400px;max-height:500px;background:rgba(0,0,0,0.9);border-radius:12px;padding:16px;color:#00ff00;font-family:monospace;font-size:12px;z-index:999999;box-shadow:0 8px 30px rgba(0,0,0,0.8);overflow:hidden;border:2px solid #00ff00;resize:both;min-width:300px;&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;div style=&amp;quot;display:flex;justify-content:space-between;align-items:center;margin-bottom:8px;cursor:move;&amp;quot;&amp;gt;&lt;br /&gt;
        &amp;lt;span style=&amp;quot;font-weight:bold;color:#00ff00;&amp;quot;&amp;gt;🤖 EditBot 控制台&amp;lt;/span&amp;gt;&lt;br /&gt;
        &amp;lt;div&amp;gt;&lt;br /&gt;
            &amp;lt;span id=&amp;quot;bot-status&amp;quot; style=&amp;quot;color:#ffaa00;font-size:10px;&amp;quot;&amp;gt;● 运行中&amp;lt;/span&amp;gt;&lt;br /&gt;
            &amp;lt;button id=&amp;quot;bot-toggle&amp;quot; style=&amp;quot;background:#ff4444;border:none;color:#fff;padding:2px 10px;border-radius:4px;cursor:pointer;font-size:11px;&amp;quot;&amp;gt;停止&amp;lt;/button&amp;gt;&lt;br /&gt;
            &amp;lt;button id=&amp;quot;bot-close&amp;quot; style=&amp;quot;background:#555;border:none;color:#fff;padding:2px 8px;border-radius:4px;cursor:pointer;font-size:11px;&amp;quot;&amp;gt;✕&amp;lt;/button&amp;gt;&lt;br /&gt;
        &amp;lt;/div&amp;gt;&lt;br /&gt;
    &amp;lt;/div&amp;gt;&lt;br /&gt;
    &amp;lt;div style=&amp;quot;border-top:1px solid #333;padding-top:8px;&amp;quot;&amp;gt;&lt;br /&gt;
        &amp;lt;div style=&amp;quot;display:flex;gap:8px;margin-bottom:6px;flex-wrap:wrap;&amp;quot;&amp;gt;&lt;br /&gt;
            &amp;lt;span style=&amp;quot;color:#888;&amp;quot;&amp;gt;用户: &amp;lt;span id=&amp;quot;bot-user&amp;quot; style=&amp;quot;color:#00ff00;&amp;quot;&amp;gt;加载中...&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&lt;br /&gt;
            &amp;lt;span style=&amp;quot;color:#888;&amp;quot;&amp;gt;检测: &amp;lt;span id=&amp;quot;bot-count&amp;quot; style=&amp;quot;color:#00ff00;&amp;quot;&amp;gt;0&amp;lt;/span&amp;gt; 人&amp;lt;/span&amp;gt;&lt;br /&gt;
            &amp;lt;span style=&amp;quot;color:#888;&amp;quot;&amp;gt;写入: &amp;lt;span id=&amp;quot;bot-writes&amp;quot; style=&amp;quot;color:#00ff00;&amp;quot;&amp;gt;0&amp;lt;/span&amp;gt; 次&amp;lt;/span&amp;gt;&lt;br /&gt;
        &amp;lt;/div&amp;gt;&lt;br /&gt;
        &amp;lt;div id=&amp;quot;bot-log&amp;quot; style=&amp;quot;height:200px;overflow-y:auto;background:#111;border-radius:6px;padding:6px;font-size:11px;line-height:1.6;&amp;quot;&amp;gt;&lt;br /&gt;
            &amp;lt;div style=&amp;quot;color:#888;&amp;quot;&amp;gt;⏳ 等待启动...&amp;lt;/div&amp;gt;&lt;br /&gt;
        &amp;lt;/div&amp;gt;&lt;br /&gt;
        &amp;lt;div style=&amp;quot;display:flex;gap:6px;margin-top:6px;&amp;quot;&amp;gt;&lt;br /&gt;
            &amp;lt;input id=&amp;quot;bot-interval&amp;quot; type=&amp;quot;number&amp;quot; value=&amp;quot;3&amp;quot; style=&amp;quot;width:50px;background:#222;border:1px solid #444;color:#fff;border-radius:4px;padding:2px 4px;font-size:11px;&amp;quot;&amp;gt;&lt;br /&gt;
            &amp;lt;span style=&amp;quot;color:#888;font-size:10px;&amp;quot;&amp;gt;秒&amp;lt;/span&amp;gt;&lt;br /&gt;
            &amp;lt;button id=&amp;quot;bot-scan&amp;quot; style=&amp;quot;background:#0088ff;border:none;color:#fff;padding:2px 12px;border-radius:4px;cursor:pointer;font-size:11px;&amp;quot;&amp;gt;立即扫描&amp;lt;/button&amp;gt;&lt;br /&gt;
            &amp;lt;button id=&amp;quot;bot-clear&amp;quot; style=&amp;quot;background:#555;border:none;color:#fff;padding:2px 12px;border-radius:4px;cursor:pointer;font-size:11px;&amp;quot;&amp;gt;清空日志&amp;lt;/button&amp;gt;&lt;br /&gt;
        &amp;lt;/div&amp;gt;&lt;br /&gt;
    &amp;lt;/div&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;style&amp;gt;&lt;br /&gt;
#bot-log::-webkit-scrollbar { width: 4px; }&lt;br /&gt;
#bot-log::-webkit-scrollbar-track { background: #111; }&lt;br /&gt;
#bot-log::-webkit-scrollbar-thumb { background: #444; border-radius: 2px; }&lt;br /&gt;
#bot-console .log-success { color: #00ff00; }&lt;br /&gt;
#bot-console .log-warning { color: #ffaa00; }&lt;br /&gt;
#bot-console .log-error { color: #ff4444; }&lt;br /&gt;
#bot-console .log-info { color: #66ccff; }&lt;br /&gt;
#bot-console .log-editor { color: #ff66aa; }&lt;br /&gt;
&amp;lt;/style&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;script&amp;gt;&lt;br /&gt;
(function() {&lt;br /&gt;
    &amp;#039;use strict&amp;#039;;&lt;br /&gt;
&lt;br /&gt;
    // ============ 配置 ============&lt;br /&gt;
    var BOT_NAME = mw.config.get(&amp;#039;wgUserName&amp;#039;) || &amp;#039;EditBot&amp;#039;;&lt;br /&gt;
    var CHECK_INTERVAL = 3000;&lt;br /&gt;
    var running = false;&lt;br /&gt;
    var timer = null;&lt;br /&gt;
    var writeCount = 0;&lt;br /&gt;
    var scanCount = 0;&lt;br /&gt;
    var detectedEditors = {};&lt;br /&gt;
    var logLines = [];&lt;br /&gt;
&lt;br /&gt;
    // ============ DOM 引用 ============&lt;br /&gt;
    var logEl = document.getElementById(&amp;#039;bot-log&amp;#039;);&lt;br /&gt;
    var statusEl = document.getElementById(&amp;#039;bot-status&amp;#039;);&lt;br /&gt;
    var toggleBtn = document.getElementById(&amp;#039;bot-toggle&amp;#039;);&lt;br /&gt;
    var countEl = document.getElementById(&amp;#039;bot-count&amp;#039;);&lt;br /&gt;
    var writesEl = document.getElementById(&amp;#039;bot-writes&amp;#039;);&lt;br /&gt;
    var userEl = document.getElementById(&amp;#039;bot-user&amp;#039;);&lt;br /&gt;
    var intervalInput = document.getElementById(&amp;#039;bot-interval&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
    userEl.textContent = BOT_NAME;&lt;br /&gt;
&lt;br /&gt;
    // ============ 日志系统 ============&lt;br /&gt;
    function log(msg, type) {&lt;br /&gt;
        type = type || &amp;#039;info&amp;#039;;&lt;br /&gt;
        var time = new Date().toLocaleTimeString();&lt;br /&gt;
        var colors = {&lt;br /&gt;
            success: &amp;#039;#00ff00&amp;#039;,&lt;br /&gt;
            warning: &amp;#039;#ffaa00&amp;#039;,&lt;br /&gt;
            error: &amp;#039;#ff4444&amp;#039;,&lt;br /&gt;
            info: &amp;#039;#66ccff&amp;#039;,&lt;br /&gt;
            editor: &amp;#039;#ff66aa&amp;#039;,&lt;br /&gt;
            mute: &amp;#039;#555&amp;#039;&lt;br /&gt;
        };&lt;br /&gt;
        var color = colors[type] || &amp;#039;#ffffff&amp;#039;;&lt;br /&gt;
        var line = &amp;#039;&amp;lt;div style=&amp;quot;color:&amp;#039; + color + &amp;#039;;&amp;quot;&amp;gt;[&amp;#039; + time + &amp;#039;] &amp;#039; + msg + &amp;#039;&amp;lt;/div&amp;gt;&amp;#039;;&lt;br /&gt;
        logEl.innerHTML += line;&lt;br /&gt;
        logEl.scrollTop = logEl.scrollHeight;&lt;br /&gt;
        if (logEl.children.length &amp;gt; 500) {&lt;br /&gt;
            logEl.removeChild(logEl.firstChild);&lt;br /&gt;
        }&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 核心检测 ============&lt;br /&gt;
    function scanAllEditors() {&lt;br /&gt;
        if (!running) return;&lt;br /&gt;
&lt;br /&gt;
        var api = new mw.Api();&lt;br /&gt;
        scanCount++;&lt;br /&gt;
&lt;br /&gt;
        api.get({&lt;br /&gt;
            action: &amp;#039;query&amp;#039;,&lt;br /&gt;
            list: &amp;#039;recentchanges&amp;#039;,&lt;br /&gt;
            rclimit: 200,&lt;br /&gt;
            rcprop: &amp;#039;user|title|timestamp&amp;#039;,&lt;br /&gt;
            rcshow: &amp;#039;!bot&amp;#039;,&lt;br /&gt;
            rcnamespace: 0,&lt;br /&gt;
            format: &amp;#039;json&amp;#039;&lt;br /&gt;
        }).then(function(data) {&lt;br /&gt;
            var pageMap = {};&lt;br /&gt;
            var activeUsers = new Set();&lt;br /&gt;
&lt;br /&gt;
            if (data.query &amp;amp;&amp;amp; data.query.recentchanges) {&lt;br /&gt;
                data.query.recentchanges.forEach(function(rc) {&lt;br /&gt;
                    var title = rc.title;&lt;br /&gt;
                    var user = rc.user;&lt;br /&gt;
                    var timeDiff = Date.now() - new Date(rc.timestamp).getTime();&lt;br /&gt;
&lt;br /&gt;
                    if (timeDiff &amp;lt; 60000 &amp;amp;&amp;amp; user !== BOT_NAME) {&lt;br /&gt;
                        if (!pageMap[title]) pageMap[title] = new Set();&lt;br /&gt;
                        pageMap[title].add(user);&lt;br /&gt;
                        activeUsers.add(user);&lt;br /&gt;
                    }&lt;br /&gt;
                });&lt;br /&gt;
            }&lt;br /&gt;
&lt;br /&gt;
            var totalEditors = 0;&lt;br /&gt;
            var writePromises = [];&lt;br /&gt;
&lt;br /&gt;
            for (var page in pageMap) {&lt;br /&gt;
                var editors = Array.from(pageMap[page]);&lt;br /&gt;
                totalEditors += editors.length;&lt;br /&gt;
&lt;br /&gt;
                editors.forEach(function(editor) {&lt;br /&gt;
                    if (editor === BOT_NAME) return;&lt;br /&gt;
                    var otherEditors = editors.filter(function(e) {&lt;br /&gt;
                        return e !== editor &amp;amp;&amp;amp; e !== BOT_NAME;&lt;br /&gt;
                    });&lt;br /&gt;
                    writePromises.push(writeUserStatus(editor, page, otherEditors));&lt;br /&gt;
                });&lt;br /&gt;
            }&lt;br /&gt;
&lt;br /&gt;
            // 清理不在线的用户状态&lt;br /&gt;
            var cleanupPromise = cleanupOldStatus(activeUsers);&lt;br /&gt;
&lt;br /&gt;
            Promise.all(writePromises).then(function() {&lt;br /&gt;
                countEl.textContent = totalEditors;&lt;br /&gt;
                if (totalEditors &amp;gt; 0) {&lt;br /&gt;
                    var editorList = Array.from(activeUsers).slice(0, 5).join(&amp;#039;、&amp;#039;);&lt;br /&gt;
                    log(&amp;#039;📊 检测到 &amp;#039; + totalEditors + &amp;#039; 位活跃用户：&amp;#039; + editorList + (activeUsers.size &amp;gt; 5 ? &amp;#039; ...&amp;#039; : &amp;#039;&amp;#039;), &amp;#039;editor&amp;#039;);&lt;br /&gt;
                } else {&lt;br /&gt;
                    log(&amp;#039;📊 暂无活跃用户&amp;#039;, &amp;#039;mute&amp;#039;);&lt;br /&gt;
                }&lt;br /&gt;
            }).catch(function(err) {&lt;br /&gt;
                log(&amp;#039;⚠️ 写入失败: &amp;#039; + err.message, &amp;#039;warning&amp;#039;);&lt;br /&gt;
            });&lt;br /&gt;
&lt;br /&gt;
        }).fail(function(err) {&lt;br /&gt;
            log(&amp;#039;❌ 扫描失败: &amp;#039; + (err.error?.info || err.message || &amp;#039;未知错误&amp;#039;), &amp;#039;error&amp;#039;);&lt;br /&gt;
        });&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 写入用户状态 ============&lt;br /&gt;
    function writeUserStatus(username, page, editors) {&lt;br /&gt;
        return new Promise(function(resolve, reject) {&lt;br /&gt;
            var statusPage = &amp;#039;User:&amp;#039; + username + &amp;#039;/edit-status&amp;#039;;&lt;br /&gt;
            var api = new mw.Api();&lt;br /&gt;
&lt;br /&gt;
            var statusData = {&lt;br /&gt;
                page: page,&lt;br /&gt;
                editors: editors.map(function(e) {&lt;br /&gt;
                    return { user: e, timestamp: Date.now() };&lt;br /&gt;
                }),&lt;br /&gt;
                timestamp: Date.now(),&lt;br /&gt;
                checkedBy: BOT_NAME,&lt;br /&gt;
                status: editors.length &amp;gt; 0 ? &amp;#039;editing&amp;#039; : &amp;#039;idle&amp;#039;&lt;br /&gt;
            };&lt;br /&gt;
&lt;br /&gt;
            api.postWithEditToken({&lt;br /&gt;
                action: &amp;#039;edit&amp;#039;,&lt;br /&gt;
                title: statusPage,&lt;br /&gt;
                text: JSON.stringify(statusData, null, 2),&lt;br /&gt;
                summary: &amp;#039;🤖 &amp;#039; + BOT_NAME + &amp;#039; 检测编辑状态&amp;#039;,&lt;br /&gt;
                minor: true,&lt;br /&gt;
                bot: true&lt;br /&gt;
            }).then(function() {&lt;br /&gt;
                writeCount++;&lt;br /&gt;
                writesEl.textContent = writeCount;&lt;br /&gt;
                resolve();&lt;br /&gt;
            }).fail(function(err) {&lt;br /&gt;
                reject(err);&lt;br /&gt;
            });&lt;br /&gt;
        });&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 清理过期状态 ============&lt;br /&gt;
    function cleanupOldStatus(activeUsers) {&lt;br /&gt;
        return new Promise(function(resolve) {&lt;br /&gt;
            var api = new mw.Api();&lt;br /&gt;
            api.get({&lt;br /&gt;
                action: &amp;#039;query&amp;#039;,&lt;br /&gt;
                list: &amp;#039;allpages&amp;#039;,&lt;br /&gt;
                apnamespace: 2,&lt;br /&gt;
                apprefix: &amp;#039;edit-status&amp;#039;,&lt;br /&gt;
                aplimit: 100,&lt;br /&gt;
                format: &amp;#039;json&amp;#039;&lt;br /&gt;
            }).then(function(data) {&lt;br /&gt;
                if (!data.query || !data.query.allpages) {&lt;br /&gt;
                    resolve();&lt;br /&gt;
                    return;&lt;br /&gt;
                }&lt;br /&gt;
&lt;br /&gt;
                var promises = [];&lt;br /&gt;
                data.query.allpages.forEach(function(page) {&lt;br /&gt;
                    var username = page.title.replace(&amp;#039;User:&amp;#039;, &amp;#039;&amp;#039;).replace(&amp;#039;/edit-status&amp;#039;, &amp;#039;&amp;#039;);&lt;br /&gt;
                    if (username === BOT_NAME || activeUsers.has(username)) return;&lt;br /&gt;
&lt;br /&gt;
                    var p = new mw.Api().get({&lt;br /&gt;
                        action: &amp;#039;query&amp;#039;,&lt;br /&gt;
                        titles: page.title,&lt;br /&gt;
                        prop: &amp;#039;revisions&amp;#039;,&lt;br /&gt;
                        rvprop: &amp;#039;content&amp;#039;,&lt;br /&gt;
                        rvlimit: 1,&lt;br /&gt;
                        format: &amp;#039;json&amp;#039;&lt;br /&gt;
                    }).then(function(contentData) {&lt;br /&gt;
                        var pages = contentData.query.pages;&lt;br /&gt;
                        for (var id in pages) {&lt;br /&gt;
                            if (pages[id].revisions &amp;amp;&amp;amp; pages[id].revisions[0]) {&lt;br /&gt;
                                try {&lt;br /&gt;
                                    var status = JSON.parse(pages[id].revisions[0][&amp;#039;*&amp;#039;]);&lt;br /&gt;
                                    if (status.status === &amp;#039;editing&amp;#039; &amp;amp;&amp;amp; (Date.now() - status.timestamp) &amp;gt; 60000) {&lt;br /&gt;
                                        var api2 = new mw.Api();&lt;br /&gt;
                                        var statusData = {&lt;br /&gt;
                                            page: status.page || &amp;#039;&amp;#039;,&lt;br /&gt;
                                            editors: [],&lt;br /&gt;
                                            timestamp: Date.now(),&lt;br /&gt;
                                            checkedBy: BOT_NAME,&lt;br /&gt;
                                            status: &amp;#039;idle&amp;#039;&lt;br /&gt;
                                        };&lt;br /&gt;
                                        return api2.postWithEditToken({&lt;br /&gt;
                                            action: &amp;#039;edit&amp;#039;,&lt;br /&gt;
                                            title: page.title,&lt;br /&gt;
                                            text: JSON.stringify(statusData, null, 2),&lt;br /&gt;
                                            summary: &amp;#039;🤖 &amp;#039; + BOT_NAME + &amp;#039; 清理过期状态&amp;#039;,&lt;br /&gt;
                                            minor: true,&lt;br /&gt;
                                            bot: true&lt;br /&gt;
                                        });&lt;br /&gt;
                                    }&lt;br /&gt;
                                } catch(e) {}&lt;br /&gt;
                            }&lt;br /&gt;
                        }&lt;br /&gt;
                        return Promise.resolve();&lt;br /&gt;
                    });&lt;br /&gt;
                    promises.push(p);&lt;br /&gt;
                });&lt;br /&gt;
&lt;br /&gt;
                Promise.all(promises).then(resolve);&lt;br /&gt;
            }).fail(function() { resolve(); });&lt;br /&gt;
        });&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 执行一轮 ============&lt;br /&gt;
    function doRound() {&lt;br /&gt;
        if (!running) return;&lt;br /&gt;
        log(&amp;#039;🔄 扫描中...&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
        scanAllEditors();&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 控制功能 ============&lt;br /&gt;
    function startBot() {&lt;br /&gt;
        if (running) return;&lt;br /&gt;
        running = true;&lt;br /&gt;
        var interval = parseInt(intervalInput.value) || 3;&lt;br /&gt;
        CHECK_INTERVAL = interval * 1000;&lt;br /&gt;
        statusEl.textContent = &amp;#039;● 运行中&amp;#039;;&lt;br /&gt;
        statusEl.style.color = &amp;#039;#00ff00&amp;#039;;&lt;br /&gt;
        toggleBtn.textContent = &amp;#039;停止&amp;#039;;&lt;br /&gt;
        toggleBtn.style.background = &amp;#039;#ff4444&amp;#039;;&lt;br /&gt;
        log(&amp;#039;✅ 机器人已启动，间隔 &amp;#039; + interval + &amp;#039; 秒&amp;#039;, &amp;#039;success&amp;#039;);&lt;br /&gt;
        doRound();&lt;br /&gt;
        timer = setInterval(doRound, CHECK_INTERVAL);&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    function stopBot() {&lt;br /&gt;
        if (!running) return;&lt;br /&gt;
        running = false;&lt;br /&gt;
        if (timer) {&lt;br /&gt;
            clearInterval(timer);&lt;br /&gt;
            timer = null;&lt;br /&gt;
        }&lt;br /&gt;
        statusEl.textContent = &amp;#039;● 已停止&amp;#039;;&lt;br /&gt;
        statusEl.style.color = &amp;#039;#ff4444&amp;#039;;&lt;br /&gt;
        toggleBtn.textContent = &amp;#039;启动&amp;#039;;&lt;br /&gt;
        toggleBtn.style.background = &amp;#039;#44aa44&amp;#039;;&lt;br /&gt;
        log(&amp;#039;⏹️ 机器人已停止&amp;#039;, &amp;#039;warning&amp;#039;);&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    function toggleBot() {&lt;br /&gt;
        if (running) {&lt;br /&gt;
            stopBot();&lt;br /&gt;
        } else {&lt;br /&gt;
            startBot();&lt;br /&gt;
        }&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // ============ 拖拽支持 ============&lt;br /&gt;
    var consoleEl = document.getElementById(&amp;#039;bot-console&amp;#039;);&lt;br /&gt;
    var isDragging = false;&lt;br /&gt;
    var startX, startY, origX, origY;&lt;br /&gt;
&lt;br /&gt;
    consoleEl.querySelector(&amp;#039;div:first-child&amp;#039;).addEventListener(&amp;#039;mousedown&amp;#039;, function(e) {&lt;br /&gt;
        if (e.target.tagName === &amp;#039;BUTTON&amp;#039;) return;&lt;br /&gt;
        isDragging = true;&lt;br /&gt;
        startX = e.clientX;&lt;br /&gt;
        startY = e.clientY;&lt;br /&gt;
        origX = consoleEl.offsetLeft;&lt;br /&gt;
        origY = consoleEl.offsetTop;&lt;br /&gt;
        consoleEl.style.cursor = &amp;#039;grabbing&amp;#039;;&lt;br /&gt;
        e.preventDefault();&lt;br /&gt;
    });&lt;br /&gt;
&lt;br /&gt;
    document.addEventListener(&amp;#039;mousemove&amp;#039;, function(e) {&lt;br /&gt;
        if (!isDragging) return;&lt;br /&gt;
        var dx = e.clientX - startX;&lt;br /&gt;
        var dy = e.clientY - startY;&lt;br /&gt;
        consoleEl.style.left = (origX + dx) + &amp;#039;px&amp;#039;;&lt;br /&gt;
        consoleEl.style.top = (origY + dy) + &amp;#039;px&amp;#039;;&lt;br /&gt;
        consoleEl.style.right = &amp;#039;auto&amp;#039;;&lt;br /&gt;
        consoleEl.style.bottom = &amp;#039;auto&amp;#039;;&lt;br /&gt;
    });&lt;br /&gt;
&lt;br /&gt;
    document.addEventListener(&amp;#039;mouseup&amp;#039;, function() {&lt;br /&gt;
        isDragging = false;&lt;br /&gt;
        consoleEl.style.cursor = &amp;#039;default&amp;#039;;&lt;br /&gt;
    });&lt;br /&gt;
&lt;br /&gt;
    // ============ 按钮绑定 ============&lt;br /&gt;
    document.getElementById(&amp;#039;bot-toggle&amp;#039;).addEventListener(&amp;#039;click&amp;#039;, toggleBot);&lt;br /&gt;
    document.getElementById(&amp;#039;bot-close&amp;#039;).addEventListener(&amp;#039;click&amp;#039;, function() {&lt;br /&gt;
        if (running) stopBot();&lt;br /&gt;
        consoleEl.style.display = &amp;#039;none&amp;#039;;&lt;br /&gt;
        log(&amp;#039;📦 控制台已隐藏，重新打开请运行 showBot()&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
    });&lt;br /&gt;
    document.getElementById(&amp;#039;bot-scan&amp;#039;).addEventListener(&amp;#039;click&amp;#039;, function() {&lt;br /&gt;
        if (running) {&lt;br /&gt;
            log(&amp;#039;🔄 手动扫描...&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
            doRound();&lt;br /&gt;
        } else {&lt;br /&gt;
            log(&amp;#039;⚠️ 机器人已停止，请先启动&amp;#039;, &amp;#039;warning&amp;#039;);&lt;br /&gt;
        }&lt;br /&gt;
    });&lt;br /&gt;
    document.getElementById(&amp;#039;bot-clear&amp;#039;).addEventListener(&amp;#039;click&amp;#039;, function() {&lt;br /&gt;
        logEl.innerHTML = &amp;#039;&amp;#039;;&lt;br /&gt;
        log(&amp;#039;🗑️ 日志已清空&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
    });&lt;br /&gt;
&lt;br /&gt;
    intervalInput.addEventListener(&amp;#039;change&amp;#039;, function() {&lt;br /&gt;
        var val = parseInt(this.value) || 3;&lt;br /&gt;
        if (val &amp;lt; 1) this.value = 1;&lt;br /&gt;
        if (val &amp;gt; 30) this.value = 30;&lt;br /&gt;
        if (running) {&lt;br /&gt;
            log(&amp;#039;⏱️ 间隔已改为 &amp;#039; + this.value + &amp;#039; 秒，重启生效&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
            stopBot();&lt;br /&gt;
            startBot();&lt;br /&gt;
        }&lt;br /&gt;
    });&lt;br /&gt;
&lt;br /&gt;
    // ============ 暴露全局 ============&lt;br /&gt;
    window.showBot = function() {&lt;br /&gt;
        consoleEl.style.display = &amp;#039;block&amp;#039;;&lt;br /&gt;
        log(&amp;#039;📦 控制台已显示&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
    };&lt;br /&gt;
    window.hideBot = function() {&lt;br /&gt;
        consoleEl.style.display = &amp;#039;none&amp;#039;;&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    // ============ 自动启动 ============&lt;br /&gt;
    log(&amp;#039;🤖 &amp;#039; + BOT_NAME + &amp;#039; 控制台已加载&amp;#039;, &amp;#039;success&amp;#039;);&lt;br /&gt;
    log(&amp;#039;💡 点击 &amp;quot;启动&amp;quot; 开始检测，或拖拽移动控制台&amp;#039;, &amp;#039;info&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
    // 自动启动&lt;br /&gt;
    startBot();&lt;br /&gt;
&lt;br /&gt;
})();&lt;br /&gt;
&amp;lt;/script&amp;gt;&lt;/div&gt;</summary>
		<author><name>EditBot</name></author>
	</entry>
</feed>