您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
Hide/remove games matching your keywords on GOG.com and collapse the grid slots they occupied
// ==UserScript== // @name GOG.com - Promo Filter // @namespace GOG.com - Promo Filter // @version 2.4 // @description Hide/remove games matching your keywords on GOG.com and collapse the grid slots they occupied // @author masterofobzene // @homepage https://github.com/masterofobzene/UserScriptRepo // @icon https://www.gog.com/favicon.ico // @match https://www.gog.com/*/games* // @grant none // @run-at document-end // @license GNU GPLv3 // ==/UserScript== (function() { 'use strict'; // — your forbidden words (case‐insensitive) — const filterWords = ['bundle', 'edition', 'supporter', 'halloween', 'christmas', 'soundtrack']; const hideMethod = 'remove'; // 'remove' or 'hide' const checkInterval = 1000; // ms // core filter routine function filterGames() { document .querySelectorAll('.product-tile:not([data-filtered])') .forEach(tile => { const titleEl = tile.querySelector('.product-tile__title, .product-tile__info__name'); if (!titleEl) return; const title = titleEl.textContent.trim().toLowerCase(); if (filterWords.some(w => title.includes(w))) { tile.setAttribute('data-filtered', 'true'); // climb up until our parent is the real grid/flex container let wrapper = tile; while ( wrapper.parentElement && !['grid', 'flex'].includes( window.getComputedStyle(wrapper.parentElement).display ) ) { wrapper = wrapper.parentElement; } // if we found that container, remove/hide the grid‐item itself if ( wrapper.parentElement && ['grid', 'flex'].includes( window.getComputedStyle(wrapper.parentElement).display ) ) { if (hideMethod === 'remove') { wrapper.remove(); } else { wrapper.style.display = 'none'; } } else { // fallback: hide the tile itself tile.style.display = 'none'; } } }); } // set up observers & intervals function init() { filterGames(); // watch for new tiles (infinite scroll, dynamic re-render) const obs = new MutationObserver(muts => { if (muts.some(m => m.addedNodes.length > 0)) { filterGames(); } }); obs.observe(document.body, { childList: true, subtree: true }); // belt‐and‐suspenders: interval re-check setInterval(filterGames, checkInterval); // clean up on page unload window.addEventListener('beforeunload', () => obs.disconnect()); } // **bootstrapping**: wait until at least one .product-tile exists const bootstrap = setInterval(() => { if (document.querySelector('.product-tile')) { clearInterval(bootstrap); init(); } }, 500); })();