Universal Speed Hack

A powerful Universal Speed Hack supporting setTimeout,setInterval,requestAnimationFrame,Date.now(), and performance.now()

Vous devrez installer une extension telle que Tampermonkey, Greasemonkey ou Violentmonkey pour installer ce script.

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

Vous devrez installer une extension telle que Tampermonkey ou Violentmonkey pour installer ce script.

Vous devrez installer une extension telle que Tampermonkey ou Userscripts pour installer ce script.

Vous devrez installer une extension telle que Tampermonkey pour installer ce script.

Vous devrez installer une extension de gestionnaire de script utilisateur pour installer ce script.

(J'ai déjà un gestionnaire de scripts utilisateur, laissez-moi l'installer !)

Vous devrez installer une extension telle que Stylus pour installer ce style.

Vous devrez installer une extension telle que Stylus pour installer ce style.

Vous devrez installer une extension telle que Stylus pour installer ce style.

Vous devrez installer une extension du gestionnaire de style pour utilisateur pour installer ce style.

Vous devrez installer une extension du gestionnaire de style pour utilisateur pour installer ce style.

Vous devrez installer une extension du gestionnaire de style pour utilisateur pour installer ce style.

(J'ai déjà un gestionnaire de style utilisateur, laissez-moi l'installer!)

// ==UserScript==
// @name         Universal Speed Hack
// @namespace    http://tampermonkey.net/
// @version      1
// @description  A powerful Universal Speed Hack supporting setTimeout,setInterval,requestAnimationFrame,Date.now(), and performance.now()
// @author       OpenSource (https://www.youtube.com/@OpenSource-w4j)
// @match        *://*/*
// @run-at       document-start
// @grant        none
// ==/UserScript==

