Nurbo Mod

Auto Insta etc Shift=InstaNormal R=ReverseInsta Space=BoostSpike 2nd click Fast Break B=4Traps-Boost C=4Spikes ,=AntiTrap / M=AutoMills F=Trap-BoostPad V=Spike N=Mill g=Teleport-Turret / AutoBiomeHat Esc=Menu AutoHeal AutoGG

スクリプトをインストールするには、Tampermonkey, GreasemonkeyViolentmonkey のような拡張機能のインストールが必要です。

You will need to install an extension such as Tampermonkey to install this script.

スクリプトをインストールするには、TampermonkeyViolentmonkey のような拡張機能のインストールが必要です。

スクリプトをインストールするには、TampermonkeyUserscripts のような拡張機能のインストールが必要です。

このスクリプトをインストールするには、Tampermonkeyなどの拡張機能をインストールする必要があります。

このスクリプトをインストールするには、ユーザースクリプト管理ツールの拡張機能をインストールする必要があります。

(ユーザースクリプト管理ツールは設定済みなのでインストール!)

このスタイルをインストールするには、Stylusなどの拡張機能をインストールする必要があります。

このスタイルをインストールするには、Stylus などの拡張機能をインストールする必要があります。

このスタイルをインストールするには、Stylus tなどの拡張機能をインストールする必要があります。

このスタイルをインストールするには、ユーザースタイル管理用の拡張機能をインストールする必要があります。

このスタイルをインストールするには、ユーザースタイル管理用の拡張機能をインストールする必要があります。

このスタイルをインストールするには、ユーザースタイル管理用の拡張機能をインストールする必要があります。

(ユーザースタイル管理ツールは設定済みなのでインストール!)

このスクリプトの質問や評価の投稿はこちら通報はこちらへお寄せください
// ==UserScript==
// @name         Nurbo Mod
// @namespace    http://youtube.com
// @version      1.5.5.10
// @description  Auto Insta etc  Shift=InstaNormal   R=ReverseInsta   Space=BoostSpike  2nd click Fast Break    B=4Traps-Boost   C=4Spikes     ,=AntiTrap / M=AutoMills   F=Trap-BoostPad    V=Spike N=Mill  g=Teleport-Turret / AutoBiomeHat  Esc=Menu  AutoHeal AutoGG 
// @icon         https://static.wikia.nocookie.net/moom/images/7/70/Cookie.png/revision/latest?cb=20190223141839
// @author       Nurbo Mod
// @match        *://moomoo.io/*
// @match        *://*.moomoo.io/*
// @match        *://sandbox.moomoo.io/*
// @match        *://dev.moomoo.io/*
// @grant        none
// @require      https://update.greasyfork.org/scripts/423602/1005014/msgpack.js
// @require      https://update.greasyfork.org/scripts/480301/1322984/CowJS.js
// @require      https://cdn.jsdelivr.net/npm/[email protected]/fontfaceobserver.standalone.min.js
// @license      MIT
// ==/UserScript==

