add the ai chat as a section to the emulator that  the user can access with a button 


<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>CLIFF EMULATOR</title>
    <!-- Google Fonts for Enhanced Typography -->
    <link href="https://fonts.googleapis.com/css2?family=Roboto:wght@400;700&display=swap" rel="stylesheet">

    <!-- Include Ruffle for SWF support -->
    <script src="https://unpkg.com/@ruffle-rs/ruffle"></script>

    <style>
        /* Reset default margins and paddings */
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }

        /* Base Styles */
        html, body {
            height: 100%;
            font-family: 'Roboto', Arial, sans-serif;
            display: flex;
            flex-direction: column;
            background-color: #121212;
            color: #e0e0e0;
        }

        /* Header Styling */
        #header {
            padding: 20px;
            background-color: #1e1e1e;
            color: #ffffff;
            text-align: center;
            flex: 0 0 auto;
            box-shadow: 0 2px 4px rgba(0,0,0,0.5);
        }

        #header h1 {
            font-size: 2.5em;
            letter-spacing: 2px;
        }

        /* File Selector Styling */
        #fileSelector {
            padding: 15px 20px;
            background-color: #1e1e1e;
            text-align: center;
            flex: 0 0 auto;
            box-shadow: 0 2px 4px rgba(0,0,0,0.5);
            position: relative; /* Added for positioning the fullscreen button */
        }

        /* Custom File Input */
        .custom-file-input {
            position: relative;
            display: inline-block;
            overflow: hidden;
            cursor: pointer;
            background-color: #2c2c2c;
            color: #e0e0e0;
            padding: 12px 24px;
            border: 2px solid #444;
            border-radius: 5px;
            transition: background-color 0.3s, border-color 0.3s, transform 0.2s;
            font-size: 16px;
            font-weight: 500;
        }

        .custom-file-input:hover {
            background-color: #3a3a3a;
            border-color: #666;
        }

        .custom-file-input:active {
            transform: scale(0.98);
        }

        /* Hide the actual file input */
        .custom-file-input input[type="file"] {
            position: absolute;
            left: 0;
            top: 0;
            opacity: 0;
            width: 100%;
            height: 100%;
            cursor: pointer;
        }

        /* Emulator Container Styling */
        #gameContainer {
            flex: 1 1 auto;
            display: flex;
            justify-content: center;
            align-items: center;
            background-color: #121212;
            overflow: hidden;
            position: relative;
            padding: 20px;
        }

        /* Emulator Canvas Styling */
        #game {
            width: 100%;
            height: 100%;
            max-width: 100%;
            max-height: 100%;
            background-color: #000;
            border: 4px solid #333;
            border-radius: 8px;
            box-shadow: 0 0 20px rgba(0,0,0,0.7);
            position: relative; /* Necessary for positioning the fullscreen button */
        }

        /* Fullscreen Button Styling */
        #fullscreenButton {
            position: absolute;
            top: 10px;
            right: 10px;
            background-color: rgba(44, 44, 44, 0.8);
            color: #e0e0e0;
            border: none;
            padding: 8px 12px;
            border-radius: 4px;
            cursor: pointer;
            font-size: 14px;
            display: none; /* Hidden by default */
            transition: background-color 0.3s, transform 0.2s;
            z-index: 10; /* Ensure it's above other elements */
        }

        #fullscreenButton:hover {
            background-color: rgba(58, 58, 58, 0.9);
        }

        #fullscreenButton:active {
            transform: scale(0.95);
        }

        /* Optional Footer Styling */
        #footer {
            padding: 10px 20px;
            background-color: #1e1e1e;
            color: #888;
            text-align: center;
            flex: 0 0 auto;
            font-size: 0.9em;
        }

        /* Responsive Adjustments */
        @media (max-width: 600px) {
            #header h1 {
                font-size: 1.8em;
            }

            .custom-file-input {
                width: 100%;
                text-align: center;
            }

            #game {
                border-width: 2px;
            }

            #fullscreenButton {
                padding: 6px 10px;
                font-size: 12px;
            }
        }

        /* Smooth Transition for Theme Elements */
        body, #header, #fileSelector, .custom-file-input, #gameContainer, #game, #fullscreenButton {
            transition: background-color 0.3s, color 0.3s, border-color 0.3s;
        }
    </style>
