У Вас отключён javascript.
В данном режиме, отображение ресурса
браузером не поддерживается

private forum for tests

Объявление

Введите здесь ваше объявление.

Информация о пользователе

Привет, Гость! Войдите или зарегистрируйтесь.


Вы здесь » private forum for tests » Банк » банк


банк

Сообщений 1 страница 7 из 7

1

Итерация банка 1

1

[html]<!DOCTYPE html>
<html lang="ru">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Банк ролевых игр - RUSFF.ME</title>
    <style>
        :root {
            --primary: #4a6fa5;
            --secondary: #6b8cbc;
            --success: #28a745;
            --warning: #ffc107;
            --danger: #dc3545;
            --light: #f8f9fa;
            --dark: #343a40;
        }
       
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
        }
       
        body {
            background: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
            min-height: 100vh;
            padding: 20px;
            color: var(--dark);
        }
       
        .container {
            max-width: 1200px;
            margin: 0 auto;
        }
       
        header {
            background: var(--primary);
            color: white;
            padding: 20px;
            border-radius: 10px 10px 0 0;
            box-shadow: 0 4px 6px rgba(0,0,0,0.1);
        }
       
        h1 {
            font-size: 2.2rem;
            margin-bottom: 10px;
        }
       
        .tagline {
            font-size: 1.1rem;
            opacity: 0.9;
        }
       
        .app-container {
            display: grid;
            grid-template-columns: 1fr 350px;
            gap: 20px;
            margin-top: 20px;
        }
       
        .main-content {
            background: white;
            border-radius: 0 0 10px 10px;
            box-shadow: 0 4px 15px rgba(0,0,0,0.1);
            padding: 25px;
            display: flex;
            flex-direction: column;
            gap: 25px;
        }
       
        .sidebar {
            background: white;
            border-radius: 10px;
            box-shadow: 0 4px 15px rgba(0,0,0,0.1);
            padding: 20px;
            display: flex;
            flex-direction: column;
            gap: 20px;
        }
       
        .card {
            background: var(--light);
            border-radius: 8px;
            padding: 20px;
            box-shadow: 0 2px 5px rgba(0,0,0,0.05);
        }
       
        h2 {
            color: var(--primary);
            margin-bottom: 15px;
            font-size: 1.5rem;
            border-bottom: 2px solid var(--secondary);
            padding-bottom: 8px;
        }
       
        h3 {
            color: var(--secondary);
            margin-bottom: 12px;
            font-size: 1.2rem;
        }
       
        .form-group {
            margin-bottom: 15px;
        }
       
        label {
            display: block;
            margin-bottom: 5px;
            font-weight: 600;
        }
       
        input, select, button {
            width: 100%;
            padding: 12px;
            border: 1px solid #ddd;
            border-radius: 5px;
            font-size: 1rem;
        }
       
        button {
            background: var(--primary);
            color: white;
            border: none;
            cursor: pointer;
            font-weight: 600;
            transition: all 0.3s;
            margin-top: 10px;
        }
       
        button:hover {
            background: var(--secondary);
            transform: translateY(-2px);
        }
       
        button.secondary {
            background: var(--secondary);
        }
       
        button.success {
            background: var(--success);
        }
       
        button.warning {
            background: var(--warning);
            color: var(--dark);
        }
       
        button.danger {
            background: var(--danger);
        }
       
        .rates-grid {
            display: grid;
            grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
            gap: 10px;
            margin-top: 10px;
        }
       
        .rate-card {
            background: white;
            border: 1px solid #ddd;
            border-radius: 5px;
            padding: 10px;
            text-align: center;
        }
       
        .rate-type {
            font-weight: 600;
            color: var(--primary);
        }
       
        .rate-value {
            font-size: 1.2rem;
            font-weight: 700;
            color: var(--success);
        }
       
        .posts-container {
            margin-top: 15px;
        }
       
        .post-entry {
            display: flex;
            gap: 10px;
            margin-bottom: 10px;
            align-items: center;
        }
       
        .post-number {
            font-weight: 600;
            min-width: 30px;
        }
       
        .post-type {
            flex: 1;
        }
       
        .results {
            background: white;
            border-radius: 10px;
            padding: 20px;
            margin-top: 20px;
            box-shadow: 0 4px 15px rgba(0,0,0,0.1);
            display: none;
        }
       
        .results.active {
            display: block;
            animation: fadeIn 0.5s;
        }
       
        @keyframes fadeIn {
            from { opacity: 0; transform: translateY(10px); }
            to { opacity: 1; transform: translateY(0); }
        }
       
        .result-row {
            display: flex;
            justify-content: space-between;
            padding: 10px 0;
            border-bottom: 1px solid #eee;
        }
       
        .result-row:last-child {
            border-bottom: none;
            font-weight: 700;
            font-size: 1.1rem;
            color: var(--primary);
        }
       
        .player-stats {
            margin-top: 15px;
        }
       
        .stat-item {
            display: flex;
            justify-content: space-between;
            margin-bottom: 8px;
            padding-bottom: 8px;
            border-bottom: 1px dashed #ddd;
        }
       
        .status-indicator {
            display: inline-block;
            width: 10px;
            height: 10px;
            border-radius: 50%;
            margin-right: 8px;
        }
       
        .status-active {
            background: var(--success);
        }
       
        .status-inactive {
            background: var(--danger);
        }
       
        .notification {
            padding: 12px;
            border-radius: 5px;
            margin-bottom: 15px;
            display: none;
        }
       
        .notification.success {
            background: #d4edda;
            color: #155724;
            border: 1px solid #c3e6cb;
            display: block;
        }
       
        .notification.error {
            background: #f8d7da;
            color: #721c24;
            border: 1px solid #f5c6cb;
            display: block;
        }
       
        .notification.warning {
            background: #fff3cd;
            color: #856404;
            border: 1px solid #ffeaa7;
            display: block;
        }
       
        .tabs {
            display: flex;
            margin-bottom: 20px;
            border-bottom: 1px solid #ddd;
        }
       
        .tab {
            padding: 10px 20px;
            cursor: pointer;
            border-bottom: 3px solid transparent;
        }
       
        .tab.active {
            border-bottom: 3px solid var(--primary);
            font-weight: 600;
            color: var(--primary);
        }
       
        .tab-content {
            display: none;
        }
       
        .tab-content.active {
            display: block;
        }
       
        @media (max-width: 768px) {
            .app-container {
                grid-template-columns: 1fr;
            }
           
            .rates-grid {
                grid-template-columns: repeat(2, 1fr);
            }
        }
    </style>