//Utility
(function () {
    'use strict';

    let ws;
    const msgpack5 = window.msgpack;

    let boostType, spikeType, turretType = null, windmillType = null, foodType;
    let width, height, mouseX, mouseY;
    let myPlayer = {
        id: null, x: null, y: null, dir: null, object: null,
        weapon: null, clan: null, isLeader: null,
        hat: null, accessory: null, isSkull: null,
        health: 100
    };
    let myPlayeroldx, myPlayeroldy;
    let automillx = 10, automilly = 10;
    let walkmillhaha = false;
    let autoHeal = true;
    const keysPressed = {};
    const placementIntervals = {};
    let gInterval = null;

    let autoaim = true;
    let nearestEnemy = null, nearestEnemyAngle = 0, enemiesNear = [];

    let gameTick = 0, lastDamageTick = 0, damageTimes = 0, shame = 0, shameTime = 0, HP = 100;
    let anti = true;
    let hitBack = false;
    let primary = null;

    // Auto Insta variables - КАК В x-RedDragon Client
    let autoInstaEnabled = false;
    let autoInstaDistance = 200; // расстояние для автоматической инсты (в пикселях)
    let autoInstaCooldown = 2000; // кулдаун в миллисекундах
    let lastAutoInstaTime = 0;
    let autoInstaCheckInterval = null;

    // Auto Spike Surround variables
    let autoSpikeSurroundEnabled = false;
    let spikeSurroundDistance = 50;
    let lastSpikeSurroundTime = 0;
    let spikeSurroundCooldown = 3000;

    // Menu variables
    let menuOpen = false;
    let menuElement = null;
    let menuBtn = null;

    function storeEquip(id, index) {
        doNewSend(["c", [0, id, index]]);
    }

    const cvs = document.getElementById("gameCanvas");
    if (!cvs) return;

    cvs.addEventListener("mousemove", e => {
        mouseX = e.clientX;
        mouseY = e.clientY;
        width = e.target.clientWidth;
        height = e.target.clientHeight;
    });

    function doNewSend(sender) {
        if (ws && msgpack5) ws.send(new Uint8Array(Array.from(msgpack5.encode(sender))));
    }

    function place(id, angle = Math.atan2(mouseY - height / 2, mouseX - width / 2)) {
        if (id == null) return;
        doNewSend(["z", [id, null]]);
        doNewSend(["F", [1, angle]]);
        doNewSend(["F", [0, angle]]);
        doNewSend(["z", [myPlayer.weapon, true]]);
    }

    function isVisible(el) {
        return el && el.offsetParent !== null;
    }

    function updateItems() {
        for (let i = 31; i < 33; i++) if (isVisible(document.getElementById("actionBarItem" + i))) boostType = i - 16;
        for (let i = 22; i < 26; i++) if (isVisible(document.getElementById("actionBarItem" + i))) spikeType = i - 16;
        for (let i = 26; i <= 28; i++) if (isVisible(document.getElementById("actionBarItem" + i))) windmillType = i - 16;
        for (let i = 33; i <= 38; i++) if (i !== 36 && isVisible(document.getElementById("actionBarItem" + i))) turretType = i - 16;
        for (let i = 16; i <= 18; i++) if (isVisible(document.getElementById("actionBarItem" + i))) foodType = i - 16;
    }
    setInterval(updateItems, 250);

    function toRad(degrees) {
        return degrees * 0.01745329251;
    }

    function getSecondaryWeaponIndex() {
        for (let i = 9; i <= 15; i++) {
            if (isVisible(document.getElementById("actionBarItem" + i)) && i !== myPlayer.weapon) {
                return i;
            }
        }
        return myPlayer.weapon;
    }

    function startPlacingStructure(key, itemId) {
        if (!placementIntervals[key]) placementIntervals[key] = setInterval(() => place(itemId), 50);
    }
    function stopPlacingStructure(key) {
        clearInterval(placementIntervals[key]);
        delete placementIntervals[key];
    }

    function performGSequence() {
        if (!nearestEnemy) return;

        const dx = myPlayer.x - nearestEnemy[1];
        const dy = myPlayer.y - nearestEnemy[2];
        const distance = Math.sqrt(dx * dx + dy * dy);

        doNewSend(["9", [nearestEnemyAngle]]);

        place(spikeType, nearestEnemyAngle + Math.PI / 2);
        place(spikeType, nearestEnemyAngle - Math.PI / 2);

        if (distance <= 150) {
            place(spikeType, nearestEnemyAngle - Math.PI / 4);
            place(spikeType, nearestEnemyAngle + Math.PI / 4);
        }

        place(boostType, nearestEnemyAngle);
    }

    function performBPlacement() {
        const base = myPlayer.dir;
        place(boostType, base);
        place(boostType, base + Math.PI / 2);
        place(boostType, base - Math.PI / 2);
        place(boostType, base + Math.PI);
    }

    function placeFourSpikesUp() {
        const firstAngle = -Math.PI / 2;
        place(spikeType, firstAngle);
        place(spikeType, firstAngle + toRad(90));
        place(spikeType, firstAngle + toRad(180));
        place(spikeType, firstAngle + toRad(270));
    }

    // Auto Spike Surround function
    function performSpikeSurround() {
        if (!nearestEnemy || !autoSpikeSurroundEnabled) return;

        const currentTime = Date.now();
        if (currentTime - lastSpikeSurroundTime < spikeSurroundCooldown) return;

        const dx = myPlayer.x - nearestEnemy[1];
        const dy = myPlayer.y - nearestEnemy[2];
        const distance = Math.sqrt(dx * dx + dy * dy);

        if (distance <= spikeSurroundDistance) {
            const enemyAngle = nearestEnemyAngle;
            place(spikeType, enemyAngle);
            place(spikeType, enemyAngle + Math.PI / 2);
            place(spikeType, enemyAngle + Math.PI);
            place(spikeType, enemyAngle + 3 * Math.PI / 2);

            lastSpikeSurroundTime = Date.now();
        }
    }

    // === INSTAKILL NORMAL === (ТОЧНО КАК В x-RedDragon Client)
    function performNormalInsta() {
        if (!nearestEnemy) return;

        storeEquip(0, 1);
        setTimeout(() => {
            autoaim = true;
            const primary = myPlayer.weapon;
            const secondary = getSecondaryWeaponIndex();

            doNewSend(["c", [0, 7, 0]]);
            doNewSend(["z", [primary, true]]);
            doNewSend(["F", [1]]);
            setTimeout(() => doNewSend(["F", [0]]), 25);

            setTimeout(() => {
                doNewSend(["c", [0, 53, 0]]);
                doNewSend(["z", [secondary, true]]);
                doNewSend(["F", [1]]);
                setTimeout(() => doNewSend(["F", [0]]), 25);

                setTimeout(() => {
                    doNewSend(["c", [0, 6, 0]]);
                    doNewSend(["z", [primary, true]]);
                    doNewSend(["z", [primary, true]]);
                    autoaim = false;

                    setTimeout(() => {
                        storeEquip(11, 1);

                        if (secondary === 15) {
                            doNewSend(["z", [secondary, true]]);
                            setTimeout(() => doNewSend(["z", [primary, true]]), 1900);
                        } else if (secondary === 12) {
                            doNewSend(["z", [secondary, true]]);
                            setTimeout(() => doNewSend(["z", [primary, true]]), 1000);
                        } else if (secondary === 13) {
                            doNewSend(["z", [secondary, true]]);
                            setTimeout(() => doNewSend(["z", [primary, true]]), 400);
                        }
                    }, 170);
                }, 120);
            }, 120);
        }, 120);
    }

    // Reverse Insta function (manual only)
    function performReverseInsta() {
        if (!nearestEnemy) return;

        storeEquip(0, 1);
        setTimeout(() => {
            autoaim = true;
            const primary = myPlayer.weapon;
            const secondary = getSecondaryWeaponIndex();

            doNewSend(["z", [secondary, true]]);
            doNewSend(["z", [secondary, true]]);

            doNewSend(["c", [0, 53, 0]]);
            doNewSend(["F", [1]]);
            setTimeout(() => doNewSend(["F", [0]]), 20);

            setTimeout(() => {
                doNewSend(["z", [primary, true]]);
                doNewSend(["c", [0, 7, 0]]);
                doNewSend(["F", [1]]);
                setTimeout(() => doNewSend(["F", [0]]), 20);
            }, 80);

            setTimeout(() => {
                doNewSend(["z", [primary, true]]);
                doNewSend(["z", [primary, true]]);
                doNewSend(["c", [0, 6, 0]]);
                storeEquip(11, 1);
                autoaim = false;

                setTimeout(() => {
                    if (secondary === 15) {
                        doNewSend(["z", [secondary, true]]);
                        setTimeout(() => doNewSend(["z", [primary, true]]), 1000);
                    } else if (secondary === 12) {
                        doNewSend(["z", [secondary, true]]);
                        setTimeout(() => doNewSend(["z", [primary, true]]), 700);
                    } else if (secondary === 13) {
                        doNewSend(["z", [secondary, true]]);
                        setTimeout(() => doNewSend(["z", [primary, true]]), 300);
                    }
                }, 150);
            }, 400);
        }, 100);
    }

    // Auto Insta function (КАК В x-RedDragon Client)
    function checkAndPerformAutoInsta() {
        if (!autoInstaEnabled || !nearestEnemy || myPlayer.health < 50) return;

        const currentTime = Date.now();
        if (currentTime - lastAutoInstaTime < autoInstaCooldown) return;

        const dx = myPlayer.x - nearestEnemy[1];
        const dy = myPlayer.y - nearestEnemy[2];
        const distance = Math.sqrt(dx * dx + dy * dy);

        if (distance <= autoInstaDistance) {
            performNormalInsta();
            lastAutoInstaTime = Date.now();
            doNewSend(["6", ["Auto-Insta активирована!"]]);
        }
    }

    function toggleAutoInsta() {
        autoInstaEnabled = !autoInstaEnabled;
        if (autoInstaEnabled) {
            if (!autoInstaCheckInterval) {
                autoInstaCheckInterval = setInterval(checkAndPerformAutoInsta, 1000); // Проверка каждую секунду
            }
            doNewSend(["6", ["Auto-Insta: ON (расстояние: " + autoInstaDistance + ")"]]);
        } else {
            if (autoInstaCheckInterval) {
                clearInterval(autoInstaCheckInterval);
                autoInstaCheckInterval = null;
            }
            doNewSend(["6", ["Auto-Insta: OFF"]]);
        }
        updateMenu();
    }

    function toggleAutoSpikeSurround() {
        autoSpikeSurroundEnabled = !autoSpikeSurroundEnabled;
        doNewSend(["6", ["AS " + (autoSpikeSurroundEnabled ?'hehe' : 'off')]]);
        updateMenu();
    }

    function toggleAutoHeal() {
        autoHeal = !autoHeal;
        doNewSend(["6", ["AH " + (autoHeal ? "terminator" : "bad boy")]]);
        updateMenu();
    }

    // Compact Menu functions
    function createMenu() {
        if (document.getElementById('nurbo-mod-menu')) return;

        menuElement = document.createElement('div');
        menuElement.id = 'nurbo-mod-menu';
        menuElement.style.cssText = `
            position: fixed;
            top: 50px;
            left: 10px;
            background: rgba(0, 0, 0, 0.92);
            color: white;
            padding: 12px;
            border-radius: 8px;
            z-index: 9999;
            font-family: 'Segoe UI', Arial, sans-serif;
            font-size: 13px;
            min-width: 280px;
            display: none;
            border: 2px solid #00ff00;
            box-shadow: 0 0 15px rgba(0, 255, 0, 0.4);
            backdrop-filter: blur(5px);
        `;

        document.body.appendChild(menuElement);
        updateMenu();
    }

    function updateMenu() {
        if (!menuElement) return;

        menuElement.innerHTML = '';

        // Title and close button
        const titleBar = document.createElement('div');
        titleBar.style.cssText = 'display: flex; justify-content: space-between; align-items: center; margin-bottom: 10px;';

        const title = document.createElement('div');
        title.textContent = '⚡ Nurbo Mod v1.5.5.5';
        title.style.cssText = 'font-size: 14px; font-weight: bold; color: #00ff00;';

        const closeBtn = document.createElement('button');
        closeBtn.textContent = '✖';
        closeBtn.style.cssText = `
            background: #ff3333;
            color: white;
            border: none;
            border-radius: 3px;
            width: 22px;
            height: 22px;
            cursor: pointer;
            font-size: 11px;
            padding: 0;
        `;
        closeBtn.onclick = () => toggleMenu();

        titleBar.appendChild(title);
        titleBar.appendChild(closeBtn);
        menuElement.appendChild(titleBar);

        // Toggle switches in compact grid
        const togglesGrid = document.createElement('div');
        togglesGrid.style.cssText = 'display: grid; grid-template-columns: repeat(2, 1fr); gap: 8px; margin-bottom: 15px;';

        const toggleSettings = [
            { name: 'Auto Insta', value: autoInstaEnabled, toggle: toggleAutoInsta, key: 'P' },
            { name: 'Auto Spike', value: autoSpikeSurroundEnabled, toggle: toggleAutoSpikeSurround, key: 'U' },
            { name: 'Auto Heal', value: autoHeal, toggle: toggleAutoHeal, key: 'H' },
            { name: 'Auto Mills', value: walkmillhaha, toggle: () => {
                walkmillhaha = !walkmillhaha;
                doNewSend(["6", ["mills: " + (walkmillhaha ? "ON" : "OFF")]]);
                updateMenu();
            }, key: 'M' },
        ];

        toggleSettings.forEach(setting => {
            const toggleItem = document.createElement('div');
            toggleItem.style.cssText = 'display: flex; justify-content: space-between; align-items: center;';

            const label = document.createElement('span');
            label.textContent = setting.name;
            label.style.cssText = 'color: #cccccc; font-size: 12px;';

            const toggleBtn = document.createElement('button');
            toggleBtn.textContent = setting.value ? 'ON' : 'OFF';
            toggleBtn.style.cssText = `
                background: ${setting.value ? '#00aa00' : '#550000'};
                color: white;
                border: none;
                border-radius: 3px;
                padding: 2px 10px;
                cursor: pointer;
                font-size: 11px;
                font-weight: bold;
                min-width: 40px;
            `;
            toggleBtn.onclick = setting.toggle;

            const keyHint = document.createElement('span');
            keyHint.textContent = setting.key;
            keyHint.style.cssText = 'color: #00ff00; font-size: 10px; margin-left: 5px;';

            toggleItem.appendChild(label);
            const rightSide = document.createElement('div');
            rightSide.style.cssText = 'display: flex; align-items: center;';
            rightSide.appendChild(toggleBtn);
            rightSide.appendChild(keyHint);
            toggleItem.appendChild(rightSide);

            togglesGrid.appendChild(toggleItem);
        });

        menuElement.appendChild(togglesGrid);

        // Settings section - ОСТАВИМ ВОЗМОЖНОСТЬ РЕГУЛИРОВКИ ДИСТАНЦИИ
        const controlsTitle = document.createElement('div');
        controlsTitle.textContent = 'Settings:';
        controlsTitle.style.cssText = 'color: #00ffff; font-weight: bold; font-size: 12px; margin: 10px 0 5px 0; border-top: 1px solid #333; padding-top: 8px;';
        menuElement.appendChild(controlsTitle);

        const createSlider = (labelText, value, min, max, step, onChange, keyText = '') => {
            const container = document.createElement('div');
            container.style.cssText = 'margin: 6px 0;';

            const labelRow = document.createElement('div');
            labelRow.style.cssText = 'display: flex; justify-content: space-between; margin-bottom: 3px;';

            const label = document.createElement('span');
            label.textContent = labelText;
            label.style.cssText = 'color: #aaaaaa; font-size: 11px;';

            const valueDisplay = document.createElement('span');
            valueDisplay.textContent = value + 'px';
            valueDisplay.style.cssText = 'color: #ffff00; font-size: 11px; font-weight: bold;';

            labelRow.appendChild(label);
            labelRow.appendChild(valueDisplay);
            container.appendChild(labelRow);

            const slider = document.createElement('input');
            slider.type = 'range';
            slider.min = min;
            slider.max = max;
            slider.step = step;
            slider.value = value;
            slider.style.cssText = 'width: 100%; height: 4px; margin: 2px 0;';

            slider.oninput = () => {
                valueDisplay.textContent = slider.value + 'px';
                onChange(parseInt(slider.value));
            };

            container.appendChild(slider);

            if (keyText) {
                const keyInfo = document.createElement('div');
                keyInfo.textContent = keyText;
                keyInfo.style.cssText = 'color: #00aa00; font-size: 9px; text-align: right; margin-top: 2px;';
                container.appendChild(keyInfo);
            }

            return container;
        };

        // Добавляем слайдер для дистанции авто-инсты
        menuElement.appendChild(createSlider(
            'Auto Insta Distance',
            autoInstaDistance,
            100,
            500,
            50,
            (val) => {
                autoInstaDistance = val;
                doNewSend(["6", ["Auto-Insta расстояние: " + val + "px"]]);
                updateMenu();
            },
            '[ ] to adjust'
        ));

        // Fixed distances info
        const fixedDistances = document.createElement('div');
        fixedDistances.style.cssText = 'margin-top: 10px; font-size: 10px; color: #888888;';
        fixedDistances.innerHTML = `
            <div>Auto Spike: ${spikeSurroundDistance}px</div>
        `;
        menuElement.appendChild(fixedDistances);

        // Hotkeys in compact view
        const hotkeysTitle = document.createElement('div');
        hotkeysTitle.textContent = 'Hotkeys:';
        hotkeysTitle.style.cssText = 'color: #ffaa00; font-weight: bold; font-size: 12px; margin: 12px 0 5px 0; border-top: 1px solid #333; padding-top: 8px;';
        menuElement.appendChild(hotkeysTitle);

        const hotkeysGrid = document.createElement('div');
        hotkeysGrid.style.cssText = 'display: grid; grid-template-columns: repeat(2, 1fr); gap: 5px; font-size: 10px;';

        const hotkeys = [
            'Shift - Insta',
            'R - Reverse Insta',
            'Space - Boost+Spike',
            'B - 4 Traps',
            'C - 4 Spikes',
            ', - AntiTrap',
            'F - Trap/Boost',
            'V - Spike',
            'N - Mill',
            '[ ] - AutoDist',
            'ESC - Menu'
        ];

        hotkeys.forEach(hotkey => {
            const item = document.createElement('div');
            item.textContent = hotkey;
            item.style.cssText = 'color: #cccccc; font-size: 10px; padding: 2px 4px; background: rgba(255,255,255,0.05); border-radius: 3px;';
            hotkeysGrid.appendChild(item);
        });

        menuElement.appendChild(hotkeysGrid);
    }

    function toggleMenu() {
        menuOpen = !menuOpen;
        if (menuElement) {
            menuElement.style.display = menuOpen ? 'block' : 'none';
        }
        if (menuBtn) {
            menuBtn.textContent = menuOpen ? '✖' : '⚙️';
            menuBtn.style.background = menuOpen ? 'rgba(100, 0, 0, 0.9)' : 'rgba(0, 0, 0, 0.9)';
        }
    }

    document.addEventListener("keydown", e => {
        if (document.activeElement.id.toLowerCase() === 'chatbox') return;
        const k = e.key.toLowerCase();
        if (keysPressed[k]) return;
        keysPressed[k] = true;

        //=== INSTAKILL NORMAL === (ТОЧНО КАК В x-RedDragon Client)
        if (e.keyCode == 16 && document.activeElement.id.toLowerCase() !== "chatbox") {
            storeEquip(0, 1);
            setTimeout(() => {
                autoaim = true;
                const primary = myPlayer.weapon;
                const secondary = getSecondaryWeaponIndex();

                doNewSend(["c", [0, 7, 0]]);
                doNewSend(["z", [primary, true]]);
                doNewSend(["F", [1]]);
                setTimeout(() => doNewSend(["F", [0]]), 25);

                setTimeout(() => {
                    doNewSend(["c", [0, 53, 0]]);
                    doNewSend(["z", [secondary, true]]);
                    doNewSend(["F", [1]]);
                    setTimeout(() => doNewSend(["F", [0]]), 25);

                    setTimeout(() => {
                        doNewSend(["c", [0, 6, 0]]);
                        doNewSend(["z", [primary, true]]);
                        doNewSend(["z", [primary, true]]);
                        autoaim = false;

                        setTimeout(() => {
                            storeEquip(11, 1);

                            if (secondary === 15) {
                                doNewSend(["z", [secondary, true]]);
                                setTimeout(() => doNewSend(["z", [primary, true]]), 1500);
                            } else if (secondary === 12) {
                                doNewSend(["z", [secondary, true]]);
                                setTimeout(() => doNewSend(["z", [primary, true]]), 1000);
                            } else if (secondary === 13) {
                                doNewSend(["z", [secondary, true]]);
                                setTimeout(() => doNewSend(["z", [primary, true]]), 400);
                            }
                        }, 170);
                    }, 120);
                }, 120);
            }, 120);
        }

        //=== INSTAKILL REVERSO ===
        if (e.keyCode == 82 && document.activeElement.id.toLowerCase() !== "chatbox") {
            performReverseInsta();
        }

        //=== BOOST SPIKE (Space) ===
        if (e.keyCode == 32 && document.activeElement.id.toLowerCase() !== "chatbox") {
            if (!nearestEnemy) return;

            // Быстрый буст+спайк
            doNewSend(["9", [nearestEnemyAngle]]);
            place(boostType, nearestEnemyAngle);
            place(spikeType, nearestEnemyAngle + Math.PI / 4);
            place(spikeType, nearestEnemyAngle - Math.PI / 4);

            if (!gInterval) {
                gInterval = setInterval(() => {
                    if (nearestEnemy) {
                        doNewSend(["9", [nearestEnemyAngle]]);
                        place(boostType, nearestEnemyAngle);
                    }
                }, 80);
            }
        }

        //=== AUTO INSTA TOGGLE ===
        if (k === 'p') {
            toggleAutoInsta();
        }

        //=== AUTO SPIKE SURROUND TOGGLE ===
        if (k === 'u') {
            toggleAutoSpikeSurround();
        }

        //=== AUTO HEAL TOGGLE ===
        if (k === 'h') {
            toggleAutoHeal();
        }

        //=== MENU TOGGLE ===
        if (e.keyCode === 27) {
            toggleMenu();
        }

        //=== AUTO INSTA DISTANCE CONTROL === (ТОЧНО КАК В x-RedDragon Client)
        if (k === '[' && autoInstaEnabled) {
            autoInstaDistance = Math.max(100, autoInstaDistance - 50);
            doNewSend(["6", ["Auto-Insta расстояние: " + autoInstaDistance]]);
            updateMenu();
        }
        if (k === ']' && autoInstaEnabled) {
            autoInstaDistance = Math.min(500, autoInstaDistance + 50);
            doNewSend(["6", ["Auto-Insta расстояние: " + autoInstaDistance]]);
            updateMenu();
        }

        //=== SPIKE DISTANCE CONTROL ===
        if (k === '.' && autoSpikeSurroundEnabled) {
            spikeSurroundDistance = Math.max(30, spikeSurroundDistance - 10);
            doNewSend(["6", ["Auto Spike расстояние: " + spikeSurroundDistance]]);
            updateMenu();
        }
        if (k === '/' && autoSpikeSurroundEnabled) {
            spikeSurroundDistance = Math.min(100, spikeSurroundDistance + 10);
            doNewSend(["6", ["Auto Spike расстояние: " + spikeSurroundDistance]]);
            updateMenu();
        }

        if (k === 'm') {
            walkmillhaha = !walkmillhaha;
            doNewSend(["6", ["Auto Mills: " + (walkmillhaha ? "ON" : "OFF")]]);
            updateMenu();
        }
        if (k === 'f') startPlacingStructure(k, boostType);
        if (k === 'v') startPlacingStructure(k, spikeType);
        if (k === 'n') startPlacingStructure(k, windmillType);
        if (k === 'g') startPlacingStructure(k, turretType);

        if (k === 'b') performBPlacement();
        if (k === 'c') placeFourSpikesUp();
    });

    document.addEventListener("keyup", e => {
        const k = e.key.toLowerCase();
        keysPressed[k] = false;
        stopPlacingStructure(k);

        if (e.keyCode == 32 && gInterval) { // Space released
            clearInterval(gInterval);
            gInterval = null;

            if (nearestEnemy) {
                doNewSend(["9", [myPlayer.dir]]);
                place(spikeType, nearestEnemyAngle - Math.PI / 4);
                place(spikeType, nearestEnemyAngle + Math.PI / 4);
            }
        }
    });

    if (!WebSocket.prototype.__originalSend) {
        WebSocket.prototype.__originalSend = WebSocket.prototype.send;
        WebSocket.prototype.send = function (data) {
            if (!ws) {
                ws = this;
                document.ws = this;
                ws.addEventListener("message", handleMessage);
            }
            return this.__originalSend(data);
        };
    }

    function handleMessage(m) {
        let temp = msgpack5.decode(new Uint8Array(m.data));
        let data = (temp.length > 1) ? [temp[0], ...temp[1]] : temp;
        if (!data) return;

        if (data[0] === "C" && myPlayer.id == null) myPlayer.id = data[1];

        if (data[0] === "a") {
            for (let i = 0; i < data[1].length / 13; i++) {
                let obj = data[1].slice(13 * i, 13 * i + 13);
                if (obj[0] === myPlayer.id) {
                    [myPlayer.x, myPlayer.y, myPlayer.dir, myPlayer.object, myPlayer.weapon,
                        , myPlayer.clan, myPlayer.isLeader, myPlayer.hat, myPlayer.accessory,
                        myPlayer.isSkull] = [obj[1], obj[2], obj[3], obj[4],
                        obj[5], obj[7], obj[8], obj[9], obj[10], obj[11]];
                } else enemiesNear.push(obj);
            }

            if (enemiesNear.length > 0) {
                nearestEnemy = enemiesNear.sort(
                    (a, b) => Math.hypot(a[1] - myPlayer.x, a[2] - myPlayer.y) - Math.hypot(b[1] - myPlayer.x, b[2] - myPlayer.y)
                )[0];
                nearestEnemyAngle = Math.atan2(nearestEnemy[2] - myPlayer.y, nearestEnemy[1] - myPlayer.x);

                if (autoSpikeSurroundEnabled) {
                    performSpikeSurround();
                }
            } else nearestEnemy = null;

            enemiesNear = [];

            if (automillx === false) automillx = myPlayer.x;
            if (automilly === false) automilly = myPlayer.y;

            if (myPlayeroldy !== myPlayer.y || myPlayeroldx !== myPlayer.x) {
                if (walkmillhaha) {
                    if (Math.sqrt(Math.pow(myPlayer.y - automilly, 2) + Math.pow(myPlayer.x - automillx, 2)) > 100) {
                        let angle = Math.atan2(myPlayeroldy - myPlayer.y, myPlayeroldx - myPlayer.x);
                        place(windmillType, angle + toRad(78));
                        place(windmillType, angle - toRad(78));
                        place(windmillType, angle);
                        doNewSend(["D", [Math.atan2(mouseY - height / 2, mouseX - width / 2)]]);
                        automillx = myPlayer.x;
                        automilly = myPlayer.y;
                    }
                }
                myPlayeroldx = myPlayer.x;
                myPlayeroldy = myPlayer.y;
            }
        }

        if (data[0] === "O" && data[1] === myPlayer.id) {
            gameTick = 0;
            lastDamageTick = 0;
            shame = 0;
            HP = 100;
            shameTime = 0;
            myPlayer.health = data[2];

            // Автохил при получении урона
            if (autoHeal && myPlayer.health < 100) {
                setTimeout(() => {
                    if (autoHeal && myPlayer.health < 100) {
                        doNewSend(["z", [0, null]]);
                        doNewSend(["F", [1, null]]);
                        doNewSend(["z", [1, null]]);
                        doNewSend(["F", [1, null]]);
                        doNewSend(["F", [0, null]]);
                    }
                }, 80);
            }
        }
    }

    setInterval(() => {
        if (autoaim && nearestEnemy) doNewSend(["D", [nearestEnemyAngle]]);
    }, 10);

    // 🧠 Anti-Rotación
    Object.defineProperty(Object.prototype, "turnSpeed", {
        get() { return 0; },
        set(_) {},
        configurable: true
    });

    // === AUTO GG ===
    let prevKillCount = 0;

    function initAutoGG() {
        const killCounter = document.getElementById("killCounter");
        if (!killCounter) {
            setTimeout(initAutoGG, 500);
            return;
        }

        const observer = new MutationObserver(() => {
            const count = parseInt(killCounter.innerText, 10) || 0;
            if (count > prevKillCount) {
                prevKillCount = count;
                doNewSend(["6", ["Nurbo mod gg"]]);
                setTimeout(() => {
                    doNewSend(["6", [``]]);
                }, 1000);
            }
        });

        observer.observe(killCounter, { childList: true, characterData: true, subtree: true });
    }

    initAutoGG();

    // === FASTBREAK ===
    let rightClickAttackInterval = null;
    let rightClickHeld = false;
    let isPlacingStructure = false;
    let attackPausedForPlacement = false;

    function ensureCorrectWeapon() {
        const primary = myPlayer.weapon;
        const secondary = getSecondaryWeaponIndex();

        let correctWeapon = (secondary === 10) ? secondary : primary;

        if (myPlayer.weapon !== correctWeapon) {
            doNewSend(["z", [correctWeapon, true]]);
        }
    }

    function startAttackLoop() {
        if (rightClickAttackInterval) return;

        rightClickAttackInterval = setInterval(() => {
            ensureCorrectWeapon();
            doNewSend(["c", [0, 40, 0]]);
            doNewSend(["F", [1]]);
            setTimeout(() => doNewSend(["F", [0]]), 8);
        }, 50);
    }

    function stopAttackLoop() {
        clearInterval(rightClickAttackInterval);
        rightClickAttackInterval = null;
    }

    document.addEventListener("mousedown", function (e) {
        if (e.button === 2 && !rightClickHeld) {
            rightClickHeld = true;
            doNewSend(["c", [0, 40, 0]]);

            setTimeout(() => {
                if (rightClickHeld && !isPlacingStructure) {
                    startAttackLoop();
                }
            }, 50);
        }
    });

    document.addEventListener("mouseup", function (e) {
        if (e.button === 2 && rightClickHeld) {
            rightClickHeld = false;
            stopAttackLoop();
            doNewSend(["F", [0]]);
            setTimeout(() => doNewSend(["c", [0, 6, 0]]), 80);
        }
    });

    const originalPlace = place;
    place = function (...args) {
        isPlacingStructure = true;

        if (rightClickAttackInterval) {
            attackPausedForPlacement = true;
            stopAttackLoop();
        }

        originalPlace.apply(this, args);

        setTimeout(() => {
            isPlacingStructure = false;
            if (rightClickHeld && attackPausedForPlacement) {
                attackPausedForPlacement = false;
                startAttackLoop();
            }
        }, 80);
    };

    const oldStoreEquip = window.storeEquip;
    window.storeEquip = function (id, slot) {
        oldStoreEquip.apply(this, arguments);

        if (rightClickHeld) {
            ensureCorrectWeapon();
        }
    };

    const oldEquipWeapon = window.equipWeapon;
    window.equipWeapon = function (id) {
        oldEquipWeapon.apply(this, arguments);

        if (rightClickHeld) {
            ensureCorrectWeapon();
        }
    };

    // 🎩 AutoBiomeHatController
    function autoBiomeHatController() {
        let normalHat = 12;
        let currentHat = null;
        let overridePause = false;
        let resumeTimeout = null;
        const movementKeys = new Set();
        const overrideKeys = new Set([16, "r", " "]);

        function setHat(id) {
            if (id !== currentHat && myPlayer && myPlayer.id != null) {
                currentHat = id;
                doNewSend(["c", [0, id, 0]]);

                let accessoryId = null;
                if (id === 6) {
                    accessoryId = 0;
                } else if ([15, 31, 12].includes(id)) {
                    accessoryId = 11;
                }

                if (accessoryId !== null) {
                    [30, 60, 90].forEach(delay => {
                        setTimeout(() => {
                            storeEquip(accessoryId, 1);
                        }, delay);
                    });
                }
            }
        }

        function updateBiomeHat() {
            if (!myPlayer || typeof myPlayer.y !== "number") return;
            if (myPlayer.y < 2400) normalHat = 15;
            else if (myPlayer.y > 6850 && myPlayer.y < 7550) normalHat = 31;
            else normalHat = 12;
        }

        function updateHatLogic() {
            if (overridePause) return;
            updateBiomeHat();
            if (movementKeys.size > 0) {
                setHat(normalHat);
            } else {
                setHat(6);
            }
        }

        function pauseOverride() {
            overridePause = true;
            if (resumeTimeout) clearTimeout(resumeTimeout);
        }

        function resumeOverride() {
            if (resumeTimeout) clearTimeout(resumeTimeout);
            resumeTimeout = setTimeout(() => {
                overridePause = false;
                updateHatLogic();
            }, 300);
        }

        document.addEventListener("keydown", e => {
            const key = e.key.toLowerCase();
            if (["w", "a", "s", "d", "arrowup", "arrowdown", "arrowleft", "arrowright"].includes(key)) {
                if (!movementKeys.has(key)) {
                    movementKeys.add(key);
                    updateHatLogic();
                }
            }
            if (overrideKeys.has(key)) pauseOverride();
        });

        document.addEventListener("keyup", e => {
            const key = e.key.toLowerCase();
            if (movementKeys.delete(key)) updateHatLogic();
            if (overrideKeys.has(key)) resumeOverride();
        });

        document.addEventListener("mousedown", e => {
            if (e.button === 0 || e.button === 2) pauseOverride();
        });

        document.addEventListener("mouseup", e => {
            if (e.button === 0 || e.button === 2) resumeOverride();
        });

        setInterval(() => {
            if (!overridePause) updateHatLogic();
        }, 200);
    }

    autoBiomeHatController();

    // === ANTI TRAP ===
    let antiTrap = false;
    let intrap = false;
    let trapAngle = null;
    let trapId = null;

    document.addEventListener("keydown", e => {
        if (document.activeElement.id.toLowerCase() === 'chatbox') return;
        if (e.key === ",") {
            antiTrap = !antiTrap;
            doNewSend(["6", ["AntiTrap: " + (antiTrap ? "ON" : "OFF")]]);
        }
    });

    function handleTrapData(node) {
        for (let i = 0; i < node[1].length / 8; i++) {
            let obj = node[1].slice(8 * i, 8 * i + 8);
            if (obj[6] === 15 && obj[7] !== myPlayer.id && obj[7] !== myPlayer.clan) {
                let dx = obj[1] - myPlayer.x;
                let dy = obj[2] - myPlayer.y;
                let dist = Math.sqrt(dx * dx + dy * dy);
                if (dist < 90) {
                    intrap = true;
                    trapAngle = Math.atan2(dy, dx);
                    trapId = obj[0];

                }
            }
        }
    }

    const oldHandleMessage = handleMessage;
    handleMessage = function (m) {
        let temp = msgpack5.decode(new Uint8Array(m.data));
        let data = (temp.length > 1) ? [temp[0], ...temp[1]] : temp;
        if (!data) return;

        if (data[0] === "H") handleTrapData(data);

        if (data[0] === "Q" && intrap && trapId === data[1]) {
            intrap = false;
            trapId = null;
            setTimeout(() => doNewSend(["c", [0, 6, 0]]), 80);

        }

        oldHandleMessage(m);
    };

    function hookEquipFunctions() {
        if (typeof window.storeEquip === "function" && typeof window.equipWeapon === "function") {
            const oldStoreEquip = window.storeEquip;
            window.storeEquip = function (id, slot) {
                const result = oldStoreEquip.apply(this, arguments);
                if (antiTrap && intrap) ensureCorrectWeapon();
                return result;
            };

            const oldEquipWeapon = window.equipWeapon;
            window.equipWeapon = function (id) {
                const result = oldEquipWeapon.apply(this, arguments);
                if (antiTrap && intrap) ensureCorrectWeapon();
                return result;
            };
        } else {
            setTimeout(hookEquipFunctions, 100);
        }
    }
    hookEquipFunctions();

    setInterval(() => {
        if (!antiTrap || !intrap) return;
        if (!ws || ws.readyState !== WebSocket.OPEN) return;

        let oppositeAngle = trapAngle + Math.PI;
        place(spikeType, oppositeAngle);
        ensureCorrectWeapon();

        doNewSend(["D", [trapAngle]]);
        doNewSend(["c", [0, 40, 0]]);
        doNewSend(["F", [1, trapAngle]]);
        setTimeout(() => doNewSend(["F", [0, trapAngle]]), 12);
    }, 250);

    // Create menu on load
    setTimeout(() => {
        if (document.getElementById('nurbo-mod-menu-btn')) return;

        createMenu();

        // Add menu button
        menuBtn = document.createElement('button');
        menuBtn.id = 'nurbo-mod-menu-btn';
        menuBtn.textContent = '⚙️';
        menuBtn.style.cssText = `
            position: fixed;
            top: 10px;
            left: 10px;
            background: rgba(0, 0, 0, 0.9);
            color: #00ff00;
            border: 1px solid #00ff00;
            border-radius: 4px;
            width: 30px;
            height: 30px;
            font-size: 16px;
            cursor: pointer;
            z-index: 9998;
            display: flex;
            align-items: center;
            justify-content: center;
            box-shadow: 0 0 8px rgba(0, 255, 0, 0.3);
            transition: all 0.2s;
            padding: 0;
        `;
        menuBtn.onmouseover = () => {
            menuBtn.style.background = 'rgba(0, 80, 0, 0.9)';
            menuBtn.style.transform = 'scale(1.05)';
        };
        menuBtn.onmouseout = () => {
            menuBtn.style.background = menuOpen ? 'rgba(100, 0, 0, 0.9)' : 'rgba(0, 0, 0, 0.9)';
            menuBtn.style.transform = 'scale(1)';
        };
        menuBtn.onclick = () => toggleMenu();
        document.body.appendChild(menuBtn);
    }, 1500);
})();