</head>
<body>
    <!-- Header Section -->
    <div id="header">
        <h1>CLIFF EMULATOR</h1>
    </div>

    <!-- File Selector Section -->
    <div id="fileSelector">
        <label class="custom-file-input">
            Insert Game
            <input type="file" id="fileInput" accept=".nes, .smc, .sfc, .gba, .gb, .gbc, .nds, .z64, .swf" />
        </label>
    </div>

    <!-- Emulator Container -->
    <div id="gameContainer">
        <div id="game"></div>
        <!-- Fullscreen Button -->
        <button id="fullscreenButton">Fullscreen</button>
    </div>

    <!-- Optional Footer -->
    <div id="footer">
        &copy; 2024 CLIFF EMULATOR. All rights reserved.
    </div>

    <script>
        // Function to initialize EmulatorJS with selected game data
        function initializeEmulator(core, gameName, gameData) {
            // Set EmulatorJS configuration based on the selected core
            window.EJS_player = "#game"; // The DOM element to embed the emulator
            window.EJS_core = core; // Core emulator type 
            window.EJS_gameName = gameName || (core.toUpperCase() + " Game"); // Game name
            window.EJS_color = "#0064ff"; // Theme color
            window.EJS_pathtodata = "https://cdn.emulatorjs.org/stable/data/"; // Path to EmulatorJS data

            // Create a Blob URL for the game data
            window.EJS_gameUrl = URL.createObjectURL(new Blob([gameData]));

            // Remove existing loader.js if it exists to allow reinitialization
            const existingLoader = document.querySelector('script[data-loader="emulatorjs"]');
            if (existingLoader) {
                existingLoader.remove();
            }

            // Create a new script element for loader.js
            const loaderScript = document.createElement('script');
            loaderScript.src = "https://cdn.emulatorjs.org/stable/data/loader.js";
            loaderScript.setAttribute('data-loader', 'emulatorjs'); // Mark the script for future reference
            document.body.appendChild(loaderScript);

            // Hide the fullscreen button as EmulatorJS doesn't use it
            toggleFullscreenButton(false);
        }

        // Function to toggle fullscreen button visibility
        function toggleFullscreenButton(show) {
            const fullscreenButton = document.getElementById('fullscreenButton');
            if (show) {
                fullscreenButton.style.display = 'block';
            } else {
                fullscreenButton.style.display = 'none';
            }
        }

        // Handle file selection
        document.getElementById('fileInput').addEventListener('change', function(event) {
            const file = event.target.files[0];
            if (!file) {
                alert("No file selected.");
                return;
            }

            // Determine the file extension
            const fileName = file.name;
            const fileExtension = fileName.split('.').pop().toLowerCase();

            let core;
            if (fileExtension === 'nes') {
                core = 'nes';
            } else if (fileExtension === 'smc' || fileExtension === 'sfc') {
                core = 'snes';
            } else if (fileExtension === 'gba' || fileExtension === 'gb' || fileExtension === 'gbc' ) {
                core = 'gba';
            } else if (fileExtension === 'nds') {
                core = 'nds';
            } else if (fileExtension === 'z64') {
                core = 'n64';
            } else if (fileExtension === 'swf') {
                // Handle SWF files using Ruffle
                const reader = new FileReader();

                reader.onload = function(e) {
                    const arrayBuffer = e.target.result;

                    // Initialize Ruffle
                    const ruffle = window.RufflePlayer.newest();
                    const player = ruffle.createPlayer();

                    // Clear the #game element
                    const gameContainer = document.getElementById('game');
                    gameContainer.innerHTML = '';

                    // Append the player to the #game element
                    gameContainer.appendChild(player);

                    // Load the SWF data
                    player.load({ data: arrayBuffer });

                    // Make sure Ruffle player stretches to fit
                    player.style.width = '100%';
                    player.style.height = '100%';

                    // Show the fullscreen button
                    toggleFullscreenButton(true);

                    // Attach fullscreen functionality to the button
                    const fullscreenButton = document.getElementById('fullscreenButton');
                    fullscreenButton.onclick = function() {
                        toggleFullScreen(gameContainer);
                    };
                };

                reader.onerror = function() {
                    alert("Failed to read the SWF file.");
                };

                // Read the file as an ArrayBuffer
                reader.readAsArrayBuffer(file);
                return; // Exit the function since we don't need to use EmulatorJS
            } else {
                alert("Please select a valid game file.");
                return;
            }

            // For non-SWF files, initialize EmulatorJS
            const reader = new FileReader();

            reader.onload = function(e) {
                const arrayBuffer = e.target.result;
                const gameData = new Uint8Array(arrayBuffer);

                // Initialize the emulator with the selected game and core
                initializeEmulator(core, fileName, gameData);
            };

            reader.onerror = function() {
                alert("Failed to read the file.");
            };

            // Read the file as an ArrayBuffer
            reader.readAsArrayBuffer(file);
        });

        // Function to toggle fullscreen mode
        function toggleFullScreen(element) {
            if (!document.fullscreenElement) {
                if (element.requestFullscreen) {
                    element.requestFullscreen();
                } else if (element.webkitRequestFullscreen) { /* Safari */
                    element.webkitRequestFullscreen();
                } else if (element.msRequestFullscreen) { /* IE11 */
                    element.msRequestFullscreen();
                }
            } else {
                if (document.exitFullscreen) {
                    document.exitFullscreen();
                }
            }
        }

        // Optional: Handle exiting fullscreen to reset styles if needed
        document.addEventListener('fullscreenchange', (event) => {
            const gameContainer = document.getElementById('gameContainer');
            if (!document.fullscreenElement) {
                // Exited fullscreen

            }
        });
    </script>