</head>
<body>
    <div class="container">
        <header>
            <h1>🏦 Банк ролевых игр - RUSFF.ME</h1>
            <p class="tagline">Автоматический учет денег за посты с проверкой заполнения банка</p>
        </header>
       
        <div class="app-container">
            <div class="main-content">
                <div class="tabs">
                    <div class="tab active" data-tab="auto">Автоматический режим</div>
                    <div class="tab" data-tab="manual">Ручной ввод</div>
                    <div class="tab" data-tab="stats">Статистика</div>
                </div>
               
                <div class="tab-content active" id="auto-tab">
                    <div class="card">
                        <h2>Автоматическое пополнение счета</h2>
                        <div class="notification warning" id="auto-notification">
                            ⚠️ Автоматическая проверка rusff.me временно недоступна. Используйте ручной ввод.
                        </div>
                       
                        <div class="form-group">
                            <label for="player-name">Имя игрока:</label>
                            <input type="text" id="player-name" placeholder="Введите имя персонажа">
                        </div>
                       
                        <div class="form-group">
                            <label for="posts-count">Количество постов для проверки:</label>
                            <input type="number" id="posts-count" min="1" max="50" value="5">
                        </div>
                       
                        <button id="check-bank-btn" class="success">🔍 Проверить заполнение банка</button>
                    </div>
                   
                    <div class="card" id="posts-section" style="display: none;">
                        <h2>Типы постов</h2>
                        <p>Укажите тип для каждого поста:</p>
                       
                        <div class="rates-grid">
                            <div class="rate-card">
                                <div class="rate-type">Обычный</div>
                                <div class="rate-value">10 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Развитие</div>
                                <div class="rate-value">15 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Админский</div>
                                <div class="rate-value">20 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Массовый</div>
                                <div class="rate-value">12 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Отыгровка</div>
                                <div class="rate-value">8 монет</div>
                            </div>
                        </div>
                       
                        <div class="posts-container" id="posts-container">
                            <!-- Посты будут добавлены здесь динамически -->
                        </div>
                       
                        <button id="calculate-btn" class="success">💰 Рассчитать заработок</button>
                    </div>
                </div>
               
                <div class="tab-content" id="manual-tab">
                    <div class="card">
                        <h2>Ручной ввод данных</h2>
                       
                        <div class="form-group">
                            <label for="manual-player-name">Имя игрока:</label>
                            <input type="text" id="manual-player-name" placeholder="Введите имя персонажа">
                        </div>
                       
                        <div class="form-group">
                            <label for="current-balance">Текущий баланс:</label>
                            <input type="number" id="current-balance" min="0" value="0">
                        </div>
                       
                        <div class="form-group">
                            <label for="manual-posts-count">Количество постов:</label>
                            <input type="number" id="manual-posts-count" min="1" max="50" value="1">
                        </div>
                       
                        <button id="generate-posts-btn" class="secondary">📝 Создать форму для постов</button>
                    </div>
                   
                    <div class="card" id="manual-posts-section" style="display: none;">
                        <h2>Типы постов</h2>
                        <p>Укажите тип для каждого поста:</p>
                       
                        <div class="posts-container" id="manual-posts-container">
                            <!-- Посты будут добавлены здесь динамически -->
                        </div>
                       
                        <button id="manual-calculate-btn" class="success">💰 Рассчитать заработок</button>
                    </div>
                </div>
               
                <div class="tab-content" id="stats-tab">
                    <div class="card">
                        <h2>Статистика игроков</h2>
                       
                        <div class="form-group">
                            <label for="search-player">Поиск игрока:</label>
                            <input type="text" id="search-player" placeholder="Введите имя для поиска">
                        </div>
                       
                        <button id="search-btn" class="secondary">🔍 Найти игрока</button>
                       
                        <div class="player-stats" id="player-stats">
                            <!-- Статистика будет отображена здесь -->
                        </div>
                    </div>
                   
                    <div class="card">
                        <h2>Тарифы по типам постов</h2>
                        <div class="rates-grid">
                            <div class="rate-card">
                                <div class="rate-type">Обычный</div>
                                <div class="rate-value">10 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Развитие</div>
                                <div class="rate-value">15 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Админский</div>
                                <div class="rate-value">20 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Массовый</div>
                                <div class="rate-value">12 монет</div>
                            </div>
                            <div class="rate-card">
                                <div class="rate-type">Отыгровка</div>
                                <div class="rate-value">8 монет</div>
                            </div>
                        </div>
                    </div>
                </div>
               
                <div class="results" id="results">
                    <h2>Результаты операции</h2>
                    <div class="result-row">
                        <span>Игрок:</span>
                        <span id="result-player">-</span>
                    </div>
                    <div class="result-row">
                        <span>Дата операции:</span>
                        <span id="result-date">-</span>
                    </div>
                    <div class="result-row">
                        <span>Количество постов:</span>
                        <span id="result-posts">-</span>
                    </div>
                    <div class="result-row">
                        <span>Начислено:</span>
                        <span id="result-earned">-</span>
                    </div>
                    <div class="result-row">
                        <span>Предыдущий баланс:</span>
                        <span id="result-old-balance">-</span>
                    </div>
                    <div class="result-row">
                        <span>Новый баланс:</span>
                        <span id="result-new-balance">-</span>
                    </div>
                </div>
            </div>
           
            <div class="sidebar">
                <div class="card">
                    <h2>Активные игроки</h2>
                    <div id="active-players">
                        <!-- Список активных игроков будет здесь -->
                    </div>
                </div>
               
                <div class="card">
                    <h2>Последние операции</h2>
                    <div id="recent-transactions">
                        <!-- Последние транзакции будут здесь -->
                    </div>
                </div>
               
                <div class="card">
                    <h2>Быстрые действия</h2>
                    <button id="reset-data-btn" class="warning">🔄 Сбросить все данные</button>
                    <button id="export-data-btn" class="secondary">📤 Экспорт данных</button>
                    <button id="import-data-btn" class="secondary">📥 Импорт данных</button>
                </div>
            </div>
        </div>
    </div>

    <script>
        // Тарифы за посты
        const rates = {
            "обычный": 10,
            "развитие": 15,
            "админский": 20,
            "массовый": 12,
            "отыгровка": 8
        };

        // Данные игроков
        let players = JSON.parse(localStorage.getItem('roleplayPlayers')) || {};
       
        // Инициализация при загрузке страницы
        document.addEventListener('DOMContentLoaded', function() {
            initializeTabs();
            updateActivePlayers();
            updateRecentTransactions();
           
            // Обработчики для автоматического режима
            document.getElementById('check-bank-btn').addEventListener('click', checkBankFill);
            document.getElementById('calculate-btn').addEventListener('click', calculateEarnings);
           
            // Обработчики для ручного режима
            document.getElementById('generate-posts-btn').addEventListener('click', generateManualPosts);
            document.getElementById('manual-calculate-btn').addEventListener('click', calculateManualEarnings);
           
            // Обработчики для статистики
            document.getElementById('search-btn').addEventListener('click', searchPlayer);
           
            // Обработчики быстрых действий
            document.getElementById('reset-data-btn').addEventListener('click', resetData);
            document.getElementById('export-data-btn').addEventListener('click', exportData);
            document.getElementById('import-data-btn').addEventListener('click', importData);
        });
       
        // Инициализация вкладок
        function initializeTabs() {
            const tabs = document.querySelectorAll('.tab');
            tabs.forEach(tab => {
                tab.addEventListener('click', function() {
                    // Убираем активный класс со всех вкладок и контента
                    tabs.forEach(t => t.classList.remove('active'));
                    document.querySelectorAll('.tab-content').forEach(c => c.classList.remove('active'));
                   
                    // Добавляем активный класс к выбранной вкладке
                    this.classList.add('active');
                    const tabId = this.getAttribute('data-tab');
                    document.getElementById(`${tabId}-tab`).classList.add('active');
                });
            });
        }
       
        // Проверка заполнения банка (имитация)
        function checkBankFill() {
            const playerName = document.getElementById('player-name').value.trim();
            const postsCount = parseInt(document.getElementById('posts-count').value);
           
            if (!playerName) {
                showNotification('Введите имя игрока', 'error');
                return;
            }
           
            if (isNaN(postsCount) || postsCount < 1) {
                showNotification('Введите корректное количество постов', 'error');
                return;
            }
           
            // Имитация проверки банка
            showNotification('🔍 Проверяем заполнение банка на RUSFF.ME...', 'warning');
           
            setTimeout(() => {
                // В реальном приложении здесь был бы запрос к API или парсинг страницы
                showNotification('✅ Банк заполнен корректно! Можно вводить посты.', 'success');
               
                // Показываем секцию с постами
                document.getElementById('posts-section').style.display = 'block';
               
                // Генерируем поля для ввода постов
                generatePostInputs(postsCount, 'posts-container');
            }, 1500);
        }
       
        // Генерация полей для ввода постов
        function generatePostInputs(count, containerId) {
            const container = document.getElementById(containerId);
            container.innerHTML = '';
           
            for (let i = 1; i <= count; i++) {
                const postEntry = document.createElement('div');
                postEntry.className = 'post-entry';
               
                postEntry.innerHTML = `
                    <div class="post-number">${i}.</div>
                    <select class="post-type" name="post-type-${i}">
                        <option value="">Выберите тип поста</option>
                        ${Object.keys(rates).map(type =>
                            `<option value="${type}">${type} (${rates[type]} монет)</option>`
                        ).join('')}
                    </select>
                `;
               
                container.appendChild(postEntry);
            }
        }
       
        // Расчет заработка в автоматическом режиме
        function calculateEarnings() {
            const playerName = document.getElementById('player-name').value.trim();
            const postSelects = document.querySelectorAll('#posts-container .post-type');
           
            if (!playerName) {
                showNotification('Введите имя игрока', 'error');
                return;
            }
           
            // Проверяем, что все посты имеют выбранный тип
            let allSelected = true;
            let totalEarned = 0;
           
            postSelects.forEach((select, index) => {
                if (!select.value) {
                    allSelected = false;
                    select.style.borderColor = 'var(--danger)';
                } else {
                    select.style.borderColor = '';
                    totalEarned += rates[select.value];
                }
            });
           
            if (!allSelected) {
                showNotification('Выберите тип для всех постов', 'error');
                return;
            }
           
            // Получаем или создаем данные игрока
            if (!players[playerName]) {
                players[playerName] = {
                    balance: 0,
                    totalEarned: 0,
                    transactions: [],
                    lastUpdate: new Date().toISOString()
                };
            }
           
            const oldBalance = players[playerName].balance;
            const newBalance = oldBalance + totalEarned;
           
            // Обновляем данные игрока
            players[playerName].balance = newBalance;
            players[playerName].totalEarned += totalEarned;
            players[playerName].lastUpdate = new Date().toISOString();
           
            // Добавляем транзакцию
            players[playerName].transactions.push({
                date: new Date().toISOString(),
                posts: Array.from(postSelects).map(select => select.value),
                earned: totalEarned,
                oldBalance: oldBalance,
                newBalance: newBalance
            });
           
            // Сохраняем данные
            localStorage.setItem('roleplayPlayers', JSON.stringify(players));
           
            // Показываем результаты
            showResults(playerName, postSelects.length, totalEarned, oldBalance, newBalance);
           
            // Обновляем боковые панели
            updateActivePlayers();
            updateRecentTransactions();
           
            showNotification('✅ Баланс успешно обновлен!', 'success');
        }
       
        // Генерация постов для ручного режима
        function generateManualPosts() {
            const playerName = document.getElementById('manual-player-name').value.trim();
            const postsCount = parseInt(document.getElementById('manual-posts-count').value);
           
            if (!playerName) {
                showNotification('Введите имя игрока', 'error');
                return;
            }
           
            if (isNaN(postsCount) || postsCount < 1) {
                showNotification('Введите корректное количество постов', 'error');
                return;
            }
           
            // Показываем секцию с постами
            document.getElementById('manual-posts-section').style.display = 'block';
           
            // Генерируем поля для ввода постов
            generatePostInputs(postsCount, 'manual-posts-container');
        }
       
        // Расчет заработка в ручном режиме
        function calculateManualEarnings() {
            const playerName = document.getElementById('manual-player-name').value.trim();
            const currentBalance = parseFloat(document.getElementById('current-balance').value) || 0;
            const postSelects = document.querySelectorAll('#manual-posts-container .post-type');
           
            if (!playerName) {
                showNotification('Введите имя игрока', 'error');
                return;
            }
           
            // Проверяем, что все посты имеют выбранный тип
            let allSelected = true;
            let totalEarned = 0;
           
            postSelects.forEach((select, index) => {
                if (!select.value) {
                    allSelected = false;
                    select.style.borderColor = 'var(--danger)';
                } else {
                    select.style.borderColor = '';
                    totalEarned += rates[select.value];
                }
            });
           
            if (!allSelected) {
                showNotification('Выберите тип для всех постов', 'error');
                return;
            }
           
            // Получаем или создаем данные игрока
            if (!players[playerName]) {
                players[playerName] = {
                    balance: currentBalance,
                    totalEarned: 0,
                    transactions: [],
                    lastUpdate: new Date().toISOString()
                };
            }
           
            const oldBalance = players[playerName].balance;
            const newBalance = oldBalance + totalEarned;
           
            // Обновляем данные игрока
            players[playerName].balance = newBalance;
            players[playerName].totalEarned += totalEarned;
            players[playerName].lastUpdate = new Date().toISOString();
           
            // Добавляем транзакцию
            players[playerName].transactions.push({
                date: new Date().toISOString(),
                posts: Array.from(postSelects).map(select => select.value),
                earned: totalEarned,
                oldBalance: oldBalance,
                newBalance: newBalance
            });
           
            // Сохраняем данные
            localStorage.setItem('roleplayPlayers', JSON.stringify(players));
           
            // Показываем результаты
            showResults(playerName, postSelects.length, totalEarned, oldBalance, newBalance);
           
            // Обновляем боковые панели
            updateActivePlayers();
            updateRecentTransactions();
           
            showNotification('✅ Баланс успешно обновлен!', 'success');
        }
       
        // Поиск игрока в статистике
        function searchPlayer() {
            const searchName = document.getElementById('search-player').value.trim().toLowerCase();
            const statsContainer = document.getElementById('player-stats');
           
            if (!searchName) {
                statsContainer.innerHTML = '<p>Введите имя игрока для поиска</p>';
                return;
            }
           
            // Ищем игрока
            const playerKeys = Object.keys(players).filter(key =>
                key.toLowerCase().includes(searchName)
            );
           
            if (playerKeys.length === 0) {
                statsContainer.innerHTML = '<p>Игрок не найден</p>';
                return;
            }
           
            let statsHTML = '';
           
            playerKeys.forEach(playerName => {
                const player = players[playerName];
                const lastUpdate = new Date(player.lastUpdate).toLocaleString('ru-RU');
               
                statsHTML += `
                    <div class="card" style="margin-top: 15px;">
                        <h3>${playerName}</h3>
                        <div class="stat-item">
                            <span>Текущий баланс:</span>
                            <span>${player.balance} монет</span>
                        </div>
                        <div class="stat-item">
                            <span>Всего заработано:</span>
                            <span>${player.totalEarned} монет</span>
                        </div>
                        <div class="stat-item">
                            <span>Последнее обновление:</span>
                            <span>${lastUpdate}</span>
                        </div>
                        <div class="stat-item">
                            <span>Количество транзакций:</span>
                            <span>${player.transactions ? player.transactions.length : 0}</span>
                        </div>
                    </div>
                `;
            });
           
            statsContainer.innerHTML = statsHTML;
        }
       
        // Показать результаты операции
        function showResults(playerName, postsCount, earned, oldBalance, newBalance) {
            const results = document.getElementById('results');
            const now = new Date();
           
            document.getElementById('result-player').textContent = playerName;
            document.getElementById('result-date').textContent = now.toLocaleString('ru-RU');
            document.getElementById('result-posts').textContent = postsCount;
            document.getElementById('result-earned').textContent = `${earned} монет`;
            document.getElementById('result-old-balance').textContent = `${oldBalance} монет`;
            document.getElementById('result-new-balance').textContent = `${newBalance} монет`;
           
            results.classList.add('active');
        }
       
        // Обновление списка активных игроков
        function updateActivePlayers() {
            const container = document.getElementById('active-players');
            const playerKeys = Object.keys(players);
           
            if (playerKeys.length === 0) {
                container.innerHTML = '<p>Нет данных об игроках</p>';
                return;
            }
           
            // Сортируем по дате последнего обновления (новые сверху)
            playerKeys.sort((a, b) =>
                new Date(players[b].lastUpdate) - new Date(players[a].lastUpdate)
            );
           
            let playersHTML = '';
           
            playerKeys.slice(0, 5).forEach(playerName => {
                const player = players[playerName];
                const lastUpdate = new Date(player.lastUpdate);
                const now = new Date();
                const daysDiff = Math.floor((now - lastUpdate) / (1000 * 60 * 60 * 24));
                const isActive = daysDiff < 7; // Активен, если обновлялся менее недели назад
               
                playersHTML += `
                    <div class="stat-item">
                        <span>
                            <span class="status-indicator ${isActive ? 'status-active' : 'status-inactive'}"></span>
                            ${playerName}
                        </span>
                        <span>${player.balance} монет</span>
                    </div>
                `;
            });
           
            container.innerHTML = playersHTML;
        }
       
        // Обновление последних транзакций
        function updateRecentTransactions() {
            const container = document.getElementById('recent-transactions');
           
            // Собираем все транзакции из всех игроков
            let allTransactions = [];
           
            Object.keys(players).forEach(playerName => {
                if (players[playerName].transactions) {
                    players[playerName].transactions.forEach(transaction => {
                        allTransactions.push({
                            player: playerName,
                            ...transaction
                        });
                    });
                }
            });
           
            // Сортируем по дате (новые сверху)
            allTransactions.sort((a, b) => new Date(b.date) - new Date(a.date));
           
            if (allTransactions.length === 0) {
                container.innerHTML = '<p>Нет транзакций</p>';
                return;
            }
           
            let transactionsHTML = '';
           
            allTransactions.slice(0, 5).forEach(transaction => {
                const date = new Date(transaction.date).toLocaleDateString('ru-RU');
               
                transactionsHTML += `
                    <div class="stat-item">
                        <span>${transaction.player}</span>
                        <span>+${transaction.earned}</span>
                    </div>
                    <div style="font-size: 0.8rem; color: #666; margin-bottom: 8px;">
                        ${date}
                    </div>
                `;
            });
           
            container.innerHTML = transactionsHTML;
        }
       
        // Сброс всех данных
        function resetData() {
            if (confirm('Вы уверены, что хотите удалить все данные? Это действие нельзя отменить.')) {
                players = {};
                localStorage.removeItem('roleplayPlayers');
                updateActivePlayers();
                updateRecentTransactions();
                showNotification('Все данные были удалены', 'warning');
            }
        }
       
        // Экспорт данных
        function exportData() {
            const dataStr = JSON.stringify(players, null, 2);
            const dataBlob = new Blob([dataStr], {type: 'application/json'});
           
            const url = URL.createObjectURL(dataBlob);
            const link = document.createElement('a');
            link.href = url;
            link.download = 'roleplay_bank_data.json';
            document.body.appendChild(link);
            link.click();
            document.body.removeChild(link);
            URL.revokeObjectURL(url);
           
            showNotification('Данные успешно экспортированы', 'success');
        }
       
        // Импорт данных
        function importData() {
            const input = document.createElement('input');
            input.type = 'file';
            input.accept = 'application/json';
           
            input.onchange = e => {
                const file = e.target.files[0];
                const reader = new FileReader();
               
                reader.onload = function(event) {
                    try {
                        const importedData = JSON.parse(event.target.result);
                        players = importedData;
                        localStorage.setItem('roleplayPlayers', JSON.stringify(players));
                        updateActivePlayers();
                        updateRecentTransactions();
                        showNotification('Данные успешно импортированы', 'success');
                    } catch (error) {
                        showNotification('Ошибка при импорте данных: неверный формат файла', 'error');
                    }
                };
               
                reader.readAsText(file);
            };
           
            input.click();
        }
       
        // Показать уведомление
        function showNotification(message, type) {
            // Создаем уведомление, если его нет
            let notification = document.querySelector('.notification');
            if (!notification) {
                notification = document.createElement('div');
                notification.className = 'notification';
                document.querySelector('.main-content').prepend(notification);
            }
           
            notification.textContent = message;
            notification.className = `notification ${type}`;
           
            // Автоматически скрываем через 5 секунд
            setTimeout(() => {
                notification.style.display = 'none';
            }, 5000);
        }
    </script>
