Capture Client v1.0

Access local variables and more fun features. Shift + L for variable manager, Shift + Y for tweaks. Hook by ginger

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey, Greasemonkey или Violentmonkey.

Для установки этого скрипта вам необходимо установить расширение, такое как Tampermonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Userscripts.

Чтобы установить этот скрипт, сначала вы должны установить расширение браузера, например Tampermonkey.

Чтобы установить этот скрипт, вы должны установить расширение — менеджер скриптов.

(у меня уже есть менеджер скриптов, дайте мне установить скрипт!)

Advertisement:

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

(у меня уже есть менеджер стилей, дайте мне установить скрипт!)

Advertisement:

// ==UserScript==
// @name         Capture Client v1.0
// @version      1.0
// @description  Access local variables and more fun features. Shift + L for variable manager, Shift + Y for tweaks. Hook by ginger
// @author       Цветочек Кактус (timofeycacti) & AI
// @match        https://*.bloxd.io/*
// @namespace    CaptureClient
// @license      CC-BY-2.0
// @icon         https://i.postimg.cc/XJFnxv3m/Capture-Client-v1-(3).png
// @grant        none
// ==/UserScript==

(function() {
    'use strict';

    let font = document.createElement('link');
    font.href = 'https://fonts.googleapis.com/css2?family=Lobster&display=swap';
    font.rel = 'stylesheet';
    document.head.appendChild(font);

    let style = document.createElement('style');
    style.textContent = `
    @keyframes spin{to{transform:rotate(360deg)}}
    .Crosshair{display:inline-block;animation:spin 1s linear infinite}
    @keyframes hudRotate { from { background-position: 0% 50%; } to { background-position: 100% 50%; } }
    @keyframes flash { 0%, 100% { color:#FFF176 } 50% { color:#660000 } }
    .changed { animation: flash 0.4s ease }
    .vm-item { padding:3px 4px; cursor:pointer; color:#FFF176; white-space:pre-wrap; word-break:break-word; user-select: none; }
    .vm-item:hover { color:#FFFFFF; background:rgba(255,255,255,0.08); }
    .btn { background: rgba(255, 241, 118, 0.15); color: #FFF176; border: 1px solid #FFF176; padding: 5px; margin: 5px 0; text-align: center; cursor: pointer; font-family: monospace; font-weight: bold; user-select: none; transition: background 0.2s, color 0.2s; }
    .btn:hover { background: #FFF176; color: #330000; }
    .btn.active { background: rgba(76, 175, 80, 0.3); color: #4CAF50; border-color: #4CAF50; }
    .btn.active:hover { background: #4CAF50; color: #fff; border-color: #4CAF50; }
    .vm-search-box { display: flex; padding: 4px; background: rgba(0,0,0,0.4); border-bottom: 1px solid rgba(255, 241, 118, 0.3); gap: 4px; }
    .vm-input { flex: 1; background: rgba(0,0,0,0.6); border: 1px solid #FFF176; color: #FFF176; font-family: monospace; font-size: 12px; padding: 2px 4px; outline: none; }
    .vm-checkbox-label { color: #FFF176; font-family: monospace; font-size: 11px; display: flex; align-items: center; gap: 3px; cursor: pointer; user-select: none; }
    .vm-checkbox-label input { cursor: pointer; accent-color: #FFF176; margin: 0; }
    `;
    document.head.appendChild(style);

    let vmOpen = false, vmBox, vmPath = [], vmCurrent;
    let tweaksOpen = false, tweaksBox;
    let vmSearchQuery = '', vmDeepSearchEnabled = false;
    let tracked = JSON.parse(localStorage.getItem('capture_tracked') || '{}');
    let lastValues = {};

    function saveTracked() {
        localStorage.setItem('capture_tracked', JSON.stringify(tracked));
    }

    function makeDraggable(header, box) {
        let isDown = false, ox = 0, oy = 0;
        header.addEventListener('mousedown', e => {
            isDown = true;
            ox = e.clientX - box.offsetLeft;
            oy = e.clientY - box.offsetTop;
        });
        document.addEventListener('mousemove', e => {
            if (isDown) {
                box.style.left = (e.clientX - ox) + 'px';
                box.style.top = (e.clientY - oy) + 'px';
            }
        });
        document.addEventListener('mouseup', () => { isDown = false; });
    }

    let trackerBox = document.createElement('div');
    Object.assign(trackerBox.style, {
        position: 'fixed', right: '10px', bottom: '10px', color: '#FFF176',
        fontFamily: 'monospace', fontSize: '12px', zIndex: 99999,
        textAlign: 'right', pointerEvents: 'none', maxWidth: '300px', wordBreak: 'break-word'
    });
    document.body.appendChild(trackerBox);

    function getSafeValue(obj, key) {
        try { return (obj && typeof obj === 'object') ? obj[key] : undefined; } catch { return undefined; }
    }

    setInterval(() => {
        trackerBox.innerHTML = '';
        Object.entries(tracked).forEach(([pathStr, path]) => {
            try {
                let val = path.reduce((o, k) => getSafeValue(o, k), window.Captured);
                let line = document.createElement('div');
                line.textContent = `${pathStr}: ${val}`;
                if (lastValues[pathStr] !== undefined && lastValues[pathStr] !== val) {
                    line.classList.add('changed');
                }
                lastValues[pathStr] = val;
                trackerBox.appendChild(line);
            } catch {}
        });
    }, 200);

    function setValue(path, val) {
        try {
            let obj = path.slice(0, -1).reduce((o, k) => getSafeValue(o, k), window.Captured);
            let key = path[path.length - 1];
            obj[key] = val;
            if (obj[key] !== val) {
                Object.defineProperty(obj, key, { value: val, writable: true, configurable: true, enumerable: true });
            }
        } catch {}
    }

    function createVmItem(displayKey, value, itemPath) {
        let item = document.createElement('div');
        item.className = 'vm-item';
        let pathStr = itemPath.join('.');

        item.textContent = value === null ? `${displayKey} : null` : typeof value === 'object' ? `${displayKey} >` : `${displayKey} : ${value}`;

        let handleTrack = (e) => {
            e.preventDefault(); e.stopPropagation();
            tracked[pathStr] ? delete tracked[pathStr] : tracked[pathStr] = itemPath;
            saveTracked();
        };

        item.onclick = (e) => {
            if (e.shiftKey) return handleTrack(e);
            e.preventDefault(); e.stopPropagation();

            if (value && typeof value === 'object') {
                vmPath = [...itemPath];
                vmUpdate();
            } else if (typeof value === 'boolean') {
                setValue(itemPath, !value);
                vmUpdate();
            } else {
                let input = prompt(`Set ${pathStr}`, value);
                if (input !== null) {
                    setValue(itemPath, typeof value === 'number' ? Number(input) : input);
                    vmUpdate();
                }
            }
        };

        item.oncontextmenu = e => { if (e.shiftKey) handleTrack(e); };
        return item;
    }

    function vmRender() {
        let box = vmBox._content;
        box.innerHTML = '';

        if (vmPath.length) {
            let back = document.createElement('div');
            back.textContent = '[..]';
            back.className = 'vm-item';
            back.onclick = (e) => { e.preventDefault(); e.stopPropagation(); vmPath.pop(); vmUpdate(); };
            box.appendChild(back);
        }

        let query = vmSearchQuery.toLowerCase().trim();

        if (query && vmDeepSearchEnabled) {
            let results = [], visited = new Set();
            (function search(obj, currentFullPath, depth = 0) {
                if (depth > 4 || !obj || typeof obj !== 'object' || visited.has(obj)) return;
                visited.add(obj);
                try {
                    Object.keys(obj).forEach(k => {
                        let p = [...currentFullPath, k];
                        if (k.toLowerCase().includes(query)) results.push({ keyPath: p, val: getSafeValue(obj, k) });
                        if (obj[k] && typeof obj[k] === 'object') search(obj[k], p, depth + 1);
                    });
                } catch {}
            })(vmCurrent, [...vmPath]);

            if (!results.length) {
                let empty = document.createElement('div');
                Object.assign(empty, { className: 'vm-item', textContent: 'No results found...' });
                empty.style.color = '#660000';
                box.appendChild(empty);
            } else {
                results.forEach(res => box.appendChild(createVmItem(res.keyPath.slice(vmPath.length).join('.'), res.val, res.keyPath)));
            }
        } else {
            Object.keys(vmCurrent || {}).forEach(k => {
                if (!query || k.toLowerCase().includes(query)) {
                    box.appendChild(createVmItem(k, getSafeValue(vmCurrent, k), [...vmPath, k]));
                }
            });
        }
    }

    function vmUpdate() {
        try { vmCurrent = vmPath.reduce((o, k) => getSafeValue(o, k), window.Captured); }
        catch { vmPath = []; vmCurrent = window.Captured; }
        vmRender();
    }

    function setupUiIsolation(el) {
        ['mousedown', 'mouseup', 'click', 'contextmenu'].forEach(evt => {
            el.addEventListener(evt, e => {
                if (!e.target.closest('[style*="cursor: move"]') && !e.shiftKey) e.stopPropagation();
            });
        });
    }

    function vmToggle() {
        vmOpen = !vmOpen;
        if (vmOpen) {
            vmBox = document.createElement('div');
            Object.assign(vmBox.style, {
                position: 'fixed', top: '20px', left: '20px', width: '320px', color: '#FFF176', zIndex: 99999,
                border: '2px solid #FFF176', background: 'linear-gradient(270deg,#330000,#000,#330000)',
                backgroundSize: '400% 400%', animation: 'hudRotate 8s linear infinite', display: 'flex', flexDirection: 'column'
            });

            let header = document.createElement('div');
            header.textContent = 'Capture Client';
            Object.assign(header.style, { background: '#FFF176', color: '#330000', padding: '5px', cursor: 'move', textAlign: 'center', fontFamily: 'Lobster' });

            let searchBar = document.createElement('div');
            searchBar.className = 'vm-search-box';

            let input = document.createElement('input');
            Object.assign(input, { type: 'text', className: 'vm-input', placeholder: 'Search properties...', value: vmSearchQuery });
            ['keydown', 'keyup', 'keypress'].forEach(evt => input.addEventListener(evt, e => e.stopPropagation()));
            input.addEventListener('input', e => { vmSearchQuery = e.target.value; vmRender(); });

            let label = document.createElement('label');
            label.className = 'vm-checkbox-label';
            let checkbox = document.createElement('input');
            Object.assign(checkbox, { type: 'checkbox', checked: vmDeepSearchEnabled });
            checkbox.addEventListener('change', e => { vmDeepSearchEnabled = e.target.checked; vmRender(); });
            label.append(checkbox, "Deep");
            searchBar.append(input, label);

            let content = document.createElement('div');
            Object.assign(content.style, { padding: '5px', overflow: 'auto', maxHeight: '320px', fontFamily: 'monospace' });

            vmBox.append(header, searchBar, content);
            document.body.appendChild(vmBox);
            vmBox._content = content;
            vmPath = []; vmUpdate();
            makeDraggable(header, vmBox);
            setupUiIsolation(vmBox);
        } else vmBox.remove();
    }

    const tweaksConfig = {
        allCraft: {
            name: 'All Craft',
            type: 'action',
            callback: () => {
                try {
                    Object.values(window.Captured.bloxd.craftingManager.playerRecipes[1] || {}).forEach(arr => {
                        if (Array.isArray(arr)) arr.forEach(o => { if (o) delete o.station; });
                    });
                } catch {}
            }
        },
        defineAll: {
            name: 'Define All',
            type: 'action',
            callback: () => {
                try {
                    let visited = new Set();
                    let found = (function search(obj, depth = 0) {
                        if (depth > 4 || !obj || typeof obj !== 'object' || visited.has(obj)) return null;
                        visited.add(obj);
                        if (obj.hasOwnProperty('playerZoom')) return obj;
                        for (let key of Object.keys(obj)) {
                            try {
                                let res = search(obj[key], depth + 1);
                                if (res) return res;
                            } catch {}
                        }
                        return null;
                    })(window.Captured);
                    if (found) {
                        window.Captured.cBloxdStats = found;
                        if (vmOpen) vmUpdate();
                    }
                } catch {}
            }
        },
        resetAcc: {
            name: 'Reset Acc',
            type: 'action',
            callback: () => {
                try {
                    let domains = [".bloxd.io", location.hostname, ""];
                    domains.forEach(d => {
                        document.cookie = `__Secure-3PSIDMC=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;${d ? ` domain=${d};` : ''} Secure; SameSite=None`;
                    });
                    location.reload();
                } catch {}
            }
        }
    };

    function renderTweaks() {
        let content = tweaksBox._content;
        content.innerHTML = '';
        Object.keys(tweaksConfig).forEach(key => {
            let tweak = tweaksConfig[key];
            let btn = document.createElement('div');
            btn.className = 'btn';
            btn.textContent = tweak.type === 'boolean' ? `${tweak.name}: ${tweak.enabled ? 'ON' : 'OFF'}` : tweak.name;
            if (tweak.type === 'boolean' && tweak.enabled) btn.classList.add('active');

            btn.onclick = (e) => {
                e.preventDefault(); e.stopPropagation();
                if (tweak.type === 'boolean') {
                    tweak.enabled = !tweak.enabled;
                    tweak.callback(tweak.enabled);
                    renderTweaks();
                } else tweak.callback();
            };
            content.appendChild(btn);
        });
    }

    function tweaksToggle() {
        tweaksOpen = !tweaksOpen;
        if (tweaksOpen) {
            tweaksBox = document.createElement('div');
            Object.assign(tweaksBox.style, {
                position: 'fixed', top: '20px', right: '20px', width: '220px', color: '#FFF176', zIndex: 99999,
                border: '2px solid #FFF176', background: 'linear-gradient(270deg,#330000,#000,#330000)',
                backgroundSize: '400% 400%', animation: 'hudRotate 8s linear infinite', display: 'flex', flexDirection: 'column'
            });

            let header = document.createElement('div');
            header.textContent = 'Tweaks';
            Object.assign(header.style, { background: '#FFF176', color: '#330000', padding: '5px', cursor: 'move', textAlign: 'center', fontFamily: 'Lobster' });

            let content = document.createElement('div');
            content.style.padding = '5px';
            tweaksBox._content = content;
            tweaksBox.append(header, content);
            document.body.appendChild(tweaksBox);
            renderTweaks();
            makeDraggable(header, tweaksBox);
            setupUiIsolation(tweaksBox);
        } else tweaksBox.remove();
    }

    document.addEventListener('keydown', e => {
        if (e.target.tagName !== 'INPUT' && e.shiftKey) {
            if (e.code === 'KeyL') vmToggle();
            if (e.code === 'KeyY') tweaksToggle();
        }
    });

    let checker = setInterval(() => {
        try {
            let searchFiber = f => f?.memoizedState?.bloxd || searchFiber(f?.next);
            window.Captured = Object.values(searchFiber(Object.values(document.querySelector(".Crosshair"))[0].return.memoizedState))[2];
            clearInterval(checker);
            document.querySelector(".Crosshair").innerText = "x";
        } catch {}
    }, 1000);

})();