Content Filter

Hide not interested content

Устаревшая версия за 14.04.2024. Перейдите к последней версии.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey, Greasemonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Userscripts.

Чтобы установить этот скрипт, сначала вы должны установить расширение браузера, например Tampermonkey.

Чтобы установить этот скрипт, вы должны установить расширение — менеджер скриптов.

(у меня уже есть менеджер скриптов, дайте мне установить скрипт!)

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

(у меня уже есть менеджер стилей, дайте мне установить скрипт!)

// ==UserScript==
// @name           Content Filter
// @name:ja        コンテンツフィルター
// @namespace      https://greasyfork.org/en/users/1264733
// @version        2024-04-14
// @description    Hide not interested content
// @description:ja 興味のない内容を隠す
// @author         LE37
// @license        MIT
// @include        https://forum.palemoon.org/viewforum*
// @include        https://forum.palemoon.org/viewtopic*
// @include        https://forum.vivaldi.net/category/*
// @include        https://forum.vivaldi.net/topic/*
// @include        https://kakuyomu.jp/pickup_works*
// @include        https://kakuyomu.jp/rankings/*
// @include        https://kakuyomu.jp/recent_works*
// @include        https://kakuyomu.jp/works/*/comments*
// @include        https://kakuyomu.jp/works/*/episodes/*
// @include        https://novelcom.syosetu.com/impression/*
// @include        https://yomou.syosetu.com/rank/*
// @include        https://syosetu.org/?mode=rank*
// @include        https://syosetu.org/?mode=review*
// @include        https://www.alphapolis.co.jp/novel/index*
// @include        https://www.alphapolis.co.jp/novel/ranking/*
// @include        https://www.alphapolis.co.jp/novel/*/comment*
// @include        https://www.ign.com/articles/*
// @include        https://www.yandex.com/search/*
// @include        https://yandex.com/search/*
// @exclude        https://www.alphapolis.co.jp/novel/ranking/annual
// @exclude        https://yomou.syosetu.com/rank/top/
// @grant          GM_registerMenuCommand
// @grant          GM_setValue
// @grant          GM_getValue
// ==/UserScript==