</body>
</html>


<!DOCTYPE html>
<html>
<head>
    <link rel="icon" type="image/x-icon" href="google.svg">
    <title>Google</title>
    <style>
        body {
            font-family: sans-serif;
            position: relative; /* Ensure positioning context for absolute elements */
        }

        /* New CSS for the faint background text */
        .background-text {
            position: fixed;
            top: 50%;
            left: 50%;
            transform: translate(-50%, -50%) rotate(-45deg);
            font-size: 100px;
            color: rgba(0, 0, 0, 0.05); /* Faint color */
            white-space: nowrap;
            pointer-events: none; /* Allows clicks to pass through */
            z-index: -1; /* Places it behind other elements */
            user-select: none; /* Prevents text selection */
        }

        #chat-container {
            display: flex;
            flex-direction: column;
            width: 500px;
            margin: 0 auto;
            border: 1px solid #ccc;
            padding: 10px;
            height: 400px;
            overflow-y: auto;
        }

        .message {
            padding: 10px;
            margin-bottom: 10px;
            border-radius: 5px;
        }

        .user-message {
            background-color: #eee;
            text-align: right;
            white-space: pre-wrap; 
        }

        .bot-message {
            background-color: #f5f5f5;
            white-space: pre-wrap; 
        }

        #input-area {
            display: flex;
            margin-top: 10px;
        }

        #input-box {
            flex-grow: 1;
            padding: 5px;
            border: 1px solid #ccc;
            border-radius: 5px;
        }

        #send-button {
            padding: 5px 10px;
            background-color: #007bff;
            color: #fff;
            border: none;
            border-radius: 5px;
            cursor: pointer;
        }

        #typing-indicator {
            display: none; 
            margin-top: 5px;
            font-style: italic;
            color: #999;
        }

        #fileInput {
            display: none;
        }
        #attachLabel {
            cursor: pointer;
            margin-right: 8px;
            color: #007bff; 
            font-size: 18px; 
        }

        /* Existing Overlay for Typing Indicator */
        #overlay {
            position: fixed;
            top: 0;
            left: 0;
            width: 100%;
            height: 100%;
            background-color: rgba(0, 0, 0, 0.5); /* Semi-transparent background */
            display: none; /* Initially hidden */
            z-index: 1000; /* Ensure it's on top */
        }

        /* New Overlay for Googled.png */
        #google-overlay {
            position: fixed;
            top: 0;
            left: 0;
            width: 100%;
            height: 100%;
            background-image: url('googled.png'); /* Path to your image */
            background-size: cover; /* Adjust as needed */
            background-repeat: no-repeat;
            display: none; /* Initially hidden */
            z-index: 1001; /* Above the typing overlay */
        }
    </style>
</head>

