dumo

Google Görsel Arama ve Gelişmiş Görsel Yansıtıcı (Sürükle, Yapıştır, Ara, Yansıt)

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey, Greasemonkey of Violentmonkey.

Voor het installeren van scripts heb je een extensie nodig, zoals {tampermonkey_link:Tampermonkey}.

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey of Violentmonkey.

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey of Userscripts.

Voor het installeren van scripts heb je een extensie nodig, zoals {tampermonkey_link:Tampermonkey}.

Voor het installeren van scripts heb je een gebruikersscriptbeheerder nodig.

(Ik heb al een user script manager, laat me het downloaden!)

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

(Ik heb al een beheerder - laat me doorgaan met de installatie!)

// ==UserScript==
// @name         dumo
// @namespace    http://tampermonkey.net/
// @version      4.1 - DÜZELTİLMİŞ ENTEGRE
// @description  Google Görsel Arama ve Gelişmiş Görsel Yansıtıcı (Sürükle, Yapıştır, Ara, Yansıt)
// @author       g & Ferres (Merged)
// @match        https://gartic.io/*
// @grant        GM_addStyle
// @grant        GM_xmlhttpRequest
// @connect      googleapis.com
// @icon         https://www.google.com/s2/favicons?sz=64&domain=gartic.io
// @license      MIT
// ==/UserScript==

