Smart Notes Pro

Умные заметки с настраиваемыми генераторами

이 스크립트를 설치하려면 Tampermonkey, Greasemonkey 또는 Violentmonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey와 같은 확장 프로그램을 설치해야 합니다.

이 스크립트를 설치하려면 Tampermonkey 또는 Violentmonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey 또는 Userscripts와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 유저 스크립트 관리자 확장 프로그램이 필요합니다.

(이미 유저 스크립트 관리자가 설치되어 있습니다. 설치를 진행합니다!)

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

(이미 유저 스타일 관리자가 설치되어 있습니다. 설치를 진행합니다!)

// ==UserScript==
// @name         Smart Notes Pro
// @namespace    http://tampermonkey.net/
// @version      3.4
// @description  Умные заметки с настраиваемыми генераторами
// @author       Вы
// @match        *://*/*
// @grant        GM_getValue
// @grant        GM_setValue
// @grant        GM_addStyle
// @run-at       document-end
// ==/UserScript==

(function() {
    'use strict';

    // Загрузка сохраненных данных
    let savedData = GM_getValue('smart_notes_data');
    let userRN = GM_getValue('user_rn');
    let userANTemplate = GM_getValue('user_an_template');

    // Если это первый запуск или нет данных - запрашиваем у пользователя
    if (!userRN || !userANTemplate || !savedData) {
        setupFirstRun();
        return; // Прерываем выполнение, setupFirstRun сам перезагрузит скрипт
    }

    // Инициализация сохраненных значений
    if (!savedData) {
        savedData = {
            an: generateANFromTemplate(userANTemplate),
            email: generateRandomEmail(16),
            password: generateRandomPassword(8),
            phone: generateUSAPhoneNumber()
        };
        GM_setValue('smart_notes_data', savedData);
    }

    // Получаем сохраненные пользовательские заметки
    const USER_NOTES = GM_getValue('user_smart_notes', 'Ваши заметки здесь...\nСохраняются автоматически.');

    // Функция для первого запуска - запрос RN и шаблона AN
    function setupFirstRun() {
        // Создаем стили для модального окна
        GM_addStyle(`
            #setup-modal {
                position: fixed;
                top: 0;
                left: 0;
                width: 100%;
                height: 100%;
                background: rgba(0, 0, 0, 0.8);
                z-index: 1000000;
                display: flex;
                justify-content: center;
                align-items: center;
                font-family: 'SF Pro Text', -apple-system, sans-serif;
            }

            .setup-container {
                background: white;
                padding: 30px;
                border-radius: 12px;
                width: 400px;
                max-width: 90%;
                box-shadow: 0 10px 30px rgba(0, 0, 0, 0.3);
            }

            .setup-title {
                font-size: 20px;
                font-weight: 600;
                color: #1976D2;
                margin-bottom: 20px;
                text-align: center;
            }

            .setup-input-group {
                margin-bottom: 20px;
            }

            .setup-label {
                display: block;
                font-size: 14px;
                font-weight: 500;
                margin-bottom: 8px;
                color: #333;
            }

            .setup-input {
                width: 100%;
                padding: 10px 12px;
                border: 2px solid #e0e0e0;
                border-radius: 6px;
                font-size: 14px;
                font-family: 'SF Mono', Monaco, monospace;
                box-sizing: border-box;
            }

            .setup-input:focus {
                outline: none;
                border-color: #2196F3;
                box-shadow: 0 0 0 3px rgba(33, 150, 243, 0.2);
            }

            .setup-info {
                font-size: 12px;
                color: #666;
                margin-top: 5px;
            }

            .setup-example {
                background: #f5f5f5;
                padding: 8px 12px;
                border-radius: 4px;
                font-family: 'SF Mono', Monaco, monospace;
                font-size: 13px;
                margin: 5px 0;
                border: 1px solid #e0e0e0;
            }

            .setup-button {
                width: 100%;
                padding: 12px;
                background: linear-gradient(to right, #4CAF50, #45a049);
                color: white;
                border: none;
                border-radius: 6px;
                font-size: 14px;
                font-weight: 500;
                cursor: pointer;
                transition: all 0.2s;
                margin-top: 10px;
            }

            .setup-button:hover {
                background: linear-gradient(to right, #45a049, #388E3C);
                transform: translateY(-1px);
            }
        `);

        // Создаем модальное окно
        const modal = document.createElement('div');
        modal.id = 'setup-modal';
        modal.innerHTML = `
            <div class="setup-container">
                <div class="setup-title">🚀 Настройка Smart Notes</div>

                <div class="setup-input-group">
                    <label class="setup-label">Введите RN (9 цифр):</label>
                    <input type="text" id="rn-input" class="setup-input" placeholder="253177049" maxlength="9">
                    <div class="setup-info">RN не изменяется, это фиксированный номер</div>
                    <div class="setup-example">Пример: 253177049</div>
                </div>

                <div class="setup-input-group">
                    <label class="setup-label">Введите шаблон для AN:</label>
                    <input type="text" id="an-input" class="setup-input" placeholder="448XXXXX" maxlength="8">
                    <div class="setup-info">Первые цифры - фиксированные, X - случайные цифры</div>
                    <div class="setup-example">Пример: 448XXXXX (8 цифр: 448 + 5 случайных)</div>
                    <div class="setup-example">Пример: 44XXXXXX (8 цифр: 44 + 6 случайных)</div>
                </div>

                <button id="save-setup" class="setup-button">💾 Сохранить и продолжить</button>
            </div>
        `;

        document.body.appendChild(modal);

        // Фокус на первом поле
        setTimeout(() => {
            document.getElementById('rn-input').focus();
        }, 100);

        // Обработчик сохранения
        document.getElementById('save-setup').addEventListener('click', function() {
            const rnInput = document.getElementById('rn-input').value.trim();
            const anInput = document.getElementById('an-input').value.trim();

            // Проверка RN
            if (!/^\d{9}$/.test(rnInput)) {
                alert('❌ RN должен содержать ровно 9 цифр!');
                document.getElementById('rn-input').focus();
                return;
            }

            // Проверка шаблона AN
            if (!/^\d{1,7}X{1,7}$/.test(anInput) || anInput.length !== 8) {
                alert('❌ Шаблон AN должен содержать 8 символов: цифры и буквы X\nПример: 448XXXXX');
                document.getElementById('an-input').focus();
                return;
            }

            // Сохраняем данные
            GM_setValue('user_rn', rnInput);
            GM_setValue('user_an_template', anInput);

            // Создаем начальные данные
            const initialData = {
                an: generateANFromTemplate(anInput),
                email: generateRandomEmail(16),
                password: generateRandomPassword(8),
                phone: generateUSAPhoneNumber()
            };
            GM_setValue('smart_notes_data', initialData);

            // Удаляем модальное окно
            modal.remove();

            // Перезагружаем страницу для применения настроек
            showNotification('✅ Настройки сохранены! Перезагружаем...');
            setTimeout(() => {
                location.reload();
            }, 1000);
        });

        // Поддержка Enter для сохранения
        modal.addEventListener('keydown', function(e) {
            if (e.key === 'Enter') {
                document.getElementById('save-setup').click();
            }
        });
    }

    // Генерация AN по шаблону
    function generateANFromTemplate(template) {
        let result = '';
        for (let char of template) {
            if (char === 'X') {
                result += Math.floor(Math.random() * 10);
            } else {
                result += char;
            }
        }
        return result;
    }

    // Функция для генерации случайных цифр
    function generateRandomDigits(length) {
        let result = '';
        for (let i = 0; i < length; i++) {
            result += Math.floor(Math.random() * 10);
        }
        return result;
    }

    // Функция для генерации случайных букв
    function generateRandomLetters(length, uppercase = false) {
        let result = '';
        const chars = 'abcdefghijklmnopqrstuvwxyz';
        for (let i = 0; i < length; i++) {
            let char = chars.charAt(Math.floor(Math.random() * chars.length));
            result += uppercase ? char.toUpperCase() : char;
        }
        return result;
    }

    // Генерация случайной почты
    function generateRandomEmail(length = 16) {
        const prefix = generateRandomLetters(length - 10) + generateRandomDigits(3);
        return prefix.toLowerCase() + '@yahoo.com';
    }

    // Генерация случайного пароля
    function generateRandomPassword(length = 8) {
        const lowercase = 'abcdefghijklmnopqrstuvwxyz';
        const uppercase = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
        const digits = '0123456789';
        const specials = '!@#$%^&*';

        // Гарантируем хотя бы одну цифру, одну заглавную букву и один спецсимвол
        let password = '';
        password += uppercase.charAt(Math.floor(Math.random() * uppercase.length)); // Заглавная буква
        password += digits.charAt(Math.floor(Math.random() * digits.length)); // Цифра
        password += specials.charAt(Math.floor(Math.random() * specials.length)); // Спецсимвол

        // Заполняем оставшиеся символы
        const allChars = lowercase + uppercase + digits + specials;
        for (let i = password.length; i < length; i++) {
            password += allChars.charAt(Math.floor(Math.random() * allChars.length));
        }

        // Перемешиваем символы
        return password.split('').sort(() => Math.random() - 0.5).join('');
    }

    // Генерация USA номера телефона (10 цифр без форматирования)
    function generateUSAPhoneNumber() {
        return generateRandomDigits(10);
    }

    // Функция копирования в буфер обмена
    function copyToClipboard(text) {
        navigator.clipboard.writeText(text).then(() => {
            showNotification('✅ Скопировано: ' + (text.length > 20 ? text.substring(0, 20) + '...' : text));
        }).catch(err => {
            // Fallback для старых браузеров
            const textArea = document.createElement('textarea');
            textArea.value = text;
            document.body.appendChild(textArea);
            textArea.select();
            document.execCommand('copy');
            document.body.removeChild(textArea);
            showNotification('✅ Скопировано');
        });
    }

    // Функция обновления генератора
    function refreshGenerator(type) {
        let newValue;

        switch(type) {
            case 'an':
                newValue = generateANFromTemplate(userANTemplate);
                savedData.an = newValue;
                break;
            case 'email':
                newValue = generateRandomEmail(16);
                savedData.email = newValue;
                break;
            case 'password':
                newValue = generateRandomPassword(8);
                savedData.password = newValue;
                break;
            case 'phone':
                newValue = generateUSAPhoneNumber();
                savedData.phone = newValue;
                break;
        }

        // Обновляем отображение
        const valueElement = document.querySelector(`.generator-value.${type}`);
        const row = valueElement.closest('.generator-row');
        const copyBtn = row.querySelector('.gen-copy');

        valueElement.textContent = newValue;
        valueElement.onclick = () => copyToClipboard(newValue);
        copyBtn.onclick = () => copyToClipboard(newValue);

        // Сохраняем
        GM_setValue('smart_notes_data', savedData);

        showNotification(`🔄 Обновлен ${type}: ${newValue}`);
    }

    // Стили для основного окна
    GM_addStyle(`
        #smart-notes-btn {
            position: fixed;
            top: 20px;
            right: 20px;
            width: 60px;
            height: 60px;
            background: linear-gradient(135deg, #2196F3, #1976D2);
            color: white;
            border: none;
            border-radius: 50%;
            cursor: pointer;
            z-index: 999999;
            font-size: 24px;
            box-shadow: 0 4px 12px rgba(33, 150, 243, 0.4);
            transition: all 0.3s ease;
            display: flex;
            align-items: center;
            justify-content: center;
            padding: 0;
        }

        #smart-notes-btn:hover {
            transform: scale(1.1);
            box-shadow: 0 6px 15px rgba(33, 150, 243, 0.6);
        }

        #smart-notes-window {
            position: fixed;
            top: 100px;
            right: 20px;
            width: 380px;
            background: white;
            border: 2px solid #2196F3;
            border-radius: 12px;
            box-shadow: 0 8px 25px rgba(33, 150, 243, 0.3);
            z-index: 999998;
            font-family: 'SF Pro Text', -apple-system, sans-serif;
            display: none;
            overflow: hidden;
        }

        #notes-header {
            background: linear-gradient(135deg, #2196F3, #1976D2);
            color: white;
            padding: 16px 20px;
            border-radius: 10px 10px 0 0;
            cursor: move;
            display: flex;
            justify-content: space-between;
            align-items: center;
            font-weight: 600;
            font-size: 16px;
            border-bottom: 1px solid rgba(255, 255, 255, 0.2);
        }

        #notes-content {
            padding: 20px;
            max-height: 500px;
            overflow-y: auto;
            background: #f8fafc;
        }

        .generators-section {
            margin-bottom: 20px;
        }

        .section-title {
            font-size: 14px;
            font-weight: 600;
            color: #1976D2;
            margin: 20px 0 10px 0;
            display: flex;
            align-items: center;
            gap: 6px;
        }

        .section-title:first-child {
            margin-top: 0;
        }

        .generator-row {
            display: flex;
            align-items: center;
            justify-content: space-between;
            padding: 12px;
            margin: 8px 0;
            border-radius: 8px;
            background: white;
            border: 1px solid #e0e0e0;
        }

        .generator-label {
            font-weight: 600;
            font-size: 13px;
            min-width: 80px;
        }

        .generator-value {
            font-family: 'SF Mono', Monaco, monospace;
            font-size: 13px;
            flex: 1;
            margin: 0 10px;
            padding: 6px 10px;
            border-radius: 4px;
            cursor: pointer;
            transition: all 0.2s;
            word-break: break-all;
            user-select: all;
            border: 1px solid transparent;
        }

        .generator-value:hover {
            transform: scale(1.02);
            box-shadow: 0 2px 5px rgba(0,0,0,0.1);
        }

        .generator-value.rn {
            background: linear-gradient(135deg, #fff9c4, #fff176);
            color: #5d4037;
            border-color: #ffd54f;
        }

        .generator-value.an {
            background: linear-gradient(135deg, #e1bee7, #ce93d8);
            color: #4a148c;
            border-color: #ba68c8;
        }

        .generator-value.email {
            background: linear-gradient(135deg, #b3e5fc, #81d4fa);
            color: #01579b;
            border-color: #4fc3f7;
        }

        .generator-value.password {
            background: linear-gradient(135deg, #c8e6c9, #a5d6a7);
            color: #1b5e20;
            border-color: #81c784;
        }

        .generator-value.phone {
            background: linear-gradient(135deg, #ffccbc, #ffab91);
            color: #bf360c;
            border-color: #ff8a65;
        }

        .generator-buttons {
            display: flex;
            gap: 5px;
            min-width: 70px;
        }

        .gen-btn {
            padding: 6px 10px;
            border: none;
            border-radius: 4px;
            cursor: pointer;
            font-size: 11px;
            font-weight: 500;
            transition: all 0.2s;
            display: flex;
            align-items: center;
            justify-content: center;
            min-width: 32px;
        }

        .gen-refresh {
            background: #4CAF50;
            color: white;
        }

        .gen-refresh:hover {
            background: #388E3C;
            transform: scale(1.1);
        }

        .gen-copy {
            background: #2196F3;
            color: white;
        }

        .gen-copy:hover {
            background: #1976D2;
            transform: scale(1.1);
        }

        .user-notes-section {
            margin-top: 20px;
        }

        #user-notes-textarea {
            width: 100%;
            min-height: 100px;
            padding: 12px;
            border: 1px solid #bbdefb;
            border-radius: 8px;
            background: white;
            font-family: 'SF Pro Text', -apple-system, sans-serif;
            font-size: 13px;
            line-height: 1.4;
            resize: vertical;
            color: #333;
            box-sizing: border-box;
            margin-bottom: 12px;
        }

        #user-notes-textarea:focus {
            outline: none;
            border-color: #2196F3;
            box-shadow: 0 0 0 2px rgba(33, 150, 243, 0.2);
        }

        .notes-controls {
            display: flex;
            gap: 8px;
            padding: 15px 20px;
            background: #f1f8ff;
            border-top: 1px solid #e3f2fd;
        }

        .notes-btn {
            padding: 10px 12px;
            border: none;
            border-radius: 6px;
            cursor: pointer;
            flex: 1;
            font-weight: 500;
            font-size: 12px;
            transition: all 0.2s ease;
            display: flex;
            align-items: center;
            justify-content: center;
            gap: 5px;
        }

        .notes-refresh-all {
            background: linear-gradient(to right, #FF9800, #F57C00);
            color: white;
        }

        .notes-refresh-all:hover {
            background: linear-gradient(to right, #F57C00, #E65100);
            transform: translateY(-1px);
        }

        .notes-save {
            background: linear-gradient(to right, #4CAF50, #45a049);
            color: white;
        }

        .notes-save:hover {
            background: linear-gradient(to right, #45a049, #388E3C);
            transform: translateY(-1px);
        }

        .notes-close {
            background: linear-gradient(to right, #9E9E9E, #757575);
            color: white;
        }

        .notes-close:hover {
            background: linear-gradient(to right, #757575, #616161);
            transform: translateY(-1px);
        }

        .notes-info {
            font-size: 11px;
            color: #666;
            text-align: center;
            margin-top: 8px;
            padding-top: 8px;
            border-top: 1px dashed #ddd;
        }

        .template-info {
            font-size: 11px;
            color: #666;
            margin-top: 5px;
            font-style: italic;
        }
    `);

    // Создаем кнопку
    function createButton() {
        const button = document.createElement('button');
        button.id = 'smart-notes-btn';
        button.innerHTML = '📝';
        button.title = 'Smart Notes - Генераторы данных';

        button.addEventListener('click', toggleNotesWindow);
        document.body.appendChild(button);
    }

    // Создаем окно заметок
    function createNotesWindow() {
        const windowElement = document.createElement('div');
        windowElement.id = 'smart-notes-window';

        windowElement.innerHTML = `
            <div id="notes-header">
                <span>🚀 Smart Notes</span>
                <span id="notes-minimize" style="cursor:pointer; font-size:20px;">−</span>
            </div>
            <div id="notes-content">
                <div class="section-title">
                    <span>🎯 Генераторы данных</span>
                </div>
                <div class="generators-section">
                    <!-- RN (введен пользователем) -->
                    <div class="generator-row" id="rn-row">
                        <div class="generator-label">RN:</div>
                        <div class="generator-value rn">${userRN}</div>
                        <div class="generator-buttons">
                            <button class="gen-btn gen-copy" title="Копировать">📋</button>
                        </div>
                    </div>
                    <div class="template-info">Шаблон AN: ${userANTemplate}</div>

                    <!-- AN (генерируется по шаблону) -->
                    <div class="generator-row" id="an-row">
                        <div class="generator-label">AN:</div>
                        <div class="generator-value an">${savedData.an}</div>
                        <div class="generator-buttons">
                            <button class="gen-btn gen-refresh" title="Обновить">🔄</button>
                            <button class="gen-btn gen-copy" title="Копировать">📋</button>
                        </div>
                    </div>

                    <!-- Email -->
                    <div class="generator-row" id="email-row">
                        <div class="generator-label">Email:</div>
                        <div class="generator-value email">${savedData.email}</div>
                        <div class="generator-buttons">
                            <button class="gen-btn gen-refresh" title="Обновить">🔄</button>
                            <button class="gen-btn gen-copy" title="Копировать">📋</button>
                        </div>
                    </div>

                    <!-- Password -->
                    <div class="generator-row" id="password-row">
                        <div class="generator-label">Password:</div>
                        <div class="generator-value password">${savedData.password}</div>
                        <div class="generator-buttons">
                            <button class="gen-btn gen-refresh" title="Обновить">🔄</button>
                            <button class="gen-btn gen-copy" title="Копировать">📋</button>
                        </div>
                    </div>

                    <!-- USA Phone -->
                    <div class="generator-row" id="phone-row">
                        <div class="generator-label">USA Phone:</div>
                        <div class="generator-value phone">${savedData.phone}</div>
                        <div class="generator-buttons">
                            <button class="gen-btn gen-refresh" title="Обновить">🔄</button>
                            <button class="gen-btn gen-copy" title="Копировать">📋</button>
                        </div>
                    </div>
                </div>

                <div class="section-title">
                    <span>📝 Мои заметки</span>
                </div>
                <div class="user-notes-section">
                    <textarea id="user-notes-textarea" placeholder="Введите ваши заметки здесь...">${USER_NOTES}</textarea>
                    <div class="notes-info">
                        Сохраняются автоматически при закрытии
                    </div>
                </div>
            </div>
            <div class="notes-controls">
                <button id="refresh-all-btn" class="notes-btn notes-refresh-all" title="Обновить все генераторы">
                    🔄 Все
                </button>
                <button id="save-btn" class="notes-btn notes-save" title="Сохранить заметки">
                    💾 Сохранить
                </button>
                <button id="close-btn" class="notes-btn notes-close" title="Закрыть окно">
                    ✕ Закрыть
                </button>
            </div>
        `;

        document.body.appendChild(windowElement);
        makeDraggable(windowElement);
        setupNotesListeners();
        setupGeneratorListeners();
    }

    // Настройка слушателей для генераторов
    function setupGeneratorListeners() {
        // RN - копирование
        const rnRow = document.getElementById('rn-row');
        const rnCopyBtn = rnRow.querySelector('.gen-copy');
        const rnValueElement = rnRow.querySelector('.generator-value');

        rnValueElement.addEventListener('click', () => copyToClipboard(userRN));
        rnCopyBtn.addEventListener('click', (e) => {
            e.stopPropagation();
            copyToClipboard(userRN);
        });

        // AN
        setupGeneratorRow('an');

        // Email
        setupGeneratorRow('email');

        // Password
        setupGeneratorRow('password');

        // Phone
        setupGeneratorRow('phone');
    }

    // Настройка строки генератора
    function setupGeneratorRow(type) {
        const row = document.getElementById(`${type}-row`);
        const valueElement = row.querySelector('.generator-value');
        const refreshBtn = row.querySelector('.gen-refresh');
        const copyBtn = row.querySelector('.gen-copy');

        // Клик по значению - копирование
        valueElement.addEventListener('click', () => copyToClipboard(savedData[type]));

        // Кнопка обновления
        refreshBtn.addEventListener('click', (e) => {
            e.stopPropagation();
            refreshGenerator(type);
        });

        // Кнопка копирования
        copyBtn.addEventListener('click', (e) => {
            e.stopPropagation();
            copyToClipboard(savedData[type]);
        });
    }

    // Переключение окна
    function toggleNotesWindow() {
        const windowElement = document.getElementById('smart-notes-window');
        const button = document.getElementById('smart-notes-btn');

        if (windowElement.style.display === 'block') {
            windowElement.style.display = 'none';
            button.innerHTML = '📝';
            button.style.background = 'linear-gradient(135deg, #2196F3, #1976D2)';
            saveUserNotes(); // Автосохранение при закрытии
        } else {
            windowElement.style.display = 'block';
            button.innerHTML = '📘';
            button.style.background = 'linear-gradient(135deg, #4CAF50, #45a049)';
        }
    }

    // Настройка обработчиков
    function setupNotesListeners() {
        // Обновить все генераторы
        document.getElementById('refresh-all-btn').addEventListener('click', refreshAllGenerators);

        // Сохранить заметки
        document.getElementById('save-btn').addEventListener('click', saveUserNotes);

        // Закрыть окно
        document.getElementById('close-btn').addEventListener('click', toggleNotesWindow);

        // Сворачивание
        document.getElementById('notes-minimize').addEventListener('click', function(e) {
            e.stopPropagation();
            const content = document.getElementById('notes-content');
            const controls = document.querySelector('.notes-controls');
            const isHidden = content.style.display === 'none';

            content.style.display = isHidden ? 'block' : 'none';
            controls.style.display = isHidden ? 'flex' : 'none';
            this.innerHTML = isHidden ? '−' : '+';
        });
    }

    // Обновить все генераторы
    function refreshAllGenerators() {
        savedData = {
            an: generateANFromTemplate(userANTemplate),
            email: generateRandomEmail(16),
            password: generateRandomPassword(8),
            phone: generateUSAPhoneNumber()
        };

        // Обновляем отображение и слушатели
        const types = ['an', 'email', 'password', 'phone'];
        types.forEach(type => {
            const row = document.getElementById(`${type}-row`);
            const valueElement = row.querySelector('.generator-value');

            valueElement.textContent = savedData[type];

            // Обновляем слушатели
            valueElement.onclick = () => copyToClipboard(savedData[type]);

            const copyBtn = row.querySelector('.gen-copy');
            copyBtn.onclick = (e) => {
                e.stopPropagation();
                copyToClipboard(savedData[type]);
            };
        });

        // Сохраняем
        GM_setValue('smart_notes_data', savedData);

        showNotification('🔄 Все генераторы обновлены!');
    }

    // Сохранить пользовательские заметки
    function saveUserNotes() {
        const textarea = document.getElementById('user-notes-textarea');
        const text = textarea.value;

        GM_setValue('user_smart_notes', text);
        showNotification('💾 Заметки сохранены');
    }

    // Перетаскивание окна
    function makeDraggable(element) {
        const header = document.getElementById('notes-header');
        let isDragging = false;
        let currentX, currentY, initialX, initialY;

        header.addEventListener('mousedown', startDrag);

        function startDrag(e) {
            if (e.target.id === 'notes-minimize') return;

            initialX = e.clientX - element.offsetLeft;
            initialY = e.clientY - element.offsetTop;
            isDragging = true;

            document.addEventListener('mousemove', drag);
            document.addEventListener('mouseup', stopDrag);
            header.style.opacity = '0.9';
        }

        function drag(e) {
            if (isDragging) {
                e.preventDefault();
                currentX = e.clientX - initialX;
                currentY = e.clientY - initialY;

                // Ограничение перемещения
                currentX = Math.max(10, Math.min(currentX, window.innerWidth - element.offsetWidth - 10));
                currentY = Math.max(10, Math.min(currentY, window.innerHeight - element.offsetHeight - 10));

                element.style.left = currentX + 'px';
                element.style.top = currentY + 'px';
                element.style.right = 'auto';
            }
        }

        function stopDrag() {
            isDragging = false;
            document.removeEventListener('mousemove', drag);
            document.removeEventListener('mouseup', stopDrag);
            header.style.opacity = '1';
        }
    }

    // Уведомления
    function showNotification(message) {
        const notification = document.createElement('div');
        notification.textContent = message;

        notification.style.cssText = `
            position: fixed;
            top: 90px;
            right: 20px;
            background: #333;
            color: white;
            padding: 10px 15px;
            border-radius: 6px;
            z-index: 999997;
            font-family: system-ui, -apple-system, sans-serif;
            font-size: 13px;
            box-shadow: 0 3px 10px rgba(0,0,0,0.2);
            animation: slideIn 0.3s ease;
            max-width: 300px;
        `;

        document.body.appendChild(notification);

        setTimeout(() => {
            notification.style.animation = 'slideOut 0.3s ease';
            setTimeout(() => notification.remove(), 300);
        }, 2000);

        // Стили анимации
        if (!document.querySelector('#notes-notification-styles')) {
            const style = document.createElement('style');
            style.id = 'notes-notification-styles';
            style.textContent = `
                @keyframes slideIn {
                    from { transform: translateX(100%); opacity: 0; }
                    to { transform: translateX(0); opacity: 1; }
                }
                @keyframes slideOut {
                    from { transform: translateX(0); opacity: 1; }
                    to { transform: translateX(100%); opacity: 0; }
                }
            `;
            document.head.appendChild(style);
        }
    }

    // Инициализация
    setTimeout(() => {
        createButton();
        createNotesWindow();

        showNotification('🚀 Smart Notes загружен. Нажмите кнопку 📝');
    }, 1000);
})();