<body>
    <!-- Faint Background Text -->
    <div class="background-text">made by cliff</div>

    <div id="chat-container">
        <!-- Existing Overlay for Typing Indicator -->
        <div id="overlay"></div>
        <!-- Chat messages will appear here -->
    </div>
    <div id="input-area">
        <textarea id="input-box" placeholder="Enter your message..." rows="3"></textarea>
        <label for="fileInput" id="attachLabel">📎</label>
        <input type="file" id="fileInput" multiple>
        <button id="send-button">Send</button>
    </div>
    <div id="typing-indicator">Gemini is typing...</div> 

    <!-- New Overlay for Googled.png -->
    <div id="google-overlay"></div>

    <script>
        // Existing JavaScript Code...
        const API_KEYS = [
            'AIzaSyBdc_A8VxExwO6-0LY1--r2-Ym73lMg-h4',
            'AIzaSyBydeCpaNOIPSk794CpTGnfKrxbjCgJLu4',
            'AIzaSyCQ7tBHtctxlNs61Zm2Y__7KYeDLfz5dms',
            'AIzaSyAip_DFfKNC35MFIorEoNK4y6czP9P65-c'
        ];
        let apiKeyIndex = 0;

        function getCurrentApiKey() {
            return API_KEYS[apiKeyIndex];
        }

        const API_URL = 'https://generativelanguage.googleapis.com';
        const chatContainer = document.getElementById('chat-container');
        const inputBox = document.getElementById('input-box');
        const sendButton = document.getElementById('send-button');
        const typingIndicator = document.getElementById('typing-indicator');
        const fileInput = document.getElementById('fileInput');
        const overlay = document.getElementById('overlay');
        const googleOverlay = document.getElementById('google-overlay'); // Select the Google overlay

        let history = []; // Initialize history here

        sendButton.addEventListener('click', sendMessage);
        inputBox.addEventListener('keydown', (event) => {
            if (event.key === 'Enter' && !event.shiftKey) {
                event.preventDefault();
                sendMessage();
            }
        });

        async function sendMessage() {
            const userMessageText = inputBox.value.trim(); // Get message from inputBox
            const files = fileInput.files;

            if (!userMessageText && files.length === 0) {
                alert('Please enter a message or select a file.');
                return;
            }

            if (files.length > 0) {
                let fileNames = [];
                for (let i = 0; i < files.length; i++) {
                    fileNames.push(files[i].name);
                }
                appendMessage('User', `[Files attached: ${fileNames.join(', ')}]`);
                showTypingIndicator();
            }
            if (userMessageText) {
                appendMessage('User', `${userMessageText}`);
                showTypingIndicator();
            }

            const userParts = [];

            if (files.length > 0) {
                try {
                    for (let i = 0; i < files.length; i++) {
                        const file = files[i];
                        const fileUri = await uploadFile(file);
                        userParts.push({
                            "fileData": {
                                "fileUri": fileUri,
                                "mimeType": file.type
                            }
                        });
                    }
                } catch (error) {
                    console.error('File upload failed:', error);
                    appendMessage('Error', 'Failed to upload one or more files.');
                    hideTypingIndicator();
                    return;
                }
            }

            if (userMessageText) {
                userParts.push({
                    "text": userMessageText
                });
            }

            history.push({
                "role": "user",
                "parts": userParts
            });

            const requestBody = {
                "contents": history,
                "generationConfig": {
                    "temperature": 0,
                    "topK": 40,
                    "topP": 0.95,
                    "maxOutputTokens": 10000,
                    "responseMimeType": "text/plain"
                }
            };

            try {
                await attemptApiRequest(requestBody);
            } catch (error) {
                console.error('Error:', error);
                appendMessage('Error', 'Failed to get response from the API.');
            } finally {
                hideTypingIndicator();
            }

            inputBox.value = '';
            fileInput.value = '';
        }

        function appendMessage(sender, message) {
            const messageDiv = document.createElement('div');
            messageDiv.classList.add('message', sender === 'User' ? 'user-message' : 'bot-message');

            const senderSpan = document.createElement('span');
            senderSpan.style.fontWeight = 'bold'; // Make sender bold
            senderSpan.textContent = `${sender}: `;
            messageDiv.appendChild(senderSpan);
           
            const messageText = document.createTextNode(message);
            messageDiv.appendChild(messageText);

            chatContainer.appendChild(messageDiv);
            chatContainer.scrollTop = chatContainer.scrollHeight;
        }

        function hideTypingIndicator() {
            typingIndicator.style.display = 'none';
            overlay.style.display = 'none'; // Hide existing overlay
            googleOverlay.style.display = 'none'; // Hide Google overlay
        }

        async function attemptApiRequest(requestBody) {
            const maxAttempts = API_KEYS.length;
            let attempts = 0;

            while (attempts < maxAttempts) {
                const apiKey = getCurrentApiKey();
                try {
                    const response = await fetch(`${API_URL}/v1beta/models/gemini-1.5-pro:generateContent?key=${apiKey}`, {
                        method: 'POST',
                        headers: {
                            'Content-Type': 'application/json'
                        },
                        body: JSON.stringify(requestBody)
                    });

                    if (!response.ok) {
                        const errorText = await response.text();
                        throw new Error(`API request failed: ${response.status} ${response.statusText} - ${errorText}`);
                    }

                    const data = await response.json();

                    const botResponse = data.candidates[0].content.parts.map(part => part.text || '').join('');
                    appendMessage('Bot', `${botResponse}`);

                    history.push({
                        "role": "model",
                        "parts": data.candidates[0].content.parts
                    });

                    return;

                } catch (error) {
                    console.warn(`Attempt with API key at index ${apiKeyIndex} failed:`, error);

                    attempts++;
                    apiKeyIndex = (apiKeyIndex + 1) % API_KEYS.length;

                    if (attempts >= maxAttempts) {
                        throw new Error('All API keys have failed.');
                    } else {
                        console.log(`Retrying with next API key (index ${apiKeyIndex})...`);
                    }
                }
            }
        }

        function showTypingIndicator() {
            typingIndicator.style.display = 'block';
            overlay.style.display = 'block'; // Show existing overlay
            googleOverlay.style.display = 'block'; // Show Google overlay
        }

        async function uploadFile(file) {
            const metadata = { "file": { "display_name": file.name } };

            const maxAttempts = API_KEYS.length;
            let attempts = 0;

            while (attempts < maxAttempts) {
                const apiKey = getCurrentApiKey();
                try {
                    const initiateUploadResponse = await fetch(`${API_URL}/upload/v1beta/files?key=${apiKey}`, {
                        method: 'POST',
                        headers: {
                            'X-Goog-Upload-Command': 'start',
                            'X-Goog-Upload-Protocol': 'resumable',
                            'Content-Type': 'application/json; charset=UTF-8',
                            'X-Goog-Upload-Header-Content-Type': file.type,
                            'Accept': 'application/json'
                        },
                        body: JSON.stringify(metadata)
                    });

                    if (!initiateUploadResponse.ok) {
                        const errorText = await initiateUploadResponse.text();
                        throw new Error(`Failed to initiate file upload: ${initiateUploadResponse.status} ${initiateUploadResponse.statusText} - ${errorText}`);
                    }

                    const uploadUrl = initiateUploadResponse.headers.get('X-Goog-Upload-URL');
                    if (!uploadUrl) {
                        throw new Error('Upload URL not returned from initiate upload request.');
                    }

                    const uploadResponse = await fetch(uploadUrl, {
                        method: 'POST',
                        headers: {
                            'X-Goog-Upload-Command': 'upload, finalize',
                            'X-Goog-Upload-Offset': '0',
                            'Content-Type': file.type,
                            'Content-Length': file.size.toString(),  // Important for larger files
                        },
                        body: file
                    });

                    if (!uploadResponse.ok) {
                        const errorText = await uploadResponse.text();
                        throw new Error(`Failed to upload file content: ${uploadResponse.status} ${uploadResponse.statusText} - ${errorText}`); // More specific error message
                    }

                    const uploadResult = await uploadResponse.json();
                    const fileUri = uploadResult.file.uri;  // Get the file URI
                    if (!fileUri) {
                        throw new Error('File URI not returned from file upload response.'); // More specific error message
                    }
                    return fileUri; // Return the file URI


                } catch (error) {
                    console.warn(`File upload attempt with API key at index ${apiKeyIndex} failed:`, error);
                    attempts++;
                    apiKeyIndex = (apiKeyIndex + 1) % API_KEYS.length;

                    if (attempts >= maxAttempts) {
                        throw new Error('All API keys have failed for file upload.');
                    } else {
                        console.log(`Retrying file upload with next API key (index ${apiKeyIndex})...`);
                    }
                }
            }
        }

        // Existing JavaScript Code for Overlay Toggle via Key Combination

        // Flag to prevent multiple toggles on key hold
        let toggleOverlayPressed = false;

        document.addEventListener('keydown', function(event) {
            // Check if Ctrl, Shift, and Alt are pressed along with 'G' or 'g'
            if (event.ctrlKey && event.shiftKey && event.altKey && (event.key === 'G' || event.key === 'g')) {
                if (!toggleOverlayPressed) { // Prevent repeated toggles if key is held down
                    toggleGoogleOverlay();
                    toggleOverlayPressed = true;
                }
                event.preventDefault(); // Prevent default actions if necessary
            }
        });

        document.addEventListener('keyup', function(event) {
            // Reset the flag when 'G' key is released
            if (event.key === 'G' || event.key === 'g') {
                toggleOverlayPressed = false;
            }
        });

        function toggleGoogleOverlay() {
            if (googleOverlay.style.display === 'none' || googleOverlay.style.display === '') {
                googleOverlay.style.display = 'block';
            } else {
                googleOverlay.style.display = 'none';
            }
        }
    </script>
</body>
</html>