(function() {
    'use strict';

    // ==========================================
    // 1. GENEL AYARLAR VE API BİLGİLERİ
    // ==========================================
    const API_KEY = "AIzaSyBP6U28ngnKhCKYoYgkExWXNxHT_-MCJvQ";
    const SEARCH_ENGINE_ID = "d3a4fb1c91a394ccd";

    // Mobil kontrolü
    const isMobile = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent);

    // Değişkenler
    let overlayGorsel = null; // Ekrana basılan resim
    let menuAcik = false;     // Ayar menüsü durumu
    let searchPanelAcik = false; // Arama paneli durumu

    // ==========================================
    // 2. STİLLER (CSS)
    // ==========================================
    GM_addStyle(`
        /* Arama Paneli Stilleri */
        #babaSokucuPanel {
            position: fixed;
            top: ${isMobile ? '5px' : '10px'};
            left: 50%;
            transform: translateX(-50%);
            width: ${isMobile ? '95vw' : '320px'};
            max-width: ${isMobile ? '350px' : '320px'};
            background-color: #f1f1f1;
            border: 2px solid #888;
            border-radius: 8px;
            z-index: 9999;
            display: none;
            flex-direction: column;
            box-shadow: 0 4px 8px rgba(0,0,0,0.2);
            font-family: Arial, sans-serif;
            ${isMobile ? 'touch-action: none;' : ''}
        }
        #babaSokucuHeader {
            padding: ${isMobile ? '15px 10px' : '10px'};
            cursor: ${isMobile ? 'grab' : 'move'};
            z-index: 10000;
            background-color: #c0392b;
            color: white;
            border-top-left-radius: 6px;
            border-top-right-radius: 6px;
            text-align: center;
            font-weight: bold;
            font-size: ${isMobile ? '16px' : '14px'};
            user-select: none;
        }
        #babaSokucuContent {
            padding: ${isMobile ? '20px 15px' : '15px'};
            display: flex;
            flex-direction: column;
            align-items: center;
        }
        #flagSearchInput {
            width: 95%;
            padding: ${isMobile ? '12px 8px' : '8px'};
            margin-bottom: ${isMobile ? '15px' : '10px'};
            border: 1px solid #ccc;
            border-radius: 4px;
            font-size: ${isMobile ? '16px' : '14px'};
        }
        #flagImageContainer {
            width: 100%;
            height: ${isMobile ? '200px' : '180px'};
            border: 1px dashed #ccc;
            display: flex;
            justify-content: center;
            align-items: center;
            background-color: #fff;
            margin-top: 5px;
            overflow: hidden;
            position: relative;
        }
        #flagImage {
            max-width: 100%;
            max-height: 100%;
            display: none;
        }
        #searchButton {
            width: 100%;
            padding: ${isMobile ? '12px' : '8px'};
            background-color: #c0392b;
            color: white;
            border: none;
            border-radius: 4px;
            font-weight: bold;
            cursor: pointer;
            margin-top: 10px;
        }
        #btn-transfer-img {
            width: 100%;
            padding: 10px;
            background-color: #27ae60;
            color: white;
            border: none;
            border-radius: 4px;
            font-weight: bold;
            cursor: pointer;
            margin-top: 10px;
            display: none; /* Başlangıçta gizli */
        }
        #mobileToggleBtn {
            position: fixed;
            bottom: ${isMobile ? '80px' : '70px'};
            right: ${isMobile ? '20px' : '10px'};
            width: 50px;
            height: 50px;
            background-color: #c0392b;
            color: white;
            border: none;
            border-radius: 50%;
            font-size: 12px;
            font-weight: bold;
            cursor: pointer;
            z-index: 9998;
            box-shadow: 0 2px 6px rgba(0,0,0,0.3);
            display: flex;
            align-items: center;
            justify-content: center;
            text-align: center;
        }
    `);

    // ==========================================
    // 3. HTML ARAYÜZ OLUŞTURMA
    // ==========================================

    const overlayMenuHTML = `
        <div id="ressam-menu" style="
            position: fixed; top: 70px; left: 10px; background: rgba(0, 0, 0, 0.9); color: #00ff00;
            padding: 15px; border: 2px solid #00ff00; border-radius: 10px; z-index: 9999;
            font-family: sans-serif; box-shadow: 0 0 15px #00ff00; display: none; width: 240px;
        ">
            <h4 style="margin:0 0 10px 0; text-align:center; color:white;">YANSITMA AYARLARI</h4>
            <label style="font-size:12px; color:#ddd;">🔗 Link:</label>
            <input type="text" id="img-url" placeholder="https://..." style="width: 95%; background: #333; color: white; border: 1px solid #666; padding: 5px; margin-bottom: 5px;">
            <button id="btn-link-yukle" style="width:100%; background:#444; color:white; border:1px solid #666; cursor:pointer; margin-bottom:10px;">Linkten Yükle</button>
            <label style="font-size:12px; color:#ddd;">📂 Dosya:</label>
            <input type="file" id="img-upload" accept="image/*" style="width:100%; font-size:11px; margin-bottom:10px; color:white;">
            <label style="font-size:12px;">Saydamlık:</label>
            <input type="range" id="opacity-slider" min="0" max="1" step="0.1" value="0.5" style="width:100%;">
            <button id="btn-gizle" style="width: 100%; background: #ff3333; color: white; font-weight: bold; border: none; padding: 5px; cursor: pointer; margin-top: 10px; border-radius: 4px;">RESMİ KALDIR</button>
        </div>
    `;

    const toggleButtonHTML = `
        <button id="ressam-toggle-btn" style="
            position: fixed; top: 10px; left: 10px; width: 50px; height: 50px;
            background: #222; color: #00ff00; border: 2px solid #00ff00; border-radius: 50%;
            font-size: 24px; cursor: pointer; z-index: 10000; box-shadow: 0 0 10px #00ff00;
            display: flex; align-items: center; justify-content: center;
        ">🎨</button>
    `;

    const searchPanelElement = document.createElement('div');
    searchPanelElement.id = 'babaSokucuPanel';
    searchPanelElement.innerHTML = `
        <div id="babaSokucuHeader">📱 Google Görsel Arama</div>
        <div id="babaSokucuContent">
            <input type="text" id="flagSearchInput" placeholder="Kelimeyi yazın (örn: kedi)">
            <button id="searchButton">🔍 ARA</button>
            <div id="flagImageContainer">
                <img id="flagImage" src="" alt="Resim">
                <span id="infoText" style="color:#555; text-align:center; padding:10px; font-size:12px;">Google'daki ilk resim burada görünecek.</span>
            </div>
            <button id="btn-transfer-img">🎨 EKRANA YANSIT</button>
        </div>
    `;

    const searchToggleBtn = document.createElement('button');
    searchToggleBtn.id = 'mobileToggleBtn';
    searchToggleBtn.innerHTML = '🔍<br>ARA';

    const container = document.createElement('div');
    container.innerHTML = toggleButtonHTML + overlayMenuHTML;
    document.body.appendChild(container);
    document.body.appendChild(searchPanelElement);
    document.body.appendChild(searchToggleBtn);

    // ==========================================
    // YENİ EKLENEN: DOĞRU CANVAS'I BULMA SİSTEMİ
    // ==========================================
    function anaCanvasBul() {
        // Gartic ana çizim tahtasını genellikle id="canvas" ile belirtir
        let anaCanvas = document.getElementById('canvas');
        if (anaCanvas) return anaCanvas;

        // Eğer ID değişmişse, ekrandaki alan olarak EN BÜYÜK canvas'ı buluruz
        // Çünkü profil fotoğrafları küçük, çizim tahtası büyüktür.
        const tumCanvaslar = document.querySelectorAll('canvas');
        let enBuyukCanvas = null;
        let maksimumAlan = 0;

        tumCanvaslar.forEach(c => {
            const rect = c.getBoundingClientRect();
            const alan = rect.width * rect.height;
            if (alan > maksimumAlan) {
                maksimumAlan = alan;
                enBuyukCanvas = c;
            }
        });

        return enBuyukCanvas;
    }

    // ==========================================
    // 4. CORE FONKSİYONLAR (YANSITMA - Script 1)
    // ==========================================

    function gorseliBaslat(sourceUrl) {
        // Eski 'document.querySelector' yerine yeni fonksiyonumuzu kullanıyoruz
        const oyunCanvas = anaCanvasBul();

        if (!oyunCanvas) {
            alert('Çizim alanı (Oyun tahtası) bulunamadı! Lütfen oyuna/odaya girdiğinizden emin olun.');
            return;
        }

        if (!overlayGorsel) {
            overlayGorsel = document.createElement('img');
            overlayGorsel.style.position = 'absolute';
            overlayGorsel.style.pointerEvents = 'none';
            overlayGorsel.style.zIndex = '100';
            document.body.appendChild(overlayGorsel);
        }

        overlayGorsel.src = sourceUrl;
        overlayGorsel.style.display = 'block';

        const currentOpacity = document.getElementById('opacity-slider').value;
        overlayGorsel.style.opacity = currentOpacity;

        pozisyonGuncelle();

        const menu = document.getElementById('ressam-menu');
        menu.style.display = 'block';
        menuAcik = true;
    }

    function pozisyonGuncelle() {
        if (!overlayGorsel || overlayGorsel.style.display === 'none') return;

        // Eski kod yerine yine yeni fonksiyonu kullanıyoruz
        const oyunCanvas = anaCanvasBul();
        if (!oyunCanvas) return;

        const rect = oyunCanvas.getBoundingClientRect();
        const scrollTop = window.pageYOffset || document.documentElement.scrollTop;
        const scrollLeft = window.pageXOffset || document.documentElement.scrollLeft;

        overlayGorsel.style.top = (rect.top + scrollTop) + 'px';
        overlayGorsel.style.left = (rect.left + scrollLeft) + 'px';
        overlayGorsel.style.width = rect.width + 'px';
        overlayGorsel.style.height = rect.height + 'px';
    }

    function dosyaOku(file) {
        if (!file || !file.type.startsWith('image/')) return;
        const reader = new FileReader();
        reader.onload = (e) => gorseliBaslat(e.target.result);
        reader.readAsDataURL(file);
    }

    // ==========================================
    // 5. CORE FONKSİYONLAR (ARAMA - Script 2)
    // ==========================================

    const flagSearchInput = document.getElementById('flagSearchInput');
    const flagImage = document.getElementById('flagImage');
    const infoText = document.getElementById('infoText');
    const transferButton = document.getElementById('btn-transfer-img');

    function searchGoogleImages(query) {
        if (!query) return;

        infoText.textContent = "Aranıyor...";
        infoText.style.display = 'block';
        flagImage.style.display = 'none';
        transferButton.style.display = 'none';

        const finalQuery = query;
        const apiUrl = `https://www.googleapis.com/customsearch/v1?key=${API_KEY}&cx=${SEARCH_ENGINE_ID}&q=${encodeURIComponent(finalQuery)}&searchType=image`;

        GM_xmlhttpRequest({
            method: "GET",
            url: apiUrl,
            onload: function(response) {
                const data = JSON.parse(response.responseText);
                if (data.error) {
                    infoText.textContent = "Hata oluştu.";
                    return;
                }
                if (data.items && data.items.length > 0) {
                    const imgLink = data.items[0].link;
                    flagImage.src = imgLink;
                    flagImage.style.display = 'block';
                    infoText.style.display = 'none';

                    // Resim bulundu, transfer butonunu göster ve linki ata
                    transferButton.style.display = 'block';
                    transferButton.onclick = function() {
                        gorseliBaslat(imgLink);
                    };

                } else {
                    infoText.textContent = "Resim bulunamadı.";
                }
            },
            onerror: function() {
                infoText.textContent = "Bağlantı hatası.";
            }
        });
    }

    // ==========================================
    // 6. EVENT LISTENER'LAR (OLAYLAR)
    // ==========================================

    document.getElementById('ressam-toggle-btn').addEventListener('click', () => {
        const menu = document.getElementById('ressam-menu');
        menuAcik = !menuAcik;
        menu.style.display = menuAcik ? 'block' : 'none';
    });

    document.getElementById('btn-link-yukle').addEventListener('click', () => {
        const url = document.getElementById('img-url').value;
        if (url) gorseliBaslat(url);
    });

    document.getElementById('img-upload').addEventListener('change', (e) => {
        if (e.target.files[0]) dosyaOku(e.target.files[0]);
    });

    document.getElementById('btn-gizle').addEventListener('click', () => {
        if (overlayGorsel) {
            overlayGorsel.style.display = 'none';
            overlayGorsel.src = '';
        }
    });

    document.getElementById('opacity-slider').addEventListener('input', (e) => {
        if (overlayGorsel) overlayGorsel.style.opacity = e.target.value;
    });

    searchToggleBtn.onclick = function() {
        const panel = document.getElementById('babaSokucuPanel');
        searchPanelAcik = !searchPanelAcik;
        panel.style.display = searchPanelAcik ? 'flex' : 'none';
    };

    document.addEventListener('keydown', (e) => {
        if (e.key === 'Insert') {
            searchToggleBtn.click();
        }
    });

    document.getElementById('searchButton').addEventListener('click', () => {
        searchGoogleImages(flagSearchInput.value.trim());
    });

    flagSearchInput.addEventListener('keyup', (e) => {
        if (e.key === 'Enter') searchGoogleImages(flagSearchInput.value.trim());
    });

    window.addEventListener('paste', (e) => {
        const items = (e.clipboardData || e.originalEvent.clipboardData).items;
        for (let item of items) {
            if (item.type.indexOf('image') === 0) {
                const blob = item.getAsFile();
                dosyaOku(blob);
            }
        }
    });

    window.addEventListener('dragover', (e) => e.preventDefault());
    window.addEventListener('drop', (e) => {
        e.preventDefault();
        if (e.dataTransfer.files[0]) dosyaOku(e.dataTransfer.files[0]);
    });

    window.addEventListener('resize', pozisyonGuncelle);
    setInterval(pozisyonGuncelle, 1000);

    dragElement(document.getElementById('babaSokucuPanel'));

    function dragElement(elmnt) {
        let pos1 = 0, pos2 = 0, pos3 = 0, pos4 = 0;
        const header = document.getElementById('babaSokucuHeader');
        if(!header) return;

        header.onmousedown = dragMouseDown;
        if(isMobile) header.ontouchstart = dragTouchStart;

        function dragMouseDown(e) {
            e.preventDefault();
            pos3 = e.clientX;
            pos4 = e.clientY;
            document.onmouseup = closeDragElement;
            document.onmousemove = elementDrag;
        }

        function dragTouchStart(e) {
            const touch = e.touches[0];
            pos3 = touch.clientX;
            pos4 = touch.clientY;
            document.ontouchend = closeDragElement;
            document.ontouchmove = elementDragTouch;
        }

        function elementDrag(e) {
            e.preventDefault();
            pos1 = pos3 - e.clientX;
            pos2 = pos4 - e.clientY;
            pos3 = e.clientX;
            pos4 = e.clientY;
            updatePos();
        }

        function elementDragTouch(e) {
            const touch = e.touches[0];
            pos1 = pos3 - touch.clientX;
            pos2 = pos4 - touch.clientY;
            pos3 = touch.clientX;
            pos4 = touch.clientY;
            updatePos();
        }

        function updatePos() {
            elmnt.style.top = (elmnt.offsetTop - pos2) + "px";
            elmnt.style.left = (elmnt.offsetLeft - pos1) + "px";
            elmnt.style.transform = 'none';
        }

        function closeDragElement() {
            document.onmouseup = null;
            document.onmousemove = null;
            document.ontouchend = null;
            document.ontouchmove = null;
        }
    }

})();