Time Hooker

Hook the wait timers for websites that use them to delay content

Stan na 29-11-2024. Zobacz najnowsza wersja.

Aby zainstalować ten skrypt, wymagana jest instalacje jednego z następujących rozszerzeń: Tampermonkey, Greasemonkey lub Violentmonkey.

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

Aby zainstalować ten skrypt, wymagana jest instalacje jednego z następujących rozszerzeń: Tampermonkey, Violentmonkey.

Aby zainstalować ten skrypt, wymagana będzie instalacja rozszerzenia Tampermonkey lub Userscripts.

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

Aby zainstalować ten skrypt, musisz zainstalować rozszerzenie menedżera skryptów użytkownika.

(Mam już menedżera skryptów użytkownika, pozwól mi to zainstalować!)

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

Będziesz musiał zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

Będziesz musiał zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

Musisz zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

(Mam już menedżera stylów użytkownika, pozwól mi to zainstalować!)

// ==UserScript==
// @name         Time Hooker
// @namespace    https://tampermonkey.net/
// @version      1.1
// @description  Hook the wait timers for websites that use them to delay content
// @author       Niteesh
// @match        *://*/*
// @grant        none
// @license      MIT
// @run-at       document-start
// ==/UserScript==


(function() {
    'use strict';
    
    const originalSetInterval = window.setInterval;
    const originalSetTimeout = window.setTimeout;
    
    function print() {
        console.log(...arguments);
    }
    
    function clearAllTimers() {
        const highestIntervalId = setInterval(() => {}, 0);
        for (let i = 0; i <= highestIntervalId; i++) {
            clearInterval(i);
        }
    
        const highestTimeoutId = setTimeout(() => {}, 0);
        for (let i = 0; i <= highestTimeoutId; i++) {
            clearTimeout(i);
        }
    
        print('Cleared all active timers.');
    }
    
    function restoreOriginalTimers() {
        window.setInterval = originalSetInterval;
        window.setTimeout = originalSetTimeout;
        print("Restoring done.");
    }
    
    function interceptTimers(val) {
        window.setTimeout = function(callback, delay, ...args) {
            const newDelay = delay / val;
            print(`[Intercepted] setTimeout: ${delay}ms -> ${newDelay}ms`);
            return originalSetTimeout(callback, newDelay, ...args);
        };

        window.setInterval = function(callback, interval, ...args) {
            const newInterval = interval / val;
            print(`[Intercepted] setInterval: ${interval}ms -> ${newInterval}ms`);
            return originalSetInterval(callback, newInterval, ...args);
        };
    }
	interceptTimers(15);
    let timerUsed = false;
    let potentialTimers = undefined;
    
    window.onload = function() {
    
        potentialTimers = [...document.querySelectorAll('*')].filter(el => {
    		const text = el.textContent.trim().toLowerCase();
    		const waitRegexes = [
                /wait\s+\d+\s+seconds/i,          
                /please\s+wait/i,                
                /click\s+on\s+(image|button)/i, 
                /click\s+and\s+wait\s+\d+/i
            ];
            return waitRegexes.some(regex => regex.test(text));
    		//return /wait\s+\d+\s+seconds/i.test(text) || /please\s+wait/i.test(text);
    	});
    	if (potentialTimers.length > 0) {
    		print("Potential timers detected:", potentialTimers);
    		timerUsed = true;
    
    	} else {
    		print("No timers detected.");
    		clearAllTimers();
        	restoreOriginalTimers();
    	}
    	
    	if (timerUsed) {
            print("Hacking...");
            
            originalSetInterval(() => {
                const button = document.querySelector('button:enabled, .clickable');
        		const clickable = [...document.querySelectorAll('*')].find(el => 
        			(el.textContent.toLowerCase().includes("continue") || el.textContent.toLowerCase().includes("get link")) && 
        			(el.tagName === 'BUTTON' || el.tagName === 'A') && !el.disabled
        		);
    
        		if (clickable) {
        			print("Clickable element found:", clickable);
        			if (clickable.tagName === 'BUTTON') {
        			     clickable.click();
        			} else if (clickable.tagName === 'A') {
        			     print(clickable.href);
        			     window.location.replace(clickable.href);
        			} else {
        			     print("just trying to click, do you find the exact button?");
        			     clickable.click();
        			}
        			
        		} else {
        			print("No clickable element with found.");
        		}
    		}, 1000);
            
            // dynamically searching for a button
    		const observer = new MutationObserver((mutations) => {
    			mutations.forEach(mutation => {
    				const button = [...document.querySelectorAll('*')].find(el => 
    					(el.textContent.toLowerCase().includes("continue") || el.textContent.toLowerCase().includes("get link")) &&
    					(el.tagName === 'BUTTON' || el.tagName === 'A') && !el.disabled
    				);
    				if (button) {
    					print("Dynamically loaded 'continue' button found:", button);
    					observer.disconnect(); // Stop observing once found
                        button.click();
    					print("clicked");
    				}
    			});
    		});
    
    		// Start observing changes in the DOM
    		observer.observe(document.body, {
    			childList: true,
    			subtree: true
    		});
    	} else {
			clearAllTimers();
        	restoreOriginalTimers();
		}
    }

})();