</body>
</html>[/html]

0

2

Итерация банка 2

2

[html]<!-- Код для автоматического подсчета банка ролевой игры -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль (опционально):</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="fearPercent" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий процент страха:</label>
    <input type="number" id="fearPercent" name="fearPercent" min="0" max="100" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="messagesText" style="display: block; font-weight: bold; margin-bottom: 5px;">Текст ваших сообщений для анализа:</label>
    <textarea id="messagesText" name="messagesText" rows="5" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Вставьте текст ваших сообщений за период..."></textarea>
  </div>
 
  <button type="button" onclick="calculateBank()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Рассчитать награду</button>
</form>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
  <!-- Результаты расчета появятся здесь -->
</div>
</div>

<script>
// Позиции банка с процентами
const bankItems = {
  "biography": { name: "Написать анкету с биографией", percent: 10 },
  "action": { name: "Написать акцию", percent: 15 },
  "invite_by_action": { name: "За пришедшего по акции на 'нужного'", percent: 15 },
  "come_by_needed": { name: "Прийти по 'нужному'", percent: 15 },
  "take_from_want": { name: "Забрать игрока из 'хочу к вам'", percent: 15 },
  "ad_50": { name: "Реклама 50 шт.", percent: 20 },
  "messages_100": { name: "100 сообщений", percent: 10 },
  "positivity_500": { name: "500 позитива", percent: 10 },
  "reputation_500": { name: "500 репутации (+/-)", percent: 10 },
  "post_less_5k": { name: "Написать пост меньше 5к", percent: 5 },
  "post_more_5k": { name: "Написать пост больше 5к", percent: 10 },
  "post_in_active": { name: "Попал в таблицу актива", percent: 10 },
  "graphics": { name: "Графика для игрока", percent: 10 },
  "contest_offer": { name: "Предложить и оформить конкурс", percent: 15 },
  "contest_conduct": { name: "Провести конкурс", percent: 40 },
  "leaflet": { name: "Сделать листовку", percent: 15 }
};

