Focus Assistant - Site Blocker

Blocks distracting websites with a full-screen red overlay to help you stay focused.

当前为 2025-07-10 提交的版本,查看 最新版本

// ==UserScript==
// @name         Focus Assistant - Site Blocker
// @namespace    https://gf.qytechs.cn/users/1111205-geekfox
// @version      1.2
// @description  Blocks distracting websites with a full-screen red overlay to help you stay focused.
// @author       GeekFox
// @match        *://*/*
// @grant        GM_setValue
// @grant        GM_getValue
// @grant        GM_registerMenuCommand
// @run-at       document-start
// @license      MIT
// ==/UserScript==

(function () {
    'use strict';

    // 获取存储的设置
    const BLOCKED_SITES_KEY = 'blockedSites';
    const BLOCK_ENABLED_KEY = 'blockEnabled';
    
    let blockedSites = GM_getValue(BLOCKED_SITES_KEY, []);
    let blockEnabled = GM_getValue(BLOCK_ENABLED_KEY, true);

    // 注册(不可用)菜单命令
    GM_registerMenuCommand('📝 编辑屏蔽网站列表', openSettings);
    GM_registerMenuCommand(blockEnabled ? '✅ 屏蔽已启用' : '❌ 屏蔽已禁用', toggleBlocking);
    GM_registerMenuCommand('➕ 添加当前网站', addCurrentSite);
    GM_registerMenuCommand('⏳ 临时禁用屏蔽(1小时)', disableTemporarily);

    // 检查当前网站是否需要屏蔽
    function shouldBlockSite() {
        if (!blockEnabled) return false;
        
        const hostname = window.location.hostname;
        return blockedSites.some(site => {
            // 支持通配符匹配
            const regex = new RegExp('^' + site.replace(/\*/g, '.*') + '$');
            return regex.test(hostname);
        });
    }

    // 创建屏蔽页面
    function createBlockPage() {
        // 移除页面原有内容
        document.documentElement.innerHTML = '';
        
        // 创建全屏覆盖层
        const overlay = document.createElement('div');
        overlay.style = `
            position: fixed;
            top: 0;
            left: 0;
            width: 100%;
            height: 100%;
            background: linear-gradient(135deg, #ff0000, #b30000);
            display: flex;
            flex-direction: column;
            justify-content: center;
            align-items: center;
            z-index: 999999;
            color: white;
            font-family: Arial, sans-serif;
            text-align: center;
            padding: 20px;
            box-sizing: border-box;
        `;
        
        // 添加标题
        const title = document.createElement('h1');
        title.textContent = 'BE FOCUSED!';
        title.style = `
            font-size: 6em;
            font-weight: 900;
            margin: 0;
            text-shadow: 0px 4px 10px rgba(0, 0, 0, 0.5);
            letter-spacing: 2px;
        `;
        
        // 添加消息
        const message = document.createElement('p');
        message.textContent = 'This website has been blocked to help you stay focused on your work.';
        message.style = `
            font-size: 1.8em;
            max-width: 800px;
            margin: 20px 0;
            line-height: 1.5;
        `;
        
        // 添加当前网站信息
        const siteInfo = document.createElement('p');
        siteInfo.textContent = `Blocked site: ${window.location.hostname}`;
        siteInfo.style = `
            font-size: 1.5em;
            margin: 10px 0;
            color: rgba(255, 255, 255, 0.8);
        `;
        
        // 添加设置链接
        const settingsLink = document.createElement('button');
        settingsLink.textContent = 'Edit Blocked Sites';
        settingsLink.style = `
            background: white;
            color: #ff0000;
            border: none;
            padding: 15px 30px;
            font-size: 1.3em;
            font-weight: bold;
            border-radius: 8px;
            cursor: pointer;
            margin-top: 30px;
            box-shadow: 0px 4px 15px rgba(0, 0, 0, 0.2);
            transition: transform 0.2s, box-shadow 0.2s;
        `;
        settingsLink.onmouseover = () => {
            settingsLink.style.transform = 'scale(1.05)';
            settingsLink.style.boxShadow = '0px 6px 20px rgba(0, 0, 0, 0.3)';
        };
        settingsLink.onmouseout = () => {
            settingsLink.style.transform = 'scale(1)';
            settingsLink.style.boxShadow = '0px 4px 15px rgba(0, 0, 0, 0.2)';
        };
        settingsLink.onclick = openSettings;
        
        // 添加计时器
        const timer = document.createElement('div');
        timer.id = 'focus-timer';
        timer.style = `
            margin-top: 30px;
            font-size: 1.5em;
            background: rgba(0, 0, 0, 0.2);
            padding: 10px 20px;
            border-radius: 8px;
        `;
        
        // 组装页面
        overlay.appendChild(title);
        overlay.appendChild(message);
        overlay.appendChild(siteInfo);
        overlay.appendChild(settingsLink);
        overlay.appendChild(timer);
        document.body.appendChild(overlay);
        
        // 开始倒计时
        startTimer(timer);
    }

    // 专注计时器
    function startTimer(element) {
        let seconds = 0;
        setInterval(() => {
            seconds++;
            const hours = Math.floor(seconds / 3600);
            const minutes = Math.floor((seconds % 3600) / 60);
            const secs = seconds % 60;
            
            element.textContent = `You've been focused for: ${hours.toString().padStart(2, '0')}:${minutes.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;
        }, 1000);
    }

    // 打开设置
    function openSettings() {
        // 创建设置弹窗
        const modal = document.createElement('div');
        modal.style = `
            position: fixed;
            top: 0;
            left: 0;
            width: 100%;
            height: 100%;
            background: rgba(0, 0, 0, 0.7);
            display: flex;
            justify-content: center;
            align-items: center;
            z-index: 1000000;
        `;
        
        // 设置内容
        const content = document.createElement('div');
        content.style = `
            background: white;
            border-radius: 12px;
            padding: 30px;
            width: 80%;
            max-width: 600px;
            max-height: 80vh;
            overflow: auto;
            box-shadow: 0 10px 30px rgba(0, 0, 0, 0.3);
        `;
        
        // 标题
        const title = document.createElement('h2');
        title.textContent = 'Focus Assistant Settings';
        title.style = `
            color: #b30000;
            margin-top: 0;
            text-align: center;
        `;
        
        // 说明
        const instructions = document.createElement('p');
        instructions.innerHTML = 'Enter websites to block (one per line).<br>Use <code>*</code> as wildcard (e.g., <code>*.youtube.com</code>).';
        instructions.style = 'margin-bottom: 20px;';
        
        // 网站列表文本框
        const textarea = document.createElement('textarea');
        textarea.style = `
            width: 100%;
            height: 200px;
            padding: 10px;
            box-sizing: border-box;
            border: 2px solid #ddd;
            border-radius: 8px;
            font-family: monospace;
            margin-bottom: 20px;
        `;
        textarea.value = blockedSites.join('\n');
        
        // 按钮容器
        const buttonContainer = document.createElement('div');
        buttonContainer.style = `
            display: flex;
            justify-content: space-between;
            gap: 10px;
        `;
        
        // 保存按钮
        const saveButton = document.createElement('button');
        saveButton.textContent = 'Save';
        saveButton.style = `
            flex: 1;
            padding: 12px;
            background: #28a745;
            color: white;
            border: none;
            border-radius: 8px;
            font-size: 1.1em;
            cursor: pointer;
        `;
        saveButton.onclick = () => {
            blockedSites = textarea.value.split('\n')
                .map(site => site.trim())
                .filter(site => site.length > 0);
            GM_setValue(BLOCKED_SITES_KEY, blockedSites);
            modal.remove();
            if (shouldBlockSite()) {
                createBlockPage();
            }
        };
        
        // 取消按钮
        const cancelButton = document.createElement('button');
        cancelButton.textContent = 'Cancel';
        cancelButton.style = `
            flex: 1;
            padding: 12px;
            background: #6c757d;
            color: white;
            border: none;
            border-radius: 8px;
            font-size: 1.1em;
            cursor: pointer;
        `;
        cancelButton.onclick = () => modal.remove();
        
        // 添加当前网站按钮
        const addCurrentButton = document.createElement('button');
        addCurrentButton.textContent = 'Add Current';
        addCurrentButton.style = `
            flex: 1;
            padding: 12px;
            background: #007bff;
            color: white;
            border: none;
            border-radius: 8px;
            font-size: 1.1em;
            cursor: pointer;
        `;
        addCurrentButton.onclick = () => {
            const currentSite = window.location.hostname;
            if (!textarea.value.includes(currentSite)) {
                textarea.value += (textarea.value ? '\n' : '') + currentSite;
            }
        };
        
        // 组装元素
        buttonContainer.appendChild(saveButton);
        buttonContainer.appendChild(cancelButton);
        buttonContainer.appendChild(addCurrentButton);
        
        content.appendChild(title);
        content.appendChild(instructions);
        content.appendChild(textarea);
        content.appendChild(buttonContainer);
        modal.appendChild(content);
        document.body.appendChild(modal);
    }

    // 添加当前网站
    function addCurrentSite() {
        const currentSite = window.location.hostname;
        if (!blockedSites.includes(currentSite)) {
            blockedSites.push(currentSite);
            GM_setValue(BLOCKED_SITES_KEY, blockedSites);
            if (shouldBlockSite()) {
                createBlockPage();
            }
        }
    }

    // 切换屏蔽状态
    function toggleBlocking() {
        blockEnabled = !blockEnabled;
        GM_setValue(BLOCK_ENABLED_KEY, blockEnabled);
        location.reload(); // 刷新页面应用更改
    }

    // 临时禁用屏蔽
    function disableTemporarily() {
        blockEnabled = false;
        GM_setValue(BLOCK_ENABLED_KEY, blockEnabled);
        
        // 1小时后自动重新启用
        setTimeout(() => {
            blockEnabled = true;
            GM_setValue(BLOCK_ENABLED_KEY, blockEnabled);
        }, 60 * 60 * 1000);
        
        location.reload();
    }

    // 页面加载时检查是否需要屏蔽
    if (shouldBlockSite()) {
        // 使用setTimeout确保DOM完全加载
        window.addEventListener('DOMContentLoaded', createBlockPage);
    }
})();

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址