// ==UserScript== // @name Flag Randomizer // @namespace http://ponepaste.org/5555 // @match https://boards.4channel.org/mlp/thread/* // @match https://boards.4chan.org/mlp/thread/* // @grant none // @version 1.18 // @author Fillyanon, ScriptFilly // @description Adds a flag randomizer to the Board. // ==/UserScript== 'use strict' let changeFlagOnKeyStroke = true; const flags = Object.freeze({ MISC: ["4CC", "AN"], G4: [ "AJ", "ANF", "APB", "AU", "BB", "BM", "BP", "BS", "CB", "CG", "CHE", "CL", "CO", "DAY", "DD", "DER", "DIS", "DT", "FAU", "FL", "FLE", "GI", "LI", "LT", "LY", "MA", "MAU", "MIN", "NI", "NUR", "OCT", "PAR", "PC", "PCE", "PI", "PLU", "PM", "QC", "RAR", "RD", "RLU", "S1L", "SCO", "SHI", "SIL", "SP", "SPI", "STA", "STL", "SUN", "SUS", "SWB", "TS", "TWI", "TX", "VS", "ZE", ], G5: ["HT", "IZ", "PP", "SPT", "ZS", "SS"], EQG: [ "ADA", "AB", "SON", "EQA", "EQF", "EQP", "EQR", "EQT", "EQI", "EQS", "ERA", ], TFH: ["TFA", "TFO", "TFP", "TFS", "TFT", "TFV", "TP"], }); // Collects all flags into a single, flat array. const allFlags = Object.values(flags).flat(); // Returns a random element from an array. const getRand = (coll) => { return coll[Math.floor(Math.random() * coll.length)]; }; const makeOpt = (option) => { const opt = document.createElement("option"); opt.value = opt.innerText = option; selector.appendChild(opt); } const getPost = (use4chanX) => { let post = (use4chanX !== "") ? use4chanX : document.forms.post; return post; } let handler = false; const changeFlag = () => { let flagSelector = post.querySelector(".flagSelector"); if (selector.value == "OFF") return; flagSelector.value = (selector.value != "ALL") ? getRand(flags[selector.value]) : getRand(allFlags); } const selector = document.createElement("select"); const botLine = document.querySelector('.navLinksBot'); selector.style = "margin-left: 1rem;"; selector.addEventListener("change", () => { window.localStorage.setItem("flagGroup", selector.value); }); Object.keys(flags).forEach((key) => {makeOpt(key);}); makeOpt("ALL"); makeOpt("OFF"); selector.value = window.localStorage.getItem("flagGroup") ?? "G4"; botLine.appendChild(selector); function debounce(func, wait, immediate) { var timeout; return function() { var context = this, args = arguments; var later = function() { timeout = null; if (!immediate) func.apply(context, args); }; var callNow = immediate && !timeout; clearTimeout(timeout); timeout = setTimeout(later, wait); if (callNow) func.apply(context, args); }; } var myEfficientFn = debounce(function() { changeFlag(); }, 250, false); let handled = true; if (changeFlagOnKeyStroke == true) { const config = {attributes: true, childList: true, subtree: true}; const callback = function (mutations, _) { for (const mutation of mutations) { if (mutation.type === 'childList') { // When new child is added let use4chanX = document.getElementById("qr") ?? document.getElementById("quickReply") ?? ""; post = getPost(use4chanX); // Do nothing if post is not loaded if (post == null || post == undefined) {return;} // Else update the flag let reply = (use4chanX !== "") ? use4chanX.childNodes[1][5] : post[8]; reply.addEventListener('input', myEfficientFn); } } }; const observer = new MutationObserver(callback); observer.observe(document, config); } else { setInterval(() => { let use4chanX = document.getElementById("qr") ?? ""; post = getPost(use4chanX); if (post == null || post == undefined) { return; } changeFlag(); }, 500); }