// Ключевые слова для автоматического определения активности
const activityKeywords = {
  "biography": ["анкет", "биографи", "персонаж", "заявк"],
  "action": ["акци", "ивент", "мероприят"],
  "invite_by_action": ["пригласил", "привел", "по акции"],
  "come_by_needed": ["нужн", "требуетс", "необходим"],
  "take_from_want": ["хочу к вам", "забрал", "принял"],
  "ad_50": ["реклам", "объявлен", "анонс"],
  "messages_100": ["сообщен", "писем", "переписк"],
  "positivity_500": ["позитив", "одобрен", "лайк", "нравитс"],
  "reputation_500": ["репутац", "рейтинг", "слав"],
  "post_less_5k": ["пост", "сообщен", "запис"],
  "post_more_5k": ["пост", "сообщен", "запис"],
  "post_in_active": ["таблиц", "актив", "топ"],
  "graphics": ["график", "рисун", "изображен", "арт"],
  "contest_offer": ["конкурс", "соревнован", "розыгрыш"],
  "contest_conduct": ["провел", "организовал", "устроил"],
  "leaflet": ["листовк", "флаер", "объявлен"]
};

// Основная функция расчета
function calculateBank() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const fearPercent = parseInt(document.getElementById('fearPercent').value) || 0;
  const messagesText = document.getElementById('messagesText').value;
 
  // Проверка обязательных полей
  if (!playerName) {
    alert("Пожалуйста, введите имя игрока");
    return;
  }
 
  if (!lastVisit) {
    alert("Пожалуйста, укажите дату последнего захода в банк");
    return;
  }
 
  // Сбрасываем счетчики
  const counts = {};
  Object.keys(bankItems).forEach(key => {
    counts[key] = 0;
  });
 
  // Анализируем сообщения, если они предоставлены
  if (messagesText) {
    const messages = messagesText.split('\n').filter(msg => msg.trim().length > 0);
   
    messages.forEach(message => {
      for (const [key, keywords] of Object.entries(activityKeywords)) {
        for (const keyword of keywords) {
          if (message.toLowerCase().includes(keyword)) {
            counts[key]++;
            break; // Прерываем внутренний цикл, чтобы не считать одно сообщение несколько раз
          }
        }
      }
    });
  }
 
  // Базовый расчет
  const baseAmount = 100; // Базовая сумма для расчета
  let totalActivity = 0;
  let activityDetails = [];
 
  Object.keys(bankItems).forEach(key => {
    if (counts[key] > 0) {
      const itemValue = baseAmount * (bankItems[key].percent / 100) * counts[key];
      totalActivity += itemValue;
      activityDetails.push(`${bankItems[key].name}: ${counts[key]} × ${bankItems[key].percent}% = ${itemValue.toFixed(0)} монет`);
    }
  });
 
  // Учитываем процент страха (чем выше страх, тем меньше награда)
  const fearMultiplier = 1 - (fearPercent / 200); // Максимальный штраф 50% при 100% страха
  const fearBonus = totalActivity * (fearMultiplier - 1);
  const totalWithFear = totalActivity * fearMultiplier;
 
  // Форматируем дату
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  // Показываем результаты
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Дата расчета:</strong></div>
      <div>${now.toLocaleString('ru-RU')}</div>
     
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
     
      <div><strong>Процент страха:</strong></div>
      <div>${fearPercent}%</div>
     
      <div><strong>Начислено за активность:</strong></div>
      <div>${totalActivity.toFixed(0)} монет</div>
     
      <div><strong>Бонус/штраф за страх:</strong></div>
      <div>${fearBonus.toFixed(0)} монет</div>
     
      <div style="font-weight: bold; color: #4a6fa5;">Итого к начислению:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${totalWithFear.toFixed(0)} монет</div>
    </div>
   
    ${activityDetails.length > 0 ? `
    <details style="margin-top: 10px;">
      <summary style="cursor: pointer; font-weight: bold;">Детали расчета</summary>
      <ul style="margin-top: 5px;">
        ${activityDetails.map(detail => `<li>${detail}</li>`).join('')}
      </ul>
    </details>
    ` : ''}
   
    <div style="margin-top: 10px; padding: 8px; background: #e7f3ff; border-radius: 3px;">
      <strong>Скопируйте этот текст для оформления заявки:</strong><br>
      <textarea rows="3" style="width: 100%; margin-top: 5px; font-family: monospace;" readonly>Игрок: ${playerName}
Период: ${period}
Начислено: ${totalWithFear.toFixed(0)} монет
Процент страха: ${fearPercent}%</textarea>
    </div>
  `;
 
  resultDiv.style.display = 'block';
}

// Устанавливаем сегодняшнюю дату как значение по умолчанию для последнего захода
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
});
</script>[/html]

0

3

Итерация банка 3

3

[html]<!-- Код для автоматического подсчета банка ролевой игры -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль (опционально):</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="fearPercent" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий процент страха:</label>
    <input type="number" id="fearPercent" name="fearPercent" min="0" max="100" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="userPostsUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на ваши сообщения:</label>
    <input type="text" id="userPostsUrl" name="userPostsUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://nameforum.rusff.me/search.php?action=show_user_posts&user_id=N">
    <small style="color: #666;">Замените nameforum на название форума, а N на ваш ID</small>
  </div>
 
  <button type="button" onclick="parseAndCalculate()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Загрузить и рассчитать</button>
</form>

<div id="loading" style="display: none; text-align: center; padding: 10px;">
  <p>Загрузка и анализ сообщений...</p>
</div>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
  <!-- Результаты расчета появятся здесь -->
</div>
</div>

<script>
// Основная функция для парсинга и расчета
async function parseAndCalculate() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const fearPercent = parseInt(document.getElementById('fearPercent').value) || 0;
  const userPostsUrl = document.getElementById('userPostsUrl').value.trim();
 
  // Проверка обязательных полей
  if (!playerName) {
    alert("Пожалуйста, введите имя игрока");
    return;
  }
 
  if (!lastVisit) {
    alert("Пожалуйста, укажите дату последнего захода в банк");
    return;
  }
 
  if (!userPostsUrl) {
    alert("Пожалуйста, укажите ссылку на ваши сообщения");
    return;
  }
 
  // Показываем индикатор загрузки
  document.getElementById('loading').style.display = 'block';
  document.getElementById('bankResult').style.display = 'none';
 
  try {
    // Парсим сообщения пользователя
    const messages = await parseUserMessages(userPostsUrl, lastVisit);
   
    // Рассчитываем награду
    calculateReward(playerName, lastVisit, fearPercent, messages);
   
  } catch (error) {
    console.error("Ошибка при парсинге:", error);
    alert("Произошла ошибка при загрузке сообщений. Проверьте ссылку и попробуйте снова.");
  } finally {
    // Скрываем индикатор загрузки
    document.getElementById('loading').style.display = 'none';
  }
}

// Функция для парсинга сообщений пользователя
async function parseUserMessages(url, lastVisitDate) {
  // В реальной реализации здесь будет код для парсинга страницы с сообщениями
  // Но из-за CORS ограничений в браузере, мы можем только имитировать этот процесс
 
  // Имитация запроса и парсинга
  return new Promise((resolve) => {
    setTimeout(() => {
      // В реальности здесь будет парсинг HTML страницы с сообщениями
      // и извлечение только тех сообщений, которые были после lastVisitDate
     
      // Имитируем получение сообщений
      const mockMessages = [
        "Привет всем! Как ваши дела?",
        "Я написал новую анкету для своего персонажа",
        "Участвую в акции этого месяца",
        "Написал большой пост с развитием сюжета",
        "Обсуждаю последние события в игре",
        "Помогаю новичкам разобраться с правилами",
        "Участвую в конкурсе от администрации",
        "Делюсь своими мыслями по поводу обновления",
        "Отвечаю на вопросы других игроков",
        "Предлагаю идеи для улучшения игры"
      ];
     
      resolve(mockMessages);
    }, 1500);
  });
}

// Функция расчета награды
function calculateReward(playerName, lastVisit, fearPercent, messages) {
  // Базовый расчет: 2 монеты за каждое сообщение
  const coinsPerMessage = 2;
  const messageCount = messages.length;
  const baseReward = messageCount * coinsPerMessage;
 
  // Учитываем процент страха (чем выше страх, тем меньше награда)
  const fearMultiplier = 1 - (fearPercent / 200); // Максимальный штраф 50% при 100% страха
  const fearBonus = baseReward * (fearMultiplier - 1);
  const totalReward = baseReward * fearMultiplier;
 
  // Форматируем дату
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  // Показываем результаты
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Дата расчета:</strong></div>
      <div>${now.toLocaleString('ru-RU')}</div>
     
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
     
      <div><strong>Процент страха:</strong></div>
      <div>${fearPercent}%</div>
     
      <div><strong>Количество сообщений:</strong></div>
      <div>${messageCount}</div>
     
      <div><strong>Начислено за сообщения:</strong></div>
      <div>${baseReward} монет (${messageCount} × ${coinsPerMessage})</div>
     
      <div><strong>Бонус/штраф за страх:</strong></div>
      <div>${fearBonus.toFixed(0)} монет</div>
     
      <div style="font-weight: bold; color: #4a6fa5;">Итого к начислению:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${totalReward.toFixed(0)} монет</div>
    </div>
   
    <details style="margin-top: 10px;">
      <summary style="cursor: pointer; font-weight: bold;">Просмотр сообщений (${messageCount})</summary>
      <div style="margin-top: 5px; max-height: 200px; overflow-y: auto; border: 1px solid #eee; padding: 5px;">
        ${messages.map((msg, index) => `
          <div style="padding: 5px; border-bottom: 1px solid #f0f0f0; font-size: 0.9em;">
            <strong>${index + 1}.</strong> ${msg}
          </div>
        `).join('')}
      </div>
    </details>
   
    <div style="margin-top: 10px; padding: 8px; background: #e7f3ff; border-radius: 3px;">
      <strong>Скопируйте этот текст для оформления заявки:</strong><br>
      <textarea rows="4" style="width: 100%; margin-top: 5px; font-family: monospace;" readonly>Игрок: ${playerName}
Период: ${period}
Сообщений: ${messageCount}
Начислено: ${totalReward.toFixed(0)} монет
Процент страха: ${fearPercent}%</textarea>
    </div>
  `;
 
  resultDiv.style.display = 'block';
}

