Chrome Dino Mod Menu V7 with Auto Play

Mod Menu with God Mode, Speed Hack, Super Jump, Fly Hack, Remove Obstacles, Bigger Dino, Rainbow Glow, Low Gravity, Rainbow Background, Night Mode, Obstacle ESP, Remove Clouds, Rain Clouds, and Auto Play for Chrome Dino Game

// ==UserScript==
// @name         Chrome Dino Mod Menu V7 with Auto Play
// @namespace    http://tampermonkey.net/
// @version      7
// @description  Mod Menu with God Mode, Speed Hack, Super Jump, Fly Hack, Remove Obstacles, Bigger Dino, Rainbow Glow, Low Gravity, Rainbow Background, Night Mode, Obstacle ESP, Remove Clouds, Rain Clouds, and Auto Play for Chrome Dino Game
// @author       Luckyday999 Jadob Lane
// @match        https://chromedino.com/
// @match        https://thedinogame.com/*
// @grant        none
// @license      MIT
// ==/UserScript==

(function () {
    'use strict';

    let flyInterval = null;
    let obstacleInterval = null;
    let rainbowGlowEnabled = false;
    let glowElement = null;
    let glowAnimation = null;
    let originalGravity = null;
    let rainbowStyleElement = null;
    let originalBgColor = null;
    let obsESPEnabled = false;
    let obsESPOverlay = null;
    let obsESPContext = null;
    let obsESPDrawHook = null;
    let removeCloudsInterval = null;
    let rainCloudsEnabled = false;
    let rainCloudsAnimationId = null;
    let rainCloudCanvas = null;
    let rainCloudContext = null;

    let autoPlayEnabled = false;
    let autoPlayInterval = null;

    function createModMenu() {
        const menu = document.createElement('div');
        menu.id = 'modMenu';
        menu.style = `
            position: fixed;
            top: 20px;
            left: 20px;
            padding: 10px;
            background-color: rgba(0, 0, 0, 0.7);
            color: #fff;
            font-family: Arial, sans-serif;
            font-size: 14px;
            border-radius: 8px;
            z-index: 9999;
            user-select: none;
            pointer-events: auto;
        `;

        const title = document.createElement('div');
        title.textContent = '🦖 Chrome Dino Mod Menu';
        title.style.fontWeight = 'bold';
        title.style.marginBottom = '8px';
        menu.appendChild(title);

        function addToggle(labelText, onToggle) {
            const label = document.createElement('label');
            label.style.display = 'block';
            label.style.marginBottom = '6px';

            const checkbox = document.createElement('input');
            checkbox.type = 'checkbox';
            checkbox.style.marginRight = '6px';
            checkbox.addEventListener('click', e => e.stopPropagation());
            checkbox.addEventListener('change', function () {
                onToggle(this.checked);
            });

            label.appendChild(checkbox);
            label.appendChild(document.createTextNode(labelText));
            menu.appendChild(label);
        }

        addToggle('God Mode', toggleGodMode);
        addToggle('Speed Hack', applySpeedHack);
        addToggle('Super Jump', toggleSuperJump);
        addToggle('Fly Hack', toggleFlyHack);
        addToggle('Remove Obstacles', toggleRemoveObstacles);
        addToggle('Remove Clouds', toggleRemoveClouds);
        addToggle('Rain Clouds', toggleRainClouds);
        addToggle('Bigger Dino', toggleBigDino);
        addToggle('Rainbow Glow', toggleRainbowGlow);
        addToggle('Low Gravity', toggleLowGravity);
        addToggle('Rainbow Background', toggleRainbowBackground);
        addToggle('Night Mode', toggleNightMode);
        addToggle('Obstacle ESP', toggleObstacleESP);
        addToggle('Auto Play', toggleAutoPlay);  // <-- Added Auto Play toggle

        document.body.appendChild(menu);
    }

    // --- Toggles ---
    function toggleGodMode(enabled) {
        const runner = window.Runner;
        if (runner && runner.prototype) {
            if (enabled) {
                if (!runner.prototype._originalGameOver)
                    runner.prototype._originalGameOver = runner.prototype.gameOver;
                runner.prototype.gameOver = function () {};
            } else {
                if (runner.prototype._originalGameOver)
                    runner.prototype.gameOver = runner.prototype._originalGameOver;
            }
        }
    }

    function applySpeedHack(enabled) {
        const instance = Runner.instance_;
        if (instance && typeof instance.setSpeed === 'function') {
            instance.setSpeed(enabled ? 1000 : 6);
        }
    }

    function toggleSuperJump(enabled) {
        const trex = Runner.instance_?.tRex;
        if (trex && typeof trex.setJumpVelocity === 'function') {
            trex.setJumpVelocity(enabled ? 100 : -10.5);
        }
    }

    function toggleFlyHack(enabled) {
        const runner = Runner.instance_;
        if (!runner?.tRex) return;

        if (enabled) {
            flyInterval = setInterval(() => {
                const trex = runner.tRex;
                trex.groundYPos = 20;
                trex.yPos = 20;
                trex.jumpVelocity = 0;
                trex.status = 'JUMPING';
            }, 20);
        } else {
            clearInterval(flyInterval);
            flyInterval = null;
            const trex = runner.tRex;
            trex.groundYPos = trex.config.GROUND_Y_POS;
            trex.status = 'RUNNING';
        }
    }

    function toggleRemoveObstacles(enabled) {
        const runner = Runner.instance_;
        if (!runner) return;

        if (enabled) {
            obstacleInterval = setInterval(() => {
                runner.horizon.obstacles = [];
            }, 30);
        } else {
            clearInterval(obstacleInterval);
            obstacleInterval = null;
        }
    }

    function toggleRemoveClouds(enabled) {
        const runner = Runner.instance_;
        if (!runner || !runner.horizon) return;

        if (enabled) {
            removeCloudsInterval = setInterval(() => {
                runner.horizon.clouds = [];
            }, 30);
        } else {
            clearInterval(removeCloudsInterval);
            removeCloudsInterval = null;
        }
    }

    function toggleRainClouds(enabled) {
        const runner = Runner.instance_;
        if (!runner || !runner.canvas) return;

        const cloudColor = 'rgba(200, 200, 200, 0.7)';
        const cloudCount = 8;
        const cloudSpeed = 0.15;
        let clouds = [];

        if (enabled) {
            rainCloudsEnabled = true;

            rainCloudCanvas = document.createElement('canvas');
            rainCloudCanvas.style.position = 'absolute';
            rainCloudCanvas.style.pointerEvents = 'none';
            rainCloudCanvas.style.zIndex = '10';

            document.body.appendChild(rainCloudCanvas);
            rainCloudContext = rainCloudCanvas.getContext('2d');

            function updateCanvasSize() {
                const rect = runner.canvas.getBoundingClientRect();
                rainCloudCanvas.width = rect.width;
                rainCloudCanvas.height = rect.height;
                rainCloudCanvas.style.top = rect.top + 'px';
                rainCloudCanvas.style.left = rect.left + 'px';
            }

            function drawCloud(x, y, r) {
                rainCloudContext.beginPath();
                rainCloudContext.fillStyle = cloudColor;
                rainCloudContext.arc(x, y, r, 0, Math.PI * 2);
                rainCloudContext.arc(x + r * 0.6, y - r * 0.3, r * 0.7, 0, Math.PI * 2);
                rainCloudContext.arc(x + r * 1.2, y, r, 0, Math.PI * 2);
                rainCloudContext.fill();
            }

            for (let i = 0; i < cloudCount; i++) {
                clouds.push({
                    x: Math.random() * window.innerWidth,
                    y: Math.random() * 40 + 10,
                    radius: Math.random() * 10 + 10,
                    speed: cloudSpeed + Math.random() * 0.1,
                });
            }

            function animate() {
                if (!rainCloudsEnabled) return;
                updateCanvasSize();
                rainCloudContext.clearRect(0, 0, rainCloudCanvas.width, rainCloudCanvas.height);

                for (let cloud of clouds) {
                    cloud.x += cloud.speed;
                    if (cloud.x - cloud.radius * 2 > rainCloudCanvas.width) {
                        cloud.x = -cloud.radius * 2;
                        cloud.y = Math.random() * 40 + 10;
                    }
                    drawCloud(cloud.x, cloud.y, cloud.radius);
                }

                rainCloudsAnimationId = requestAnimationFrame(animate);
            }

            animate();
        } else {
            rainCloudsEnabled = false;
            if (rainCloudsAnimationId) {
                cancelAnimationFrame(rainCloudsAnimationId);
                rainCloudsAnimationId = null;
            }
            if (rainCloudCanvas) {
                rainCloudCanvas.remove();
                rainCloudCanvas = null;
                rainCloudContext = null;
            }
        }
    }

    function toggleBigDino(enabled) {
        const canvas = document.querySelector('.runner-canvas');
        if (!canvas) return;
        canvas.style.transform = enabled ? 'scale(2)' : 'scale(1)';
        canvas.style.transformOrigin = 'bottom left';
    }

    function toggleRainbowGlow(enabled) {
        const canvas = document.querySelector('.runner-canvas');
        const runner = window.Runner?.instance_;
        if (!canvas || !runner) return;

        const container = canvas.parentElement;
        container.style.position = 'relative';

        if (enabled) {
            if (!glowElement) {
                glowElement = document.createElement('div');
                glowElement.style.position = 'absolute';
                glowElement.style.pointerEvents = 'none';
                glowElement.style.zIndex = 9999;
                container.appendChild(glowElement);
            }

            let hue = 0;
            rainbowGlowEnabled = true;

            glowAnimation = setInterval(() => {
                hue = (hue + 3) % 360;
                glowElement.style.boxShadow = `0 0 8px 4px hsl(${hue}, 100%, 60%)`;
            }, 50);

            const updateGlowPosition = () => {
                if (!rainbowGlowEnabled || !runner.tRex) return;
                const trex = runner.tRex;
                glowElement.style.left = `${trex.xPos}px`;
                glowElement.style.top = `${trex.yPos}px`;
                glowElement.style.width = `${trex.config.WIDTH}px`;
                glowElement.style.height = `${trex.config.HEIGHT}px`;
                requestAnimationFrame(updateGlowPosition);
            };
            updateGlowPosition();
        } else {
            rainbowGlowEnabled = false;
            if (glowElement) glowElement.remove();
            glowElement = null;
            clearInterval(glowAnimation);
        }
    }

    function toggleLowGravity(enabled) {
        const trex = Runner.instance_?.tRex;
        if (!trex) return;
        const config = trex.config;

        if (enabled) {
            if (originalGravity === null) originalGravity = config.GRAVITY;
            config.GRAVITY = 0.1;
        } else {
            if (originalGravity !== null) config.GRAVITY = originalGravity;
        }
    }

    function toggleRainbowBackground(enabled) {
        if (enabled) {
            rainbowStyleElement = document.createElement('style');
            rainbowStyleElement.innerHTML = `
                @keyframes rainbowBackground {
                    0% { background-color: red; }
                    16% { background-color: orange; }
                    33% { background-color: yellow; }
                    50% { background-color: green; }
                    66% { background-color: blue; }
                    83% { background-color: indigo; }
                    100% { background-color: violet; }
                }
                body {
                    animation: rainbowBackground 5s linear infinite !important;
                }
            `;
            document.head.appendChild(rainbowStyleElement);
        } else {
            if (rainbowStyleElement) {
                rainbowStyleElement.remove();
                rainbowStyleElement = null;
                document.body.style.animation = 'none';
            }
        }
    }

    function toggleNightMode(enabled) {
        if (enabled) {
            originalBgColor = document.body.style.backgroundColor;
            document.body.style.backgroundColor = 'black';
        } else {
            document.body.style.backgroundColor = originalBgColor || '';
        }
    }

    function toggleObstacleESP(enabled) {
        const runner = Runner.instance_;
        if (!runner?.canvas || !runner.tRex) return;

        const baseCanvas = runner.canvas;

        if (enabled) {
            if (!obsESPOverlay) {
                obsESPOverlay = document.createElement('canvas');
                obsESPOverlay.width = baseCanvas.width;
                obsESPOverlay.height = baseCanvas.height;
                obsESPOverlay.style.position = 'absolute';
                obsESPOverlay.style.left = baseCanvas.offsetLeft + 'px';
                obsESPOverlay.style.top = baseCanvas.offsetTop + 'px';
                obsESPOverlay.style.pointerEvents = 'none';
                obsESPOverlay.style.zIndex = 9998;
                baseCanvas.parentNode.appendChild(obsESPOverlay);
                obsESPContext = obsESPOverlay.getContext('2d');
            }

            obsESPDrawHook = setInterval(() => {
                const obstacles = runner.horizon.obstacles;
                obsESPContext.clearRect(0, 0, obsESPOverlay.width, obsESPOverlay.height);

                for (const obs of obstacles) {
                    obsESPContext.save();
                    obsESPContext.strokeStyle = 'red';
                    obsESPContext.lineWidth = 2;
                    obsESPContext.strokeRect(obs.xPos, obs.yPos, obs.width, obs.typeConfig.height);
                    obsESPContext.restore();
                }
            }, 50);
        } else {
            clearInterval(obsESPDrawHook);
            obsESPDrawHook = null;
            if (obsESPOverlay) {
                obsESPOverlay.remove();
                obsESPOverlay = null;
                obsESPContext = null;
            }
        }
    }

    // Auto Play toggle with pterodactyl duck/jump logic
    function toggleAutoPlay(enabled) {
        const runner = Runner.instance_;
        if (!runner) return;

        autoPlayEnabled = enabled;

        if (enabled) {
            autoPlayInterval = setInterval(() => {
                const tRex = runner.tRex;
                const obstacles = runner.horizon.obstacles;

                if (!tRex || !obstacles) return;

                // Find closest obstacle ahead of dino
                const obstacle = obstacles.find(obs => obs.xPos > tRex.xPos);

                if (obstacle) {
                    const dist = obstacle.xPos - tRex.xPos;

                    // PTERODACTYL special case
                    if (obstacle.typeConfig && obstacle.typeConfig.type === 'PTERODACTYL') {
                        // Compare bird height to dino top (yPos is from top of canvas)
                        const birdIsHigher = obstacle.yPos < tRex.yPos; // smaller y = higher on screen
                        if (dist < 80) {
                            if (birdIsHigher) {
                                // Duck if bird is higher
                                if (!tRex.ducking) {
                                    document.dispatchEvent(new KeyboardEvent('keydown', {keyCode: 40}));
                                }
                            } else {
                                // Else jump if bird is lower or same height
                                if (!tRex.jumping) {
                                    document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 40})); // release duck
                                    document.dispatchEvent(new KeyboardEvent('keydown', {keyCode: 38}));
                                    document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 38}));
                                }
                            }
                        } else {
                            // Obstacle far away, release duck if ducking
                            if (tRex.ducking) {
                                document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 40}));
                            }
                        }
                    } else {
                        // Normal obstacle: jump if close
                        if (dist < 80 && !tRex.jumping && !tRex.ducking) {
                            document.dispatchEvent(new KeyboardEvent('keydown', {keyCode: 38}));
                            document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 38}));
                        }
                        // Release duck key if ducking
                        if (tRex.ducking) {
                            document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 40}));
                        }
                    }
                } else {
                    // No obstacles, release duck if ducking
                    if (tRex.ducking) {
                        document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 40}));
                    }
                }
            }, 20);
        } else {
            clearInterval(autoPlayInterval);
            autoPlayInterval = null;
            // Release duck key if active
            document.dispatchEvent(new KeyboardEvent('keyup', {keyCode: 40}));
        }
    }

    const checkRunner = setInterval(() => {
        if (window.Runner?.instance_?.tRex) {
            clearInterval(checkRunner);
            createModMenu();
        }
    }, 500);
})();