// Остальные части скрипта (WeaponReloadPrediction, HealBarsBuildings, AutoVerifity, AutoReloadWeb) остаются без изменений
//WeaponReloadPrediction
(function () {
	"use strict";

	let ws;
	const msgpack = window.msgpack;

	WebSocket.prototype._send = WebSocket.prototype.send;
	WebSocket.prototype.send = function (m) {
		if (!ws) {
			ws = this;
			window.ws = this;
		}
		this._send(m);
	};

	function modifyCanvasRenderingContext2D() {
		if (CanvasRenderingContext2D.prototype.roundRect) {
			CanvasRenderingContext2D.prototype.roundRect = function (x, y, w, h) {
				this.beginPath();
				this.rect(x, y, w, h);
				this.closePath();
				return this;
			};
		}
	}

	if (window.jQuery) {
		$(document).ready(modifyCanvasRenderingContext2D);
	} else {
		window.addEventListener("load", modifyCanvasRenderingContext2D);
	}

	window.Cow.setCodec(msgpack);

	window.Cow.addRender("global", () => {
		const ctx = window.Cow.renderer.context;

		const hbWidth = window.config?.healthBarWidth ?? 50;
		const hbPad = window.config?.healthBarPad ?? 5;
		const nameY = window.config?.nameY ?? 0;

		const width = hbWidth / 2 - hbPad / 2;
		const height = 14;

		window.Cow.playersManager.eachVisible(player => {
			if (!player || !player.alive) return;

			const yOffset = player.renderY + player.scale + nameY - 5;

			const primaryReload = player.reloads?.primary
				? Math.min(player.reloads.primary.count / player.reloads.primary.max, 1)
				: 0;

			const secondaryReload = player.reloads?.secondary
				? Math.min(player.reloads.secondary.count / player.reloads.secondary.max, 1)
				: 0;

			const barColor = player.isAlly ? "#8ecc51" : "#cc5151";

			ctx.save();

			ctx.fillStyle = "#3d3f42";
			ctx.fillRect(
				player.renderX - width * 1.19 - width - hbPad,
				yOffset - height / 2,
				2 * width + 2 * hbPad,
				height
			);

			ctx.fillStyle = barColor;
			ctx.fillRect(
				player.renderX - width * 1.19 - width,
				yOffset - height / 2 + hbPad,
				2 * width * primaryReload,
				height - 2 * hbPad
			);

			ctx.fillStyle = "#3d3f42";
			ctx.fillRect(
				player.renderX + width * 1.19 - width - hbPad,
				yOffset - height / 2,
				2 * width + 2 * hbPad,
				height
			);

			ctx.fillStyle = barColor;
			ctx.fillRect(
				player.renderX + width * 1.19 - width,
				yOffset - height / 2 + hbPad,
				2 * width * secondaryReload,
				height - 2 * hbPad
			);

			ctx.restore();
		});
	});
})();