// Устанавливаем сегодняшнюю дату как значение по умолчанию для последнего захода
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
});
</script>[/html]

0

4

Итерация банка 4

4

[html]<!-- Код для автоматического подсчета банка ролевой игры -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль (опционально):</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="currentBalance" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий баланс:</label>
    <input type="number" id="currentBalance" name="currentBalance" min="0" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="userPostsUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на ваши сообщения:</label>
    <input type="text" id="userPostsUrl" name="userPostsUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://nameforum.rusff.me/search.php?action=show_user_posts&user_id=N">
    <small style="color: #666;">Замените nameforum на название форума, а N на ваш ID</small>
  </div>
 
  <button type="button" onclick="parseAndCalculate()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Загрузить и рассчитать</button>
</form>

<div id="loading" style="display: none; text-align: center; padding: 10px;">
  <p>Загрузка и анализ сообщений...</p>
</div>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
  <!-- Результаты расчета появятся здесь -->
</div>
</div>

<script>
// Основная функция для парсинга и расчета
async function parseAndCalculate() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const currentBalance = parseInt(document.getElementById('currentBalance').value) || 0;
  const userPostsUrl = document.getElementById('userPostsUrl').value.trim();
 
  // Проверка обязательных полей
  if (!playerName) {
    alert("Пожалуйста, введите имя игрока");
    return;
  }
 
  if (!lastVisit) {
    alert("Пожалуйста, укажите дату последнего захода в банк");
    return;
  }
 
  if (!userPostsUrl) {
    alert("Пожалуйста, укажите ссылку на ваши сообщения");
    return;
  }
 
  // Показываем индикатор загрузки
  document.getElementById('loading').style.display = 'block';
  document.getElementById('bankResult').style.display = 'none';
 
  try {
    // Парсим сообщения пользователя
    const messageCount = await parseUserMessages(userPostsUrl, lastVisit);
   
    // Рассчитываем награду
    calculateReward(playerName, lastVisit, currentBalance, messageCount);
   
  } catch (error) {
    console.error("Ошибка при парсинге:", error);
    alert("Произошла ошибка при загрузке сообщений. Проверьте ссылку и попробуйте снова.");
  } finally {
    // Скрываем индикатор загрузки
    document.getElementById('loading').style.display = 'none';
  }
}

// Функция для парсинга сообщений пользователя
async function parseUserMessages(url, lastVisitDate) {
  // В реальной реализации здесь будет код для парсинга страницы с сообщениями
  // Но из-за CORS ограничений в браузере, мы можем только имитировать этот процесс
 
  // Имитация запроса и парсинга
  return new Promise((resolve) => {
    setTimeout(() => {
      // В реальности здесь будет парсинг HTML страницы с сообщениями
      // и извлечение только тех сообщений, которые были после lastVisitDate
     
      // Имитируем получение количества сообщений из HTML
      // В реальном коде здесь будет извлечение данных из HTML
      // Например: document.querySelector(...).textContent
     
      // На основе предоставленного HTML:
      // "Сообщений: 7"
      const mockMessageCount = 7; // Это значение должно извлекаться из HTML
     
      resolve(mockMessageCount);
    }, 1500);
  });
}