(function() {
    'use strict';

    function enableSpeedHackEngine() {
        if (window.__universal_sh_engine_active) return;
        window.__universal_sh_engine_active = true;

        let globalSpeed = 1.0;
        let speedhackActive = false;

        window.__sh_setSpeed = (val) => { globalSpeed = val; };
        window.__sh_setActive = (act) => { speedhackActive = act; };

        const realPerfNow = performance.now.bind(performance);
        const origRAF = window.requestAnimationFrame.bind(window);

        let lastTime = realPerfNow();
        let simTime = lastTime;

        performance.now = function() {
            if (!speedhackActive || globalSpeed === 1.0) return realPerfNow();
            const now = realPerfNow();
            simTime += (now - lastTime) * globalSpeed;
            lastTime = now;
            return simTime;
        };

        window.requestAnimationFrame = function(cb) {
            return origRAF(function(timestamp) {
                lastTime = timestamp;
                if (!speedhackActive || globalSpeed === 1.0) return cb(timestamp);
                return cb(simTime);
            });
        };

        const origSetInterval = window.setInterval;
        const origSetTimeout = window.setTimeout;

        window.setInterval = function(callback, delay, ...args) {
            if (speedhackActive && globalSpeed > 0) {
                delay = delay / globalSpeed;
            }
            return origSetInterval(callback, delay, ...args);
        };

        window.setTimeout = function(callback, delay, ...args) {
            if (speedhackActive && globalSpeed > 0) {
                delay = delay / globalSpeed;
            }
            return origSetTimeout(callback, delay, ...args);
        };

        const realDateNow = Date.now.bind(Date);
        let simDateNow = realDateNow();
        let lastDateCheck = realDateNow();

        Date.now = function() {
            if (!speedhackActive || globalSpeed === 1.0) return realDateNow();
            const now = realDateNow();
            simDateNow += (now - lastDateCheck) * globalSpeed;
            lastDateCheck = now;
            return Math.floor(simDateNow);
        };
    }

    enableSpeedHackEngine();

    function initWhenCanvasReady() {
        if (document.getElementById('universal-speed-hack-host')) return;

        const checkInterval = setInterval(() => {
            const gameCanvas = document.querySelector('canvas');
            if (gameCanvas && (gameCanvas.width > 100 || gameCanvas.height > 100 || gameCanvas.style.display !== 'none')) {
                clearInterval(checkInterval);
                createGUI();
            }
        }, 300);
    }

    function createGUI() {
        if (document.getElementById('universal-speed-hack-host')) return;

        let globalSpeed = 1.0;
        let speedhackActive = false;
        let toggleKey = 'h';

        const host = document.createElement('div');
        host.id = 'universal-speed-hack-host';
        host.style.cssText = 'position: fixed; top: 0; left: 0; z-index: 2147483647; pointer-events: none;';
        const shadow = host.attachShadow({ mode: 'open' });

        const container = document.createElement('div');
        container.id = 'universal-speed-hack-gui';
        container.style.cssText = `
            position: fixed;
            top: 15px;
            right: 15px;
            pointer-events: auto;
            background: #141414;
            color: #e0e0e0;
            padding: 12px;
            border-radius: 8px;
            font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
            font-size: 12px;
            box-shadow: 0 8px 24px rgba(0,0,0,0.6);
            user-select: none;
            display: flex;
            flex-direction: column;
            gap: 10px;
            width: 200px;
            border: 1px solid #2a2a2a;
        `;
        shadow.appendChild(container);

        const header = document.createElement('div');
        header.style.cssText = 'font-weight: 600; display: flex; justify-content: space-between; align-items: center; border-bottom: 1px solid #262626; padding-bottom: 6px; cursor: move; color: #fff; letter-spacing: 0.3px;';
        header.innerHTML = '<span>Universal Speed Hack</span> <span style="cursor:pointer; color:#777; font-size:14px;" id="sh-min">−</span>';
        container.appendChild(header);

        const body = document.createElement('div');
        body.id = 'sh-content';
        body.style.cssText = 'display: flex; flex-direction: column; gap: 8px;';
        container.appendChild(body);

        const toggleBtn = document.createElement('button');
        toggleBtn.innerText = 'OFF';
        toggleBtn.style.cssText = `
            background: #2a2a2a;
            color: #ef4444;
            border: 1px solid #3f3f46;
            padding: 6px;
            border-radius: 5px;
            cursor: pointer;
            font-weight: 700;
            font-size: 11px;
            transition: all 0.2s;
        `;

        function updateToggleUI() {
            toggleBtn.style.background = speedhackActive ? '#166534' : '#2a2a2a';
            toggleBtn.style.color = speedhackActive ? '#4ade80' : '#ef4444';
            toggleBtn.style.borderColor = speedhackActive ? '#22c55e' : '#3f3f46';
            toggleBtn.innerText = speedhackActive ? 'ACTIVE' : 'OFF';
            if (window.__sh_setActive) window.__sh_setActive(speedhackActive);
        }

        toggleBtn.onclick = () => {
            speedhackActive = !speedhackActive;
            updateToggleUI();
        };
        body.appendChild(toggleBtn);

        const controlWrap = document.createElement('div');
        controlWrap.style.cssText = 'display: flex; flex-direction: column; gap: 6px; background: #1a1a1a; padding: 8px; border-radius: 6px; border: 1px solid #222;';

        const labelRow = document.createElement('div');
        labelRow.style.cssText = 'display: flex; justify-content: space-between; color: #a1a1aa; font-size: 11px; align-items: center;';
        labelRow.innerHTML = `<span>Speed</span>`;

        const inputControls = document.createElement('div');
        inputControls.style.cssText = 'display: flex; align-items: center; gap: 4px;';

        const minusBtn = document.createElement('button');
        minusBtn.innerText = '-';
        minusBtn.style.cssText = 'background: #222; color: #38bdf8; border: 1px solid #333; width: 22px; height: 22px; border-radius: 3px; cursor: pointer; font-weight: bold; font-size: 12px;';

        const numberInput = document.createElement('input');
        numberInput.type = 'text';
        numberInput.value = '1';
        numberInput.style.cssText = `
            width: 40px;
            background: #111;
            color: #38bdf8;
            border: 1px solid #333;
            text-align: center;
            font-family: monospace;
            font-size: 11px;
            border-radius: 4px;
            height: 20px;
            outline: none;
        `;

        const plusBtn = document.createElement('button');
        plusBtn.innerText = '+';
        plusBtn.style.cssText = 'background: #222; color: #38bdf8; border: 1px solid #333; width: 22px; height: 22px; border-radius: 3px; cursor: pointer; font-weight: bold; font-size: 12px;';

        function applySpeed(val) {
            let num = parseFloat(val);
            if (isNaN(num) || num < 1) num = 1;
            if (num > 9999) num = 9999;
            globalSpeed = num;
            numberInput.value = num;
            sliderInput.value = num > sliderInput.max ? sliderInput.max : num;
            if (window.__sh_setSpeed) window.__sh_setSpeed(globalSpeed);
        }

        // CONTINUOUS HOLD-TO-INCREMENT LOGIC (PC & MOBILE TOUCH)
        let holdInterval = null;
        let holdTimeout = null;

        function startHold(stepValue) {
            stopHold();
            applySpeed(globalSpeed + stepValue);

            holdTimeout = setTimeout(() => {
                holdInterval = setInterval(() => {
                    applySpeed(globalSpeed + stepValue);
                }, 75);
            }, 400);
        }

        function stopHold() {
            if (holdTimeout) { clearTimeout(holdTimeout); holdTimeout = null; }
            if (holdInterval) { clearInterval(holdInterval); holdInterval = null; }
        }

        minusBtn.addEventListener('mousedown', (e) => { e.preventDefault(); startHold(-1); });
        minusBtn.addEventListener('mouseup', stopHold);
        minusBtn.addEventListener('mouseleave', stopHold);
        minusBtn.addEventListener('touchstart', (e) => { e.preventDefault(); startHold(-1); }, {passive: false});
        minusBtn.addEventListener('touchend', stopHold);

        plusBtn.addEventListener('mousedown', (e) => { e.preventDefault(); startHold(1); });
        plusBtn.addEventListener('mouseup', stopHold);
        plusBtn.addEventListener('mouseleave', stopHold);
        plusBtn.addEventListener('touchstart', (e) => { e.preventDefault(); startHold(1); }, {passive: false});
        plusBtn.addEventListener('touchend', stopHold);

        numberInput.addEventListener('input', (e) => {
            let clean = e.target.value.replace(/[^0-9.]/g, '');
            if (clean !== '') applySpeed(clean);
        });

        numberInput.addEventListener('keydown', (e) => {
            e.stopPropagation();
            if (e.key === 'Enter') {
                e.preventDefault();
                numberInput.blur();
            }
        });

        inputControls.appendChild(minusBtn);
        inputControls.appendChild(numberInput);
        inputControls.appendChild(plusBtn);
        labelRow.appendChild(inputControls);
        controlWrap.appendChild(labelRow);

        const sliderInput = document.createElement('input');
        sliderInput.type = 'range';
        sliderInput.min = '1';
        sliderInput.max = '9999';
        sliderInput.step = '1';
        sliderInput.value = '1';
        sliderInput.style.cssText = 'width: 100%; cursor: pointer; accent-color: #38bdf8;';

        sliderInput.oninput = (e) => {
            applySpeed(e.target.value);
        };

        controlWrap.appendChild(sliderInput);
        body.appendChild(controlWrap);

        const footer = document.createElement('div');
        footer.style.cssText = 'font-size: 8px; color: #52525b; text-align: center; border-top: 1px solid #262626; padding-top: 4px;';
        footer.innerHTML = '<a href="https://www.youtube.com/@OpenSource-w4j" target="_blank" style="color: #38bdf8; text-decoration: none;">Made by OpenSource</a>';
        container.appendChild(footer);

        let minimized = false;
        header.querySelector('#sh-min').onclick = () => {
            minimized = !minimized;
            body.style.display = minimized ? 'none' : 'flex';
            header.querySelector('#sh-min').innerText = minimized ? '+' : '−';
        };

        window.addEventListener('keydown', (e) => {
            if (shadow.activeElement === numberInput) return;
            if (e.key.toLowerCase() === toggleKey) {
                container.style.display = container.style.display === 'none' ? 'flex' : 'none';
            }
        });

        // PC Drag-and-Drop
        let isDragging = false;
        let startX, startY, initialX, initialY;

        header.onmousedown = (e) => {
            if (e.target.id === 'sh-min') return;
            isDragging = true;
            startX = e.clientX;
            startY = e.clientY;
            initialX = container.offsetLeft;
            initialY = container.offsetTop;
            document.addEventListener('mousemove', onMouseMove);
            document.addEventListener('mouseup', onMouseUp);
        };

        function onMouseMove(e) {
            if (!isDragging) return;
            container.style.left = (initialX + (e.clientX - startX)) + 'px';
            container.style.top = (initialY + (e.clientY - startY)) + 'px';
            container.style.right = 'auto';
        }

        function onMouseUp() {
            isDragging = false;
            document.removeEventListener('mousemove', onMouseMove);
            document.removeEventListener('mouseup', onMouseUp);
        }

        // Mobile Touch Support for Dragging
        header.ontouchstart = (e) => {
            if (e.target.id === 'sh-min') return;
            const touch = e.touches[0];
            isDragging = true;
            startX = touch.clientX;
            startY = touch.clientY;
            initialX = container.offsetLeft;
            initialY = container.offsetTop;
            document.addEventListener('touchmove', onTouchMove);
            document.addEventListener('touchend', onTouchEnd);
        };

        function onTouchMove(e) {
            if (!isDragging) return;
            const touch = e.touches[0];
            container.style.left = (initialX + (touch.clientX - startX)) + 'px';
            container.style.top = (initialY + (touch.clientY - startY)) + 'px';
            container.style.right = 'auto';
        }

        function onTouchEnd() {
            isDragging = false;
            document.removeEventListener('touchmove', onTouchMove);
            document.removeEventListener('touchend', onTouchEnd);
        }

        if (document.body) {
            document.body.appendChild(host);
            showNotification(shadow);
        } else {
            window.addEventListener('DOMContentLoaded', () => {
                document.body.appendChild(host);
                showNotification(shadow);
            });
        }
    }

    function showNotification(shadowRoot) {
        const notif = document.createElement('div');
        notif.style.cssText = `
            position: fixed;
            bottom: 20px;
            left: 50%;
            transform: translateX(-50%);
            z-index: 2147483647;
            background: #18181b;
            color: #f4f4f5;
            padding: 8px 16px;
            border-radius: 6px;
            font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
            font-size: 11px;
            box-shadow: 0 4px 12px rgba(0,0,0,0.5);
            border: 1px solid #27272a;
            transition: opacity 0.5s ease;
            opacity: 1;
            pointer-events: auto;
            letter-spacing: 0.3px;
        `;
        notif.innerHTML = '<a href="https://www.youtube.com/@OpenSource-w4j" target="_blank" style="color: #38bdf8; text-decoration: none;">Made by OpenSource</a>';
        shadowRoot.appendChild(notif);

        // Disappears automatically after 2 seconds
        setTimeout(() => {
            notif.style.opacity = '0';
            setTimeout(() => notif.remove(), 500);
        }, 2000);
    }

    if (document.readyState === 'loading') {
        document.addEventListener('DOMContentLoaded', initWhenCanvasReady);
    } else {
        initWhenCanvasReady();
    }
})();