//HealBarsBuildings
(function () {
	"use strict";

	function init() {
		if (!window.Cow) {
			setTimeout(init, 100);
			return;
		}

		const Cow = window.Cow;

		function drawHP(ctx, o) {
			const max = o.maxHealth || o.maxHP || 100;
			const cur = o.health || o.hp || max;
			if (cur >= max) return;

			const hp = cur / max;
			const r = 20;
			const w = 8;
			const a = hp * Math.PI * 2;

			ctx.save();
			ctx.translate(o.renderX || o.x, o.renderY || o.y);

			ctx.strokeStyle = "#2b0000";
			ctx.lineWidth = w;
			ctx.beginPath();
			ctx.arc(0, 0, r, 0, Math.PI * 2);
			ctx.stroke();

			let hpColor;
			if (hp > 0.6) hpColor = "#00aa00";
			else if (hp > 0.3) hpColor = "#ffaa00";
			else hpColor = "#ff0000";

			ctx.strokeStyle = hpColor;
			ctx.lineWidth = w - 2;
			ctx.lineCap = "round";
			ctx.beginPath();
			ctx.arc(0, 0, r, 0, a);
			ctx.stroke();

			if (hp < 0.3) {
				ctx.fillStyle = "#ffffff";
				ctx.font = "bold 10px Arial";
				ctx.textAlign = "center";
				ctx.textBaseline = "middle";
				ctx.fillText(Math.round(hp * 100) + "%", 0, 0);
			}

			ctx.restore();
		}

		function render() {
			if (!Cow.player) return;
			const ctx = Cow.renderer.context;

			Cow.objectsManager.eachVisible((o) => {
				if (
					(o.health == null && o.hp == null) ||
					(o.maxHealth == null && o.maxHP == null)
				) return;

				const isEnemy = o.ownerId && o.ownerId !== Cow.player.id;
				if (isEnemy || (o.health || o.hp) < (o.maxHealth || o.maxHP)) {
					drawHP(ctx, o);
				}
			});
		}

		if (Cow.addRender) {
			Cow.addRender("hp-circle-red", render);
		} else {
			(function loop() {
				render();
				requestAnimationFrame(loop);
			})();
		}
	}

	if (document.readyState === "complete") init();
	else window.addEventListener("load", init);
})();