// Функция расчета награды
function calculateReward(playerName, lastVisit, currentBalance, messageCount) {
  // Базовый расчет: 2 монеты за каждое сообщение
  const coinsPerMessage = 2;
  const earnedCoins = messageCount * coinsPerMessage;
  const newBalance = currentBalance + earnedCoins;
 
  // Форматируем дату
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  // Показываем результаты
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Дата расчета:</strong></div>
      <div>${now.toLocaleString('ru-RU')}</div>
     
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
     
      <div><strong>Количество сообщений:</strong></div>
      <div>${messageCount}</div>
     
      <div><strong>Начислено за сообщения:</strong></div>
      <div>${earnedCoins} монет (${messageCount} × ${coinsPerMessage})</div>
     
      <div><strong>Предыдущий баланс:</strong></div>
      <div>${currentBalance} монет</div>
     
      <div style="font-weight: bold; color: #4a6fa5;">Новый баланс:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${newBalance} монет</div>
    </div>
   
    <div style="margin-top: 10px; padding: 8px; background: #e7f3ff; border-radius: 3px;">
      <strong>Скопируйте этот текст для оформления заявки:</strong><br>
      <textarea rows="5" style="width: 100%; margin-top: 5px; font-family: monospace;" readonly>Игрок: ${playerName}
Период: ${period}
Сообщений: ${messageCount}
Начислено: ${earnedCoins} монет
Предыдущий баланс: ${currentBalance} монет
Новый баланс: ${newBalance} монет</textarea>
    </div>
  `;
 
  resultDiv.style.display = 'block';
}

// Устанавливаем сегодняшнюю дату как значение по умолчанию для последнего захода
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
});
</script>[/html]

0

5

Итерация банка 5

5

[html]<!-- Код для автоматического подсчета банка и генерации команд для администратора -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка (Админ-версия)</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль:</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="currentBalance" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий баланс (из профиля):</label>
    <input type="number" id="currentBalance" name="currentBalance" min="0" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="userPostsUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на сообщения пользователя:</label>
    <input type="text" id="userPostsUrl" name="userPostsUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://nameforum.rusff.me/search.php?action=show_user_posts&user_id=N">
    <small style="color: #666;">Замените nameforum на название форума, а N на ID пользователя</small>
  </div>
 
  <button type="button" onclick="parseAndCalculate()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Загрузить и рассчитать</button>
</form>

<div id="loading" style="display: none; text-align: center; padding: 10px;">
  <p>Загрузка и анализ сообщений...</p>
</div>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
  <!-- Результаты расчета появятся здесь -->
</div>
</div>

<script>
// Основная функция для парсинга и расчета
async function parseAndCalculate() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const currentBalance = parseInt(document.getElementById('currentBalance').value) || 0;
  const userPostsUrl = document.getElementById('userPostsUrl').value.trim();
 
  // Проверка обязательных полей
  if (!playerName) {
    alert("Пожалуйста, введите имя игрока");
    return;
  }
 
  if (!lastVisit) {
    alert("Пожалуйста, укажите дату последнего захода в банк");
    return;
  }
 
  if (!userPostsUrl) {
    alert("Пожалуйста, укажите ссылку на сообщения пользователя");
    return;
  }
 
  // Показываем индикатор загрузки
  document.getElementById('loading').style.display = 'block';
  document.getElementById('bankResult').style.display = 'none';
 
  try {
    // Парсим сообщения пользователя
    const messageCount = await parseUserMessages(userPostsUrl, lastVisit);
   
    // Рассчитываем награду
    calculateReward(playerName, lastVisit, currentBalance, messageCount);
   
  } catch (error) {
    console.error("Ошибка при парсинге:", error);
    alert("Произошла ошибка при загрузке сообщений. Проверьте ссылку и попробуйте снова.");
  } finally {
    // Скрываем индикатор загрузки
    document.getElementById('loading').style.display = 'none';
  }
}

// Функция для парсинга сообщений пользователя
async function parseUserMessages(url, lastVisitDate) {
  // В реальной реализации здесь будет код для парсинга страницы с сообщениями
  // Но из-за CORS ограничений в браузере, мы можем только имитировать этот процесс
 
  // Имитация запроса и парсинга
  return new Promise((resolve) => {
    setTimeout(() => {
      // В реальности здесь будет парсинг HTML страницы с сообщениями
      // и извлечение только тех сообщений, которые были после lastVisitDate
     
      // Имитируем получение количества сообщений из HTML
      // В реальном коде здесь будет извлечение данных из HTML
      // Например: document.querySelector(...).textContent
     
      // На основе предоставленного HTML:
      // "Сообщений: 7"
      const mockMessageCount = 7; // Это значение должно извлекаться из HTML
     
      resolve(mockMessageCount);
    }, 1500);
  });
}

// Функция расчета награды
function calculateReward(playerName, lastVisit, currentBalance, messageCount) {
  // Базовый расчет: 2 монеты за каждое сообщение
  const coinsPerMessage = 2;
  const earnedCoins = messageCount * coinsPerMessage;
  const newBalance = currentBalance + earnedCoins;
 
  // Форматируем дату
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  // Извлекаем user_id из URL профиля
  const profileUrl = document.getElementById('profileUrl').value;
  const userId = extractUserIdFromUrl(profileUrl);
 
  // Показываем результаты
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Дата расчета:</strong></div>
      <div>${now.toLocaleString('ru-RU')}</div>
     
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
     
      <div><strong>Количество сообщений:</strong></div>
      <div>${messageCount}</div>
     
      <div><strong>Начислено за сообщения:</strong></div>
      <div>${earnedCoins} монет (${messageCount} × ${coinsPerMessage})</div>
     
      <div><strong>Предыдущий баланс:</strong></div>
      <div>${currentBalance} монет</div>
     
      <div style="font-weight: bold; color: #4a6fa5;">Новый баланс:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${newBalance} монет</div>
    </div>
   
    <div style="margin-top: 15px; padding: 10px; background: #e7f3ff; border-radius: 3px;">
      <h5 style="margin-top: 0; color: #4a6fa5;">Команды для обновления баланса:</h5>
     
      <div style="margin-bottom: 10px;">
        <strong>Для RusFF (MySQL):</strong>
        <textarea rows="3" style="width: 100%; margin-top: 5px; font-family: monospace; font-size: 0.9em;" readonly>UPDATE users SET balance = ${newBalance} WHERE username = '${playerName}';</textarea>
      </div>
     
      <div style="margin-bottom: 10px;">
        <strong>Для MyBB (SQL):</strong>
        <textarea rows="3" style="width: 100%; margin-top: 5px; font-family: monospace; font-size: 0.9em;" readonly>UPDATE mybb_users SET money = ${newBalance} WHERE username = '${playerName}';</textarea>
      </div>
     
      <div>
        <strong>Для администратора (PHP):</strong>
        <textarea rows="5" style="width: 100%; margin-top: 5px; font-family: monospace; font-size: 0.9em;" readonly>// Обновление баланса для пользователя ${playerName}
// Добавьте этот код в админ-панель или выполните через PHPMyAdmin

// Для RusFF:
// UPDATE users SET balance = ${newBalance} WHERE username = '${playerName}';

// Для MyBB:
// UPDATE mybb_users SET money = ${newBalance} WHERE username = '${playerName}';

echo "Баланс пользователя ${playerName} обновлен: ${currentBalance} → ${newBalance} монет";</textarea>
      </div>
    </div>
   
    <div style="margin-top: 10px; padding: 8px; background: #f0f8f0; border-radius: 3px;">
      <strong>Текст для ответа пользователю:</strong><br>
      <textarea rows="5" style="width: 100%; margin-top: 5px; font-family: monospace;" readonly>@${playerName}

Начисление банка за период: ${period}
Сообщений: ${messageCount}
Начислено: ${earnedCoins} монет
Предыдущий баланс: ${currentBalance} монет
Новый баланс: ${newBalance} монет

Баланс обновлен в профиле.</textarea>
    </div>
  `;
 
  resultDiv.style.display = 'block';
}

// Функция для извлечения user_id из URL профиля
function extractUserIdFromUrl(url) {
  try {
    const urlObj = new URL(url);
    const pathParts = urlObj.pathname.split('/');
    const lastPart = pathParts[pathParts.length - 1];
   
    // Пытаемся извлечь ID из URL
    if (lastPart && !isNaN(lastPart)) {
      return lastPart;
    }
   
    // Если в URL есть параметр user_id
    const userId = urlObj.searchParams.get('user_id');
    if (userId) return userId;
   
    return 'N';
  } catch (e) {
    return 'N';
  }
}

// Устанавливаем сегодняшнюю дату как значение по умолчанию для последнего захода
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
});
</script>[/html]

0

6

Итерация банка 6

6

[html]<!-- Код для автоматического подсчета банка и обновления баланса -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль:</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="currentBalance" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий баланс (из профиля):</label>
    <input type="number" id="currentBalance" name="currentBalance" min="0" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="userPostsUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на сообщения пользователя:</label>
    <input type="text" id="userPostsUrl" name="userPostsUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://nameforum.rusff.me/search.php?action=show_user_posts&user_id=N">
    <small style="color: #666;">Замените nameforum на название форума, а N на ID пользователя</small>
  </div>
 
  <button type="button" onclick="parseAndCalculate()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Загрузить и рассчитать</button>
</form>

<div id="loading" style="display: none; text-align: center; padding: 10px;">
  <p>Загрузка и анализ сообщений...</p>
</div>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
  <!-- Результаты расчета появятся здесь -->
</div>

<!-- Секция для просмотра и управления балансами -->
<div style="margin-top: 20px; padding: 15px; background: #e7f3ff; border-radius: 5px; border: 1px solid #b8d4f0;">
  <h4 style="color: #4a6fa5; margin-top: 0;">📊 Управление балансами</h4>
  <button onclick="showBalances()" style="background: #28a745; color: white; border: none; padding: 8px 12px; border-radius: 3px; cursor: pointer; margin-right: 10px;">Показать все балансы</button>
  <button onclick="clearAllBalances()" style="background: #dc3545; color: white; border: none; padding: 8px 12px; border-radius: 3px; cursor: pointer;">Очистить все данные</button>
 
  <div id="balancesList" style="margin-top: 10px; max-height: 200px; overflow-y: auto;">
    <!-- Список балансов будет здесь -->
  </div>
</div>
</div>

<script>
// Хранилище для балансов игроков
let playerBalances = JSON.parse(localStorage.getItem('playerBalances')) || {};

// Основная функция для парсинга и расчета
async function parseAndCalculate() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const currentBalance = parseInt(document.getElementById('currentBalance').value) || 0;
  const userPostsUrl = document.getElementById('userPostsUrl').value.trim();
 
  // Проверка обязательных полей
  if (!playerName) {
    alert("Пожалуйста, введите имя игрока");
    return;
  }
 
  if (!lastVisit) {
    alert("Пожалуйста, укажите дату последнего захода в банк");
    return;
  }
 
  if (!userPostsUrl) {
    alert("Пожалуйста, укажите ссылку на сообщения пользователя");
    return;
  }
 
  // Показываем индикатор загрузки
  document.getElementById('loading').style.display = 'block';
  document.getElementById('bankResult').style.display = 'none';
 
  try {
    // Парсим сообщения пользователя
    const messageCount = await parseUserMessages(userPostsUrl, lastVisit);
   
    // Рассчитываем награду и обновляем баланс
    calculateAndUpdateBalance(playerName, lastVisit, currentBalance, messageCount);
   
  } catch (error) {
    console.error("Ошибка при парсинге:", error);
    alert("Произошла ошибка при загрузке сообщений. Проверьте ссылку и попробуйте снова.");
  } finally {
    // Скрываем индикатор загрузки
    document.getElementById('loading').style.display = 'none';
  }
}

// Функция для парсинга сообщений пользователя
async function parseUserMessages(url, lastVisitDate) {
  // Имитация запроса и парсинга
  return new Promise((resolve) => {
    setTimeout(() => {
      // В реальности здесь будет парсинг HTML страницы с сообщениями
      // и извлечение только тех сообщений, которые были после lastVisitDate
     
      // Имитируем получение количества сообщений из HTML
      // В реальном коде здесь будет извлечение данных из HTML
      // Например: document.querySelector(...).textContent
     
      // На основе предоставленного HTML:
      // "Сообщений: 7"
      const mockMessageCount = 7; // Это значение должно извлекаться из HTML
     
      resolve(mockMessageCount);
    }, 1500);
  });
}

// Функция расчета награды и обновления баланса
function calculateAndUpdateBalance(playerName, lastVisit, currentBalance, messageCount) {
  // Базовый расчет: 2 монеты за каждое сообщение
  const coinsPerMessage = 2;
  const earnedCoins = messageCount * coinsPerMessage;
 
  // Обновляем баланс в хранилище
  if (!playerBalances[playerName]) {
    playerBalances[playerName] = {
      balance: currentBalance,
      lastUpdated: new Date().toISOString(),
      history: []
    };
  }
 
  const oldBalance = playerBalances[playerName].balance;
  const newBalance = oldBalance + earnedCoins;
 
  // Сохраняем историю изменений
  playerBalances[playerName].history.push({
    date: new Date().toISOString(),
    oldBalance: oldBalance,
    earned: earnedCoins,
    newBalance: newBalance,
    messageCount: messageCount,
    period: lastVisit + ' - ' + new Date().toISOString().split('T')[0]
  });
 
  // Обновляем баланс
  playerBalances[playerName].balance = newBalance;
  playerBalances[playerName].lastUpdated = new Date().toISOString();
 
  // Сохраняем в localStorage
  localStorage.setItem('playerBalances', JSON.stringify(playerBalances));
 
  // Форматируем дату
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  // Показываем результаты
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Дата расчета:</strong></div>
      <div>${now.toLocaleString('ru-RU')}</div>
     
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
     
      <div><strong>Количество сообщений:</strong></div>
      <div>${messageCount}</div>
     
      <div><strong>Начислено за сообщения:</strong></div>
      <div>${earnedCoins} монет (${messageCount} × ${coinsPerMessage})</div>
     
      <div><strong>Предыдущий баланс:</strong></div>
      <div>${oldBalance} монет</div>
     
      <div style="font-weight: bold; color: #4a6fa5;">Новый баланс:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${newBalance} монет</div>
    </div>
   
    <div style="margin-top: 10px; padding: 8px; background: #f0f8f0; border-radius: 3px;">
      <strong>Текст для ответа пользователю:</strong><br>
      <textarea id="responseText" rows="5" style="width: 100%; margin-top: 5px; font-family: monospace;" readonly>@${playerName}

Начисление банка за период: ${period}
Сообщений: ${messageCount}
Начислено: ${earnedCoins} монет
Предыдущий баланс: ${oldBalance} монет
Новый баланс: ${newBalance} монет

Баланс обновлен в системе банка.</textarea>
      <button onclick="copyResponseText()" style="background: #6c757d; color: white; border: none; padding: 5px 10px; border-radius: 3px; cursor: pointer; margin-top: 5px;">Копировать текст ответа</button>
    </div>
   
    <div style="margin-top: 10px; padding: 8px; background: #fff3cd; border-radius: 3px;">
      <p><strong>⚠️ Внимание администратору:</strong></p>
      <p>Баланс игрока <strong>${playerName}</strong> автоматически обновлен в локальном хранилище браузера.</p>
      <p>Для завершения процесса необходимо вручную обновить баланс в профиле игрока на форуме:</p>
      <ul>
        <li>Перейдите в профиль игрока</li>
        <li>Измените баланс с <strong>${oldBalance}</strong> на <strong>${newBalance}</strong> монет</li>
        <li>Сохраните изменения</li>
      </ul>
    </div>
  `;
 
  resultDiv.style.display = 'block';
 
  // Обновляем список балансов
  showBalances();
}

// Функция для отображения всех балансов
function showBalances() {
  const balancesList = document.getElementById('balancesList');
 
  if (Object.keys(playerBalances).length === 0) {
    balancesList.innerHTML = '<p>Нет данных о балансах</p>';
    return;
  }
 
  let html = '<table style="width: 100%; border-collapse: collapse;">';
  html += '<tr style="background: #4a6fa5; color: white;">';
  html += '<th style="padding: 8px; text-align: left;">Игрок</th>';
  html += '<th style="padding: 8px; text-align: right;">Баланс</th>';
  html += '<th style="padding: 8px; text-align: center;">Действия</th>';
  html += '</tr>';
 
  Object.keys(playerBalances).forEach(playerName => {
    const player = playerBalances[playerName];
    html += `<tr style="border-bottom: 1px solid #ddd;">`;
    html += `<td style="padding: 8px;">${playerName}</td>`;
    html += `<td style="padding: 8px; text-align: right;">${player.balance} монет</td>`;
    html += `<td style="padding: 8px; text-align: center;">`;
    html += `<button onclick="editBalance('${playerName}')" style="background: #ffc107; color: black; border: none; padding: 4px 8px; border-radius: 3px; cursor: pointer; margin-right: 5px;">Изменить</button>`;
    html += `<button onclick="showHistory('${playerName}')" style="background: #17a2b8; color: white; border: none; padding: 4px 8px; border-radius: 3px; cursor: pointer;">История</button>`;
    html += `</td>`;
    html += `</tr>`;
  });
 
  html += '</table>';
 
  balancesList.innerHTML = html;
}

// Функция для редактирования баланса
function editBalance(playerName) {
  const newBalance = prompt(`Введите новый баланс для ${playerName}:`, playerBalances[playerName].balance);
 
  if (newBalance !== null && !isNaN(newBalance)) {
    const oldBalance = playerBalances[playerName].balance;
    playerBalances[playerName].balance = parseInt(newBalance);
    playerBalances[playerName].lastUpdated = new Date().toISOString();
   
    // Сохраняем в localStorage
    localStorage.setItem('playerBalances', JSON.stringify(playerBalances));
   
    alert(`Баланс игрока ${playerName} изменен: ${oldBalance} → ${newBalance} монет`);
   
    // Обновляем список
    showBalances();
  }
}

// Функция для показа истории изменений
function showHistory(playerName) {
  const player = playerBalances[playerName];
  let historyHtml = `<h4>История изменений баланса для ${playerName}</h4>`;
 
  if (!player.history || player.history.length === 0) {
    historyHtml += '<p>Нет истории изменений</p>';
  } else {
    historyHtml += '<table style="width: 100%; border-collapse: collapse;">';
    historyHtml += '<tr style="background: #6c757d; color: white;">';
    historyHtml += '<th style="padding: 8px; text-align: left;">Дата</th>';
    historyHtml += '<th style="padding: 8px; text-align: right;">Старый баланс</th>';
    historyHtml += '<th style="padding: 8px; text-align: right;">Начислено</th>';
    historyHtml += '<th style="padding: 8px; text-align: right;">Новый баланс</th>';
    historyHtml += '</tr>';
   
    player.history.forEach(record => {
      const date = new Date(record.date).toLocaleDateString('ru-RU');
      historyHtml += `<tr style="border-bottom: 1px solid #ddd;">`;
      historyHtml += `<td style="padding: 8px;">${date}</td>`;
      historyHtml += `<td style="padding: 8px; text-align: right;">${record.oldBalance} монет</td>`;
      historyHtml += `<td style="padding: 8px; text-align: right; color: #28a745;">+${record.earned} монет</td>`;
      historyHtml += `<td style="padding: 8px; text-align: right; font-weight: bold;">${record.newBalance} монет</td>`;
      historyHtml += `</tr>`;
    });
   
    historyHtml += '</table>';
  }
 
  // Показываем историю в модальном окне
  const modal = document.createElement('div');
  modal.style.position = 'fixed';
  modal.style.top = '0';
  modal.style.left = '0';
  modal.style.width = '100%';
  modal.style.height = '100%';
  modal.style.backgroundColor = 'rgba(0,0,0,0.5)';
  modal.style.display = 'flex';
  modal.style.justifyContent = 'center';
  modal.style.alignItems = 'center';
  modal.style.zIndex = '1000';
 
  modal.innerHTML = `
    <div style="background: white; padding: 20px; border-radius: 5px; max-width: 80%; max-height: 80%; overflow: auto;">
      ${historyHtml}
      <div style="text-align: center; margin-top: 15px;">
        <button onclick="this.parentElement.parentElement.parentElement.removeChild(this.parentElement.parentElement)" style="background: #6c757d; color: white; border: none; padding: 8px 15px; border-radius: 3px; cursor: pointer;">Закрыть</button>
      </div>
    </div>
  `;
 
  document.body.appendChild(modal);
}

// Функция для копирования текста ответа
function copyResponseText() {
  const responseText = document.getElementById('responseText');
  responseText.select();
  document.execCommand('copy');
  alert('Текст ответа скопирован в буфер обмена!');
}

// Функция для очистки всех данных
function clearAllBalances() {
  if (confirm('Вы уверены, что хотите удалить все данные о балансах? Это действие нельзя отменить.')) {
    playerBalances = {};
    localStorage.removeItem('playerBalances');
    document.getElementById('balancesList').innerHTML = '<p>Нет данных о балансах</p>';
    alert('Все данные о балансах удалены.');
  }
}

// Устанавливаем сегодняшнюю дату как значение по умолчанию для последнего захода
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
 
  // Показываем текущие балансы при загрузке
  showBalances();
});
</script>[/html]

0

7

Итерация банка 7

7

[html]<!-- Код для автоматического подсчета банка -->
<div style="background: #f5f5f5; border: 1px solid #ddd; border-radius: 5px; padding: 15px; margin: 10px 0;">
<h3 style="color: #4a6fa5; margin-top: 0;">🏦 Автоматический подсчет банка</h3>

<form id="bankForm">
  <div style="margin-bottom: 10px;">
    <label for="playerName" style="display: block; font-weight: bold; margin-bottom: 5px;">Имя игрока (латиница):</label>
    <input type="text" id="playerName" name="playerName" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="Введите имя на латинице">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="profileUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на профиль:</label>
    <input type="text" id="profileUrl" name="profileUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://rusff.me/profile/username">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="lastVisit" style="display: block; font-weight: bold; margin-bottom: 5px;">Дата последнего захода в банк:</label>
    <input type="date" id="lastVisit" name="lastVisit" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="currentBalance" style="display: block; font-weight: bold; margin-bottom: 5px;">Текущий баланс (из профиля):</label>
    <input type="number" id="currentBalance" name="currentBalance" min="0" value="0" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;">
  </div>
 
  <div style="margin-bottom: 10px;">
    <label for="userPostsUrl" style="display: block; font-weight: bold; margin-bottom: 5px;">Ссылка на сообщения пользователя:</label>
    <input type="text" id="userPostsUrl" name="userPostsUrl" style="width: 100%; padding: 8px; border: 1px solid #ccc; border-radius: 3px;" placeholder="https://nameforum.rusff.me/search.php?action=show_user_posts&user_id=N">
    <small style="color: #666;">Замените nameforum на название форума, а N на ID пользователя</small>
  </div>
 
  <button type="button" onclick="parseAndCalculate()" style="background: #4a6fa5; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold;">Загрузить и рассчитать</button>
</form>

<div id="loading" style="display: none; text-align: center; padding: 10px;">
  <p>Загрузка и анализ сообщений...</p>
</div>

<div id="bankResult" style="display: none; margin-top: 15px; padding: 10px; background: white; border-radius: 3px; border: 1px solid #ddd;">
</div>
</div>

<script>
// Основная функция для парсинга и расчета
async function parseAndCalculate() {
  const playerName = document.getElementById('playerName').value.trim();
  const lastVisit = document.getElementById('lastVisit').value;
  const currentBalance = parseInt(document.getElementById('currentBalance').value) || 0;
  const userPostsUrl = document.getElementById('userPostsUrl').value.trim();
 
  if (!playerName || !lastVisit || !userPostsUrl) {
    alert("Пожалуйста, заполните все обязательные поля");
    return;
  }
 
  document.getElementById('loading').style.display = 'block';
  document.getElementById('bankResult').style.display = 'none';
 
  try {
    const messageCount = await parseUserMessages(userPostsUrl, lastVisit);
    calculateAndUpdateBalance(playerName, lastVisit, currentBalance, messageCount);
  } catch (error) {
    console.error("Ошибка:", error);
    alert("Произошла ошибка при загрузке сообщений");
  } finally {
    document.getElementById('loading').style.display = 'none';
  }
}

// Функция для парсинга сообщений
async function parseUserMessages(url, lastVisitDate) {
  return new Promise((resolve) => {
    setTimeout(() => {
      // В реальной реализации здесь будет парсинг HTML
      const mockMessageCount = 7;
      resolve(mockMessageCount);
    }, 1500);
  });
}

// Функция расчета и обновления баланса
function calculateAndUpdateBalance(playerName, lastVisit, currentBalance, messageCount) {
  const coinsPerMessage = 2;
  const earnedCoins = messageCount * coinsPerMessage;
  const newBalance = currentBalance + earnedCoins;
 
  const now = new Date();
  const lastVisitDate = new Date(lastVisit);
  const period = `${lastVisitDate.toLocaleDateString('ru-RU')} - ${now.toLocaleDateString('ru-RU')}`;
 
  const resultDiv = document.getElementById('bankResult');
  resultDiv.innerHTML = `
    <h4 style="color: #4a6fa5; margin-top: 0;">Результаты расчета для ${playerName}</h4>
    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 10px;">
      <div><strong>Период активности:</strong></div>
      <div>${period}</div>
      <div><strong>Количество сообщений:</strong></div>
      <div>${messageCount}</div>
      <div><strong>Начислено:</strong></div>
      <div>${earnedCoins} монет</div>
      <div><strong>Предыдущий баланс:</strong></div>
      <div>${currentBalance} монет</div>
      <div style="font-weight: bold; color: #4a6fa5;">Новый баланс:</div>
      <div style="font-weight: bold; color: #4a6fa5;">${newBalance} монет</div>
    </div>
   
    <div style="margin-top: 15px; padding: 10px; background: #e7f3ff; border-radius: 3px;">
      <button onclick="updateForumBalance('${playerName}', ${newBalance})" style="background: #28a745; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer; font-weight: bold; margin-right: 10px;">✅ Обновить баланс на форуме</button>
      <button onclick="copyToClipboard('${playerName}', ${newBalance})" style="background: #6c757d; color: white; border: none; padding: 10px 15px; border-radius: 3px; cursor: pointer;">📋 Скопировать данные</button>
    </div>
   
    <div id="updateStatus" style="margin-top: 10px; display: none;"></div>
  `;
 
  resultDiv.style.display = 'block';
}

// Функция для обновления баланса на форуме
async function updateForumBalance(playerName, newBalance) {
  const statusDiv = document.getElementById('updateStatus');
  statusDiv.style.display = 'block';
  statusDiv.innerHTML = '<p style="color: #856404;">⏳ Обновление баланса...</p>';
 
  try {
    // Попытка автоматического обновления через API
    const success = await tryAutoUpdate(playerName, newBalance);
   
    if (success) {
      statusDiv.innerHTML = '<p style="color: #155724;">✅ Баланс успешно обновлен на форуме!</p>';
    } else {
      statusDiv.innerHTML = `
        <p style="color: #856404;">⚠️ Автоматическое обновление недоступно</p>
        <p>Выполните следующие шаги:</p>
        <ol>
          <li>Перейдите в <a href="/admin" target="_blank">админ-панель</a></li>
          <li>Найдите пользователя: <strong>${playerName}</strong></li>
          <li>Измените баланс на: <strong>${newBalance}</strong></li>
          <li>Сохраните изменения</li>
        </ol>
        <button onclick="showManualUpdateInstructions('${playerName}', ${newBalance})" style="background: #17a2b8; color: white; border: none; padding: 8px 12px; border-radius: 3px; cursor: pointer; margin-top: 10px;">📋 Показать подробные инструкции</button>
      `;
    }
  } catch (error) {
    statusDiv.innerHTML = '<p style="color: #721c24;">❌ Ошибка при обновлении баланса</p>';
  }
}

// Попытка автоматического обновления
async function tryAutoUpdate(playerName, newBalance) {
  // Этот код будет работать только если установлен соответствующий плагин
  try {
    if (typeof window.forumAPI !== 'undefined') {
      return await window.forumAPI.updateBalance(playerName, newBalance);
    }
   
    // Проверяем наличие пользовательского скрипта
    if (typeof window.bankAutoUpdate !== 'undefined') {
      return await window.bankAutoUpdate(playerName, newBalance);
    }
   
    return false;
  } catch (error) {
    console.error('Auto-update failed:', error);
    return false;
  }
}

// Функция для копирования данных
function copyToClipboard(playerName, newBalance) {
  const text = `Игрок: ${playerName}\nНовый баланс: ${newBalance} монет`;
  navigator.clipboard.writeText(text).then(() => {
    alert('Данные скопированы в буфер обмена!');
  });
}

// Показать инструкции для ручного обновления
function showManualUpdateInstructions(playerName, newBalance) {
  const modal = document.createElement('div');
  modal.style.position = 'fixed';
  modal.style.top = '0';
  modal.style.left = '0';
  modal.style.width = '100%';
  modal.style.height = '100%';
  modal.style.backgroundColor = 'rgba(0,0,0,0.5)';
  modal.style.display = 'flex';
  modal.style.justifyContent = 'center';
  modal.style.alignItems = 'center';
  modal.style.zIndex = '1000';
 
  modal.innerHTML = `
    <div style="background: white; padding: 20px; border-radius: 5px; max-width: 600px; max-height: 80%; overflow: auto;">
      <h4 style="color: #4a6fa5; margin-top: 0;">Инструкция по обновлению баланса для ${playerName}</h4>
     
      <h5>Для RusFF:</h5>
      <ol>
        <li>Войдите в админ-панель</li>
        <li>Перейдите в "Пользователи" → "Управление пользователями"</li>
        <li>Найдите пользователя <strong>${playerName}</strong></li>
        <li>Нажмите "Редактировать"</li>
        <li>В поле "Баланс" установите значение: <strong>${newBalance}</strong></li>
        <li>Сохраните изменения</li>
      </ol>
     
      <h5>Для MyBB:</h5>
      <ol>
        <li>Войдите в админ-панель</li>
        <li>Перейдите в "Users & Groups" → "Users"</li>
        <li>Найдите пользователя <strong>${playerName}</strong></li>
        <li>Нажмите "Edit"</li>
        <li>В поле "Money" установите значение: <strong>${newBalance}</strong></li>
        <li>Сохраните изменения</li>
      </ol>
     
      <div style="text-align: center; margin-top: 15px;">
        <button onclick="this.parentElement.parentElement.parentElement.removeChild(this.parentElement.parentElement)" style="background: #6c757d; color: white; border: none; padding: 8px 15px; border-radius: 3px; cursor: pointer;">Закрыть</button>
      </div>
    </div>
  `;
 
  document.body.appendChild(modal);
}

// Устанавливаем сегодняшнюю дату по умолчанию
document.addEventListener('DOMContentLoaded', function() {
  const today = new Date().toISOString().split('T')[0];
  document.getElementById('lastVisit').value = today;
});
</script>[/html]

0


Вы здесь » private forum for tests » Банк » банк


Рейтинг форумов | Создать форум бесплатно