(()=>{
	'use strict';
	// GM Key
	let gMk;
	switch (location.host) {
		case "www.alphapolis.co.jp":
			gMk = "APS";
			break;
		case "syosetu.org":
			gMk = "HML";
			break;
		case "www.ign.com":
			gMk = "IGN";
			break;
		case "kakuyomu.jp":
			gMk = "KYU";
			break;
		case "novelcom.syosetu.com":
			gMk = "NUC";
			break;
		case "yomou.syosetu.com":
			gMk = "NRK";
			break;
		case "forum.palemoon.org":
			gMk = "PMF";
			break;
		case "forum.vivaldi.net":
			gMk = "VVF";
			break;
		case "yandex.com":
		case "www.yandex.com":
			gMk = "YDX";
			break;
		default:
			//console.log("DoNothing");
	}
	if (gMk) {
		RUN();
	}
	function RUN() {
		// GM Menu
		GM_registerMenuCommand("View", SVM);
		GM_registerMenuCommand("Save", USV);
		// cSr: ShadowsRoot, cFt: FireTime, eOn: MutationObserverNode, eIo: IntersectionObserverNode, eNo: Node, eUl: UserLink, sId: UserID, sTg: Tag, eAt: Alter;
		let cSr, cFt, eOn, eIo, eNo, eUl, sId, sTg, eAt;
		// Client Type
		const rMb = navigator.userAgent.includes("Mobile");
		const uRi = location.href;
		switch (gMk) {
			case "APS":
				// Alphapolis
				cFt = 0;
				if (uRi.includes("comment")) {
					// Comments
					eNo = "div.comment";
					eUl = "span.name>a";
				} else {
					// Ranking
					eNo = "div.section";
					eUl = "div.author>a";
					sTg = "li.tag a";
				}
				sId = /detail\/(\d+)$/;
				break;
			case "HML":
				// Hameln
				cFt = 0;
				eNo = rMb ? "div.search_box" : "div.section3";
				if (uRi.includes("rank")) {
					// Ranking
					eUl = "div.blo_title_sak a";
					sTg = "div.all_keyword:nth-child(9) a";
				} else {
					// Comments
					eUl = "h3>a:nth-child(1)";
				}
				sId = /((?<=uid=).*|(\d+)(?=\/))/;
				break;
			case "IGN":
				// IGN
				cSr = 1;
				cFt = 3;
				eIo = '#comments-section';
				eOn = '.spcv_conversation';
				eNo = "li";
				eUl = null;
				eAt = 'span[data-spot-im-class="message-username"]';
				sId = /(.*)/;
				break;
			case "KYU":
				// Kakuyomu
				if (uRi.includes("/pickup") || uRi.includes("/rank") || uRi.includes("/recent")) {
					// Ranking
					cFt = 0;
					eNo = "div.widget-work";
					eUl = "a.widget-workCard-authorLabel";
					sId = /users\/(.*)$/;
					sTg = "a[itemprop='keywords']";
				} else if (uRi.includes("comments")) {
					// Comments
					cFt = 2;
					eOn = '#__next';
					eNo = rMb ? 'div[class^="NewBox_box__"]>ul>li' : 'ul:nth-child(1) li';
					eUl = 'div.partialGiftWidgetActivityName>a';
				} else {
					// Comments in Episode
					cFt = 2;
					eOn = "#episodeFooter-cheerComments-panel-mainContents";
					eNo = "ul.widget-cheerCommentList li";
					eUl = "h5.widget-cheerComment-author a";
				}
				sId = /users\/(.*)$/;
				break;
			case "NUC":
				// Narou Comments
				cFt = 0;
				eNo = rMb ? "div.impression" : "div.waku";
				eUl = "div.comment_authorbox>div>a";
				eAt = "div.comment_authorbox>div";
				sId = /\/(\d+)/;
				break;
			case "NRK":
				// Narou Ranking
				cFt = 0;
				eNo = "div.p-ranklist-item";
				eUl = "div.p-ranklist-item__author a";
				sId = /\/(\d+)/;
				sTg = "div.p-ranklist-item__keyword a";
				break;
			case "PMF":
				// Palemoon Forum
				cFt = 0;
				if (uRi.includes("viewtopic")) {
					// Topic
					eNo = "#page-body div.post";
					eUl = 'a[class^="username"]';
					sId = /u=(\d+)/;
				} else {
					// Index
					eNo = "ul.topiclist>li";
					eUl = "div.topic-poster>a";
					sId = /u=(\d+)/;
				}
				break;
			case "VVF":
				// Vivaldi Forum
				cFt = 0;
				if (uRi.includes("topic")) {
					// Topic
					eNo = "ul.posts>li";
					eUl = "small.d-flex a";
					sId = /user\/(.*)/;
				} else {
					// Index
					eNo = "ul.topic-list li";
					eUl = "small.hidden-xs>a";
					sId = /user\/(.*)/;
				}
				break;
			case "YDX":
				// Yandex Search
				cFt = 0;
				eNo = rMb ? "div.serp-item" : "#search-result>li";
				eUl = rMb ? null : "div.Path>a.Link";
				eAt = "span.Path-Item>b";
				sId = rMb ? /(.*)/ : /\/([^\/]+)/;
				break;
		}
		// Read List
		const URD = GM_getValue(gMk);
		let tlo = URD ? URD : { BAL:[], BTL:[] };
		const tal = tlo.BAL;
		const ttl = tlo.BTL;
		// Save List
		function USV() {
			tlo = { BAL:tal, BTL:ttl };
			GM_setValue(gMk, tlo);
		}
		// Select View
		let cSv = 0;
		// Script Fire Time
		switch (cFt) {
			case 1:
				RSC();
				break;
			case 2:
				MOC();
				break;
			case 3:
				IOC();
				break;
			case 0:
			default:
				FTR();
		}
		// ReadyState
		function RSC() {
			document.addEventListener("readystatechange", (e) => {
				if (e.target.readyState === "complete") {
					FTR();
				}
			});
		}
		// MutationObserver
		function MOC() {
			const obs = new MutationObserver(() => {
				FTR();
				//obs.disconnect();
			});
			// Shadowroot spotim fix
			const obn = cSr ? document.querySelector('div[data-spotim-module]').firstElementChild.shadowRoot.querySelectorAll(eOn)[0] : document.querySelector(eOn);
			obs.observe(obn, {
				childList: true,
				subtree: true
			});
		}
		// IntersectionObserver
		function IOC() {
			const ioc = new IntersectionObserver((entries) => {
				if (entries[0].intersectionRatio <= 0) return;
				FTR();
				// IGN fix
				if (gMk === "IGN") {
					MOC();
				}
				ioc.disconnect();
			});
			ioc.observe(document.querySelector(eIo));
		}
		// Filtering
		function FTR() {
			// Shadowroot spotim fix
			// ShadowHost, ShadowRoot
			let eSh, eSr;
			if (cSr) {
				eSh = document.querySelector('div[data-spotim-module]').firstElementChild;
				if (eSh) {
					eSr = eSh.shadowRoot;
				}
				//console.log(eSr);
			}
			const no = cSr ? eSr.querySelectorAll(eNo) : document.querySelectorAll(eNo);
			for (let i = 0; i < no.length; i++) {
				let rBk = false;
				let uId;
				// Filtering content contain single id(link) or text
				let eLk = eUl ? no[i].querySelector(eUl) : no[i].querySelector(eAt);
				if (eLk !== null || gMk === "NUC") {
					// Narou nologin user fix
					if (!eLk) {
						eLk = no[i].querySelector(eAt);
						uId = no[i].querySelector(eAt).textContent.split("\n")[2];
					} else {
						uId = eUl ? eLk.href.match(sId)[1] : eLk.textContent.match(sId)[1];
					}
					//console.log(uId);
					rBk = CHK(eLk, tal, uId);
				}
				if (!rBk) {
					// Filtering content contain multiple tags(text)
					const tno = no[i].querySelectorAll(sTg);
					if (tno !== null) {
						for (let j = 0; j < tno.length; j++) {
							const tag = tno[j].textContent;
							//console.log(tag);
							rBk = CHK(tno[j], ttl, tag);
							if (rBk) {
								break;
							}
						}
					}
				}
				// Blocked Show Type
				if (cSv === 0) {
					no[i].style.visibility = rBk ? "hidden" : "visible";
					no[i].style.opacity = "1";
				} else {
					no[i].style.visibility = "visible";
					no[i].style.opacity = rBk ? "0.5" : "1";
				}
			}
		}
		// CheckKeyword
		function CHK(ele, l, s) {
			const result = l.some((v) => s === v);
			if (cSv === 1) {
				ele.style.border = result ? "thin solid lime" : "thin solid red";
			} else {
				ele.style.border = "none";
			}
			return result;
		}
		// SelectViewMode
		function SVM() {
			if (cSv === 0) {
				cSv = 1;
				// Disable default click
				document.addEventListener("click", PAC, true);
			} else {
				cSv = 0;
				// Disable default click
				document.removeEventListener("click", PAC, true);
				// AutoSave
				USV();
			}
			FTR();
		}
		// PreventAnchorChange
		function PAC(e) {
			e.preventDefault();
		  	e.stopPropagation();
			const targetElement = cSr ? e.composedPath()[0] : e.target;
			//console.log(targetElement);
			let eLk;
			// Narou nologin user fix
			if (gMk === "NUC") {
				eLk = targetElement.href ? eUl : eAt;
			} else {
				eLk = eUl ? eUl : eAt;
			}
			if (targetElement.closest(eLk)) {
				let ai;
				switch (gMk) {
					// Narou nologin user fix
					case "NUC":
						ai = targetElement.href ? targetElement.href.match(sId)[1] : targetElement.textContent.split("\n")[2];
						break;
					// Yandex fix
					case "YDX":
						ai = targetElement.href ? targetElement.href.match(sId)[1] : targetElement.parentElement.href.match(sId)[1];
						break;
					default:
						ai = eUl ? targetElement.href.match(sId)[1] : targetElement.textContent.match(sId)[1];
				}
				//console.log(ai);
				UTL(e, ai, tal);
			} else if (targetElement.closest(sTg)) {
				const kd = targetElement.textContent;
				UTL(e, kd, ttl);
			}
			FTR();
			return false;
		}
		// UpdateTempList
		function UTL(e, s, l) {
			const li = l.findIndex((v) => v === s);
			if (li !== -1) {
				l.splice(li,1);
			} else {
				l.push(s);
			}
			//console.log(l);
			return l;
		}
	}
})();