//AutoVerifity
(function () {
    'use strict';

    let ws = null;
    let { msgpack } = window;
    let playerID = null;
    let myPlayer = {
        id: null, x: null, y: null, dir: null, object: null, weapon: null,
        clan: null, isLeader: null, maxXP: 300, XP: 0, age: 1,
        hat: null, accessory: null, isSkull: null, maxHealth: 100,
        health: 100
    };
    let players = [], enemy = [], nearestEnemy = {};
    let gameCanvas = document.getElementById("gameCanvas");
    let width = window.innerWidth;
    let height = window.innerHeight;
    let mouseX, mouseY;

    const sendPacket = (packet, ...data) => {
        if (ws && ws.readyState === WebSocket.OPEN) {
            ws.send(new Uint8Array(msgpack.encode([packet, data])));
        }
    };

    const updatePlayers = data => {
        players = [];
        for (let i = 0; i < data[1].length / 13; i++) {
            const playerInfo = data[1].slice(i * 13, i * 13 + 13);
            if (playerInfo[0] === myPlayer.id) {
                myPlayer.x = playerInfo[1];
                myPlayer.y = playerInfo[2];
                myPlayer.dir = playerInfo[3];
                myPlayer.object = playerInfo[4];
                myPlayer.weapon = playerInfo[5];
                myPlayer.clan = playerInfo[7];
                myPlayer.isLeader = playerInfo[8];
                myPlayer.hat = playerInfo[9];
                myPlayer.accessory = playerInfo[10];
                myPlayer.isSkull = playerInfo[11];
            } else {
                players.push({
                    id: playerInfo[0],
                    x: playerInfo[1],
                    y: playerInfo[2],
                    dir: playerInfo[3],
                    object: playerInfo[4],
                    weapon: playerInfo[5],
                    clan: playerInfo[7],
                    isLeader: playerInfo[8],
                    hat: playerInfo[9],
                    accessory: playerInfo[10]
                });
            }
        }
    };

    const updateHealth = (health, playerIDCheck) => {
        if (myPlayer.id === playerIDCheck) {
            myPlayer.health = health;
        }
    };

    const handleMessage = (message) => {
        const decoded = msgpack.decode(new Uint8Array(message.data));
        const data = Array.isArray(decoded) && decoded.length > 1 ? [decoded[0], ...decoded[1]] : decoded;
        if (!data) return;
        const type = data[0];
        if (type === "C" && myPlayer.id == null) {
            myPlayer.id = data[1];
            console.log("[Nurbo Mod] Player ID:", myPlayer.id);
        }
        if (type === "a") updatePlayers(data);
        if (type === "O") updateHealth(data[2], data[1]);
    };

    const socketFound = (sock) => {
        sock.addEventListener("message", handleMessage);
        if (gameCanvas) {
            gameCanvas.addEventListener("mousemove", ({ x, y }) => {
                mouseX = x;
                mouseY = y;
            });
        }
        window.addEventListener("resize", () => {
            width = window.innerWidth;
            height = window.innerHeight;
        });
    };

    WebSocket.prototype.oldSend = WebSocket.prototype.send;
    WebSocket.prototype.send = function (m) {
        if (!ws) {
            ws = this;
            document.websocket = this;
            socketFound(this);
            console.log("[Nurbo Mod] WebSocket intercepted");
        }
        this.oldSend(m);
    };

    const altchaCheck = setInterval(() => {
        let altcha = document.getElementById('altcha');
        let altchaBox = document.getElementById('altcha_checkbox');

        if (altcha && altchaBox) {
            altcha.style.display = 'none';
            altcha.style.opacity = '0';
            altcha.style.pointerEvents = 'none';
            altchaBox.checked = true;

            altchaBox.dispatchEvent(new Event('change', { bubbles: true }));
            altchaBox.dispatchEvent(new Event('click', { bubbles: true }));

            setTimeout(() => {
                if (!altchaBox.checked) {
                    altchaBox.checked = true;
                    altchaBox.click();
                }
            }, 500);

            clearInterval(altchaCheck);
            console.log("[Nurbo Mod] Altcha solved automatically");
        }

        const captchaElements = document.querySelectorAll('[class*="captcha"], [id*="Captcha"], [class*="verif"]');
        captchaElements.forEach(el => {
            if (el && el.style) {
                el.style.display = 'none';
                el.style.opacity = '0';
                el.style.pointerEvents = 'none';
            }
        });
    }, 300);

    const originalAlert = window.alert;
    window.alert = function(message) {
        console.log("[Nurbo Mod] Alert blocked:", message);
        if (typeof message === 'string' && (
            message.toLowerCase().includes('verify') ||
            message.toLowerCase().includes('captcha') ||
            message.toLowerCase().includes('robot') ||
            message.toLowerCase().includes('human')
        )) {
            return;
        }
        return originalAlert.apply(this, arguments);
    };
})();

//AutoReloadWeb
(function() {
    "use strict";

    function delay(ms) {
        return new Promise(resolve => setTimeout(resolve, ms));
    }

    async function refreshPage() {
        console.log("[Nurbo Mod] Auto-reloading page...");
        await delay(1200);
        window.onbeforeunload = null;
        location.reload();
    }

    function interceptProperty(target, propName, onSetCallback) {
        const hiddenKey = Symbol(propName);
        Object.defineProperty(target, propName, {
            get() {
                return this[hiddenKey];
            },
            set(value) {
                onSetCallback(this, hiddenKey, value);
            },
            configurable: true
        });
    }

    function wrapFunction(originalFunc, wrapper) {
        return new Proxy(originalFunc, {
            apply(target, thisArg, args) {
                return wrapper.call(thisArg, target, args);
            }
        });
    }

    interceptProperty(Object.prototype, "errorCallback", (obj, key, val) => {
        obj[key] = val;
        if (typeof val !== "function") return;
        obj[key] = wrapFunction(val, (target, args) => {
            console.log("[Nurbo Mod] errorCallback triggered, auto-reloading");
            window.alert = () => {};
            refreshPage();
            return target.apply(this, args);
        });
    });

    ["onclose", "onerror"].forEach(eventName => {
        const descriptor = Object.getOwnPropertyDescriptor(WebSocket.prototype, eventName);
        if (!descriptor || !descriptor.set) return;

        Object.defineProperty(WebSocket.prototype, eventName, {
            set(handler) {
                const wrappedHandler = wrapFunction(handler, (target, args) => {
                    console.log(`[Nurbo Mod] WebSocket ${eventName} triggered, auto-reloading`);
                    refreshPage();
                    return target.apply(this, args);
                });
                descriptor.set.call(this, wrappedHandler);
            },
            configurable: true
        });
    });

    window.addEventListener('error', function(e) {
        if (e.message && (
            e.message.includes('WebSocket') ||
            e.message.includes('connection') ||
            e.message.includes('network')
        )) {
            console.log("[Nurbo Mod] Page error detected, auto-reloading");
            setTimeout(refreshPage, 1000);
        }
    });

    window.addEventListener('unhandledrejection', function(e) {
        if (e.reason && typeof e.reason === 'string' && (
            e.reason.includes('WebSocket') ||
            e.reason.includes('network')
        )) {
            console.log("[Nurbo Mod] Unhandled promise rejection, auto-reloading");
            setTimeout(refreshPage, 1000);
        }
    });

    setInterval(() => {
        if (document.websocket && document.websocket.readyState !== WebSocket.OPEN) {
            console.log("[Nurbo Mod] WebSocket not open, checking...");
            setTimeout(() => {
                if (document.websocket && document.websocket.readyState !== WebSocket.OPEN) {
                    console.log("[Nurbo Mod] WebSocket still closed, reloading");
                    refreshPage();
                }
            }, 2000);
        }
    }, 10000);

})();