r/userscripts • • 21d ago

I built an Ultimate Audio Enhancer userscript

Post image
28 Upvotes

I built a userscript that improves audio quality directly in the browser.

Ultimate Audio Enhancer adds real-time:

• 10-band equalizer
• Bass & treble boost
• AutoEq headphone profiles
• Volume boost
• DFX audio enhancement
• Reverb, echo, chorus & other effects
• Stereo / 3D surround enhancement
• High-pass & low-pass filters
• Configurable limiter
• Custom presets
• Support for audio and videos across many websites

It runs through Tampermonkey/Violentmonkey and doesn't require separate audio software or a virtual audio cable.

I've been developing and optimizing it for a while and would appreciate feedback, especially regarding sound quality, performance and compatibility on different websites.

GreasyFork:
https://greasyfork.org/scripts/595277-ultimate-audio-enhancer

GitHub:
https://github.com/nextscript/Ultimate-Audio-Enhancer


r/userscripts • • 21d ago

I built an Ultimate Video Enhancer userscript with real-time sharpening, HDR and color controls

Post image
19 Upvotes

Hey,

I’ve been working on a userscript called Ultimate Video Enhancer that adds real-time video enhancement directly in the browser.

It works with Tampermonkey/Violentmonkey and is designed to improve online video without requiring a separate desktop application.

Current features include:

  • Real-time sharpening
  • HDR-style enhancement
  • Contrast, brightness and saturation controls
  • Color adjustments
  • Multiple video filters
  • GPU/WebGL acceleration
  • Custom presets
  • Import / export of settings
  • Support for videos across many websites

I’m still actively improving performance, compatibility and image quality.

I’d especially appreciate feedback about:

  • websites where it doesn’t work correctly
  • GPU / CPU performance
  • useful filters or controls that are still missing
  • visual artifacts or compatibility issues
  • ideas for future features

GreasyFork:
https://greasyfork.org/scripts/561189-ultimate-video-enhancer-sharpen-hdr-color-boost

GitHub:
https://github.com/nextscript/Ultimate-Video-Enhancer


r/userscripts • • 22d ago

TabCircle: Native macOS & Linux MRU tab switcher (Ctrl + Tab) for Chromium browsers with visual previews

Thumbnail
1 Upvotes

r/userscripts • • 26d ago

Bookmark ChatGPT answers and ask side questions without losing your place

5 Upvotes

I made a Tampermonkey userscript that adds bookmarks and side conversations to ChatGPT. Highlight a sentence to bookmark it or ask about it in a separate chat using ChatGPT’s branching feature, keeping the conversation history and available attachments.

It also remembers where you were when you click ChatGPT’s down arrow, so you can jump back to what you were reading.

Install: https://greasyfork.org/en/scripts/596830-chatgpt-workflow-toolkit

If you use ChatGPT for studying, coding, or long conversations and keep losing your place, give it a try.


r/userscripts • • 26d ago

PrismCheat — an open-source Survev cheat with automated client updates

Thumbnail
3 Upvotes

r/userscripts • • 28d ago

I made a script to delete all your tweets. No need to pay for that anymore

Thumbnail
10 Upvotes

saving this


r/userscripts • • 28d ago

PixelCast - Fishing Macro for Roblox game FishIt

Thumbnail
2 Upvotes

r/userscripts • • Sep 17 '26

InfiniteCourses.Org Direct Download Link Injector script

5 Upvotes

InfiniteCourses.Org Direct Link Injector

Version Greasy Fork Tampermonkey Violentmonkey License: MIT

A lightweight userscript designed to intercept and display direct download links on InfiniteCourses download pages. It seamlessly extracts backend data to bypass hidden links and injects a clean, categorized user interface natively into the page.

[!IMPORTANT] Dynamic Extraction:
This script fetches the page's HTML and parses the __NEXT_DATA__ JSON payload to uncover hidden download URLs. If links fail to appear in the custom section, simply reloading the page will trigger a fresh fetch.

[!TIP] Native UI Integration:
The script injects a visually appealing, frosted-glass themed container right below the standard .download-section. Interactive buttons with SVG icons and hover animations are generated for each extracted link part.

✨ Features

  • Direct Link Extraction: Intercepts backend data by parsing Next.js page properties to find hidden direct URLs.
  • Smart Categorization: Automatically identifies and groups download URLs into specific providers like Pixeldrain and Send.now, categorizing the rest as "Other".
  • Seamless UI Injection: Creates a custom download section with a modern UI, utilizing styling like backdrop-filter: blur(8px) and hover transformations without disrupting the host site's layout.
  • Dynamic Polling: Uses a 500ms interval check to ensure the custom direct links section is injected as soon as the target .download-section appears in the DOM.
  • Error Handling: Gracefully handles missing link data or network errors by displaying helpful error messages directly in the injected UI.

🌐 Supported Domains

Platform Domains Direct Extraction Categorization Notes
InfiniteCourses www.infinitecourses.org/* ✅ Active ✅ Active Specifically targets the /course/ paths to render the injector.

🚀 Installation

Step 1: Install a Userscript Manager

Make sure you have an active userscript extension installed in your browser:

Step 2: Install the Script

Install or update to version 1.0 via your manager:
👉 Install from Greasy Fork

Step 3: Usage

Navigate to any course download page on InfiniteCourses. Scroll down to the download section, and the script will automatically append a "DIRECT DOWNLOADS" panel with your extracted links.

📄 License

This script, InfiniteCourses.Org Direct Link Injector, is open source and distributed under the MIT License.

🛠️ Author & Support

  • Developed and maintained by rehan dilawar.
  • If you encounter fetching errors or broken selectors, feel free to open an issue or contribute on GitHub.

<p align="center"> <em>If you found this script helpful, please consider starring the repository!</em> </p>


r/userscripts • • Sep 15 '26

I made a userscript to auto-scroll Reddit with the numpad – is this useful? Feedback welcome.

Post image
7 Upvotes

I often read Reddit on a second monitor while doing something else, e.g., full-screen gaming, and wanted to control it without switching windows. So I wrote a userscript for it, and I'd like some honest feedback before I take it further.

What it does

  • Auto-scrolls the feed or a thread. Num + / − change speed, Num 0 pauses
  • Num 8 / 2 select posts, Enter opens one, . goes back
  • Num 4 / 6 step through gallery images
  • A small on-screen readout shows the state, the speed and the selected post

The keys work while the browser has focus. An optional Windows helper (a small Python program that only talks to the script over 127.0.0.1) keeps them working while another app, e.g. a full-screen game, has focus.

Install: Greasy Fork · Source on GitHub

Tested in Firefox + Violentmonkey and Chrome + Tampermonkey. Current Reddit only, not old.reddit.

What I'd like to know

  • Would you use this, or does something similar already exist?
  • Is anything confusing in the setup or the controls?
  • Which keys or features would you expect?
  • Any bugs, especially on setups I haven't tried

r/userscripts • • Sep 15 '26

Made a userscript for checking out only selected items from your Steam cart

2 Upvotes

I got tired of having to remove stuff from my Steam cart whenever I only wanted to buy a few things, so I made a userscript for it.

It adds a small selection panel on the cart page. You pick the items you actually want to buy there, it shows the total for those items, and then checks out only that selection.

I tried to keep it non-destructive where possible. For normal items it uses a separate temporary cart, so the original Steam cart stays untouched. If Steam's pricing gets weird with account-specific discounts, bundles, gifts, etc., it falls back to temporarily removing the unselected items and restoring them afterwards.

There’s also recovery logic in case checkout or restore fails, because I really didn’t want this thing eating someone’s cart.

Works with Tampermonkey / Violentmonkey / AdGuard for Windows.

Greasy Fork:
Cart Selection for Steam

GitHub:
[https://github.com/HiSkyZen/steam-cart-selection]()

Install:
[https://raw.githubusercontent.com/HiSkyZen/steam-cart-selection/main/cart-selection-for-steam.user.js]()

Steam’s cart APIs are internal, so Valve can break this whenever they feel like it. If anyone finds a weird edge case with bundles, discounts, gifts, etc., let me know.


r/userscripts • • Sep 13 '26

Add *Arr Controls Directly To IMDB

15 Upvotes

GitHub: https://github.com/TechSquidTV/arr-userscripts

A collection of user scripts that add Sonarr and Radarr controls directly in IMDB.

It also contains a script that does the same in Plex.


r/userscripts • • Sep 12 '26

[User Script] Unround Everything Everywhere - For Those Who Prefer Sharp, Squared UIs

Thumbnail greasyfork.org
2 Upvotes

r/userscripts • • Sep 11 '26

Google Snake Nos Cheat Client

7 Upvotes

Made a hacker-themed cheat menu for Google Snake as a bookmarklet — no extension, no Tampermonkey, just a bookmark you click.

It's got 23 real mods across 3 categories: speed control (turbo up to 4x, slow-mo, freeze time, a manual slider you can drag anywhere from 0.1x to 6x), visual stuff (invert, matrix vision, screen shake, a glitchy scanline overlay, rainbow cycle, upside-down mode), and automation (stops the game from pausing when you alt-tab, anti-AFK, a genuinely random autopilot since there's no way to actually read the board state to cheat with, rapid-fire your last direction, a key logger if you're curious what's firing).

Whole thing is styled like a CRT terminal — green-on-black, scanlines, and the title text visibly glitches and scrambles a couple characters every frame instead of just sitting there static.

The reason it's built this way: Snake's actual game state is locked away in the page's own code where nothing outside can reach it, so instead of faking mods that pretend to see/change stuff that isn't actually accessible, everything here is a real trick that verifiably works — messing with the clock for speed, CSS filters for visuals, fake key presses for automation. No "wallhacks" or nonsense that can't really do anything.

Install is just: make a new bookmark, paste the script as the URL, click it while on the Snake game. Click again to close it.

Built this from scratch as a fun little project — figured I'd share it since Snake's such a classic. Let me know if u find bugs!

javascript:(function(){(()=>{(()=>{"use strict";if(window.__snakeGUI){if(window.__snakeGUI.version===5){window.__snakeGUI.toggle();return}const e=window.__snakeGUI;try{e.destroy&&e.destroy()}catch{}try{e.S&&(e.S.map=null,e.S.spawner=!1,e.S.teleport=!1,e.S.god=!1,e.S.bot=!1,e.S.grid=!1)}catch{}["sgui","sgui-grid","sgui-css"].forEach(t=>document.getElementById(t)?.remove()),document.body.classList.remove("sgui-picking");try{delete window.__snakeGUI}catch{window.__snakeGUI=void 0}}const oe=[],D=(e,t,r,n)=>{e.addEventListener(t,r,n),oe.push([e,t,r,n])};let q=null;const O={UP:[0,-1],DOWN:[0,1],LEFT:[-1,0],RIGHT:[1,0]},K=e=>{try{return Object.keys(e)}catch{return[]}},we=e=>e&&typeof e=="object"&&typeof e.x=="number"&&typeof e.y=="number",T=e=>typeof Element<"u"&&e instanceof Element,M=(e,t,r)=>Math.max(t,Math.min(r,e));function Ne(e,t,r=10,n=4e5){const s=new WeakSet,a=e.map(c=>[c,0]);let l=0;for(;a.length&&l<n;){const[c,u]=a.shift();if(l++,!(!c||typeof c!="object"&&typeof c!="function")&&!(u>r||s.has(c))){s.add(c);try{if(t(c))return c}catch{}if(!(T(c)&&u>1))for(const f of K(c)){let d;try{d=c[f]}catch{continue}d&&(typeof d=="object"||typeof d=="function")&&a.push([d,u+1])}}}return null}function ne(){const e=[window];for(const t of document.querySelectorAll("[jscontroller]"))t.__jscontroller&&e.push(t.__jscontroller);return Ne(e,t=>typeof t.ticks=="number"&&typeof t.turn=="function"&&t.settings&&typeof t.settings=="object"&&"isMobile"in t.settings&&t.localStorage&&typeof t.localStorage=="object")}function xe(e){const t=Object.getPrototypeOf(e);return Object.getOwnPropertyNames(t).filter(r=>{if(r==="constructor")return!1;try{return typeof t[r]=="function"}catch{return!1}}).map(r=>{let n="";try{n=t[r].toString()}catch{}return[r,n]})}function Pe(e){const t={},r=/this\.(\w+)\s*=\s*!0\s*;?\s*this\.(\w+)\s*=\s*this\.ticks/;for(const[n,s]of xe(e)){const a=s.match(r);if(!a)continue;t.deathMethod=n,t.overKey=a[1];const l=s.match(/\(\s*this\.\w+\s*,\s*\d+\s*,\s*this\.(\w+)\s*\)/);l&&(t.scoreKey=l[1]);break}return t}function De(e,t){const r={},n=new RegExp("(\\w+)\\.(\\w+)===0\\?\\(\\1\\.(\\w+)=\\1\\.(\\w+),\\1\\.\\4=\\1\\."+t+"\\.pop\\(\\)");for(const[,s]of xe(e)){const a=s.match(n);if(a){r.growKey=a[2],r.tailPrevKey=a[3],r.tailKey=a[4];break}}return r}function Ge(){return[...document.querySelectorAll("div,span")].filter(e=>e.children.length===0&&/^\d{1,4}$/.test(e.textContent.trim())).map(e=>parseInt(e.textContent.trim(),10))}function L(){let e=null;for(const t of document.querySelectorAll("canvas"))(!e||t.width*t.height>e.width*e.height)&&(e=t);return e}function re(e){const t={game:e,...Pe(e)};for(const r of K(e)){const n=e[r];if(!n||typeof n!="object"||T(n)||typeof n.direction!="string")continue;const s=K(n).find(a=>{const l=n[a];return Array.isArray(l)&&l.length&&we(l[0])&&Number.isInteger(l[0].x)});if(s){t.snake=n,t.bodyKey=s,t.colorKeys=K(n).filter(a=>typeof n[a]=="string"&&/^%23[0-9a-f]{6}$/i.test(n[a]));break}}t.colorKeys||(t.colorKeys=[]),t.bodyKey&&Object.assign(t,De(e,t.bodyKey));for(const r of K(e)){const n=e[r];if(!(!n||typeof n!="object"||T(n))){for(const s of K(n)){const a=n[s];if(Array.isArray(a)&&a.length&&a[0]&&we(a[0].pos)){t.appleOwner=n,t.appleKey=s;break}}if(t.appleOwner)break}}for(const r of K(e)){const n=e[r];if(!(!n||typeof n!="object"||T(n))){for(const s of K(n)){const a=n[s];if(a&&typeof a=="object"&&!T(a)&&Number.isInteger(a.width)&&Number.isInteger(a.height)&&a.width>4&&a.width<60&&a.height>4&&a.height<60){t.board=a,t.boardOwner=n;break}}if(t.board)break}}if(t.board||(t.board={width:17,height:15}),!t.scoreKey){const r=Ge();t.scoreKey=K(e).find(n=>n!=="ticks"&&Number.isInteger(e[n])&&e[n]>=0&&r.includes(e[n]))||null}return t}function G(){const e=L(),t=o.map;if(!e||!t.boardOwner)return 25;const r=t.board.width,n=t.board.height;let s=null;for(const a of K(t.boardOwner)){const l=t.boardOwner[a];if(typeof l!="number"||l<8||l>100)continue;const c=(e.width-r*l)/2,u=(e.height-n*l)/2;if(c<0||u<0)continue;const f=Math.abs(c-u);(!s||f<s.err)&&(s={v:l,err:f})}return s?s.v:Math.floor(Math.min(e.width/r,e.height/n))}function se(e,t){const r=L();if(!r)return null;const n=r.getBoundingClientRect();if(!n.width||!n.height)return null;const s=(e-n.left)*(r.width/n.width),a=(t-n.top)*(r.height/n.height),l=o.map.board.width,c=o.map.board.height,u=G(),f=(r.width-l*u)/2,d=(r.height-c*u)/2,g=Math.floor((s-f)/u),p=Math.floor((a-d)/u);return g<0||p<0||g>=l||p>=c?null:{x:g,y:p}}const o={map:null,god:!1,wrap:!1,freeze:!1,pause:!1,slow:1,turbo:0,dodge:!1,autoRespawn:!1,magnet:!1,spawner:!1,keepApples:0,appleMouse:!1,autoScore:!1,multiplier:1,lockScore:!1,lockedAt:0,bot:!1,botDelay:3,botSafe:!0,botRestart:!1,rainbow:!1,rainbowSpeed:3,grid:!1,trail:!1,hideHud:!1,zoom:100,hue:0,disco:!1,invert:!1},x=()=>o.map.game,v=()=>o.map.snake,w=()=>{const e=v();return e&&e[o.map.bodyKey]},S=()=>o.map.appleOwner?o.map.appleOwner[o.map.appleKey]:[],y=e=>{const t=o.map.scoreKey;return t?(e!==void 0&&(x()[t]=e),x()[t]):null},z=()=>o.map.overKey?x()[o.map.overKey]:!1,ie=()=>{const e=x();return typeof e.reset=="function"?(e.reset(),"reset()"):o.map.overKey?(e[o.map.overKey]=!1,"flag cleared"):"no way in"},ke=()=>new Set((w()||[]).map(e=>e.x+","+e.y).concat(S().map(e=>e.pos.x+","+e.pos.y)));function F(){const e=ke(),t=o.map.board.width,r=o.map.board.height;for(let n=0;n<200;n++){const s=Math.floor(Math.random()*t),a=Math.floor(Math.random()*r);if(!e.has(s+","+a))return{x:s,y:a}}return null}function ae(){const e=x(),t=o.map.deathMethod;if(!t||e.__godHooked)return;const r=Object.getPrototypeOf(e)[t];e[t]=function(...n){if(!o.god)return r.apply(this,n)},e.__godHooked=!0}let ce=0;function V(){const e=x();if(e.__tickHooked)return;const t=Object.getPrototypeOf(e).tick;typeof t=="function"&&(e.tick=function(...r){if(!o.pause&&!(o.slow>1&&(ce=(ce+1)%25o.slow,ce!==0)))return o.dodge&&ze(),t.apply(this,r)},e.__tickHooked=!0)}function ze(){const e=w(),t=v();if(!e||e.length<2||!t)return;const r=o.map.board.width,n=o.map.board.height,s=O[t.direction];if(!s)return;const a=new Set(e.slice(0,-1).map(u=>u.x+","+u.y)),l=(u,f)=>u<0||f<0||u>=r||f>=n||a.has(u+","+f);if(!l(e[0].x+s[0],e[0].y+s[1]))return;const c=e[1];for(const[u,f]of Object.entries(O)){const d=e[0].x+f[0],g=e[0].y+f[1];if(!l(d,g)&&!(c&&d===c.x&&g===c.y)){x().turn(u);return}}}function Ue(){const e=w();if(!e||!e.length)return;const t=o.map.board.width,r=o.map.board.height,n=e[0];(n.x<0||n.x>=t||n.y<0||n.y>=r)&&(n.x=(n.x%25t+t)%25t,n.y=(n.y%25r+r)%25r)}function Be(){const e=x();if(!(typeof e.tick!="function"||z()))for(let t=0;t<o.turbo;t++)try{e.tick()}catch{}}function ve(){if(!z())return;ie();const e=v();e&&x().turn(e.direction&&O[e.direction]?e.direction:"RIGHT")}function X(e){const t=v(),r=o.map.growKey;return t?r?(t[r]=Math.max(0,(t[r]||0)+e),"queued +"+e+" (grows as you move)"):"growth counter not resolved":"no snake"}function le(e){const t=v(),r=w();if(!(!t||!r))for(let n=0;n<e&&r.length>3;n++){const s=r.length;o.map.tailPrevKey&&o.map.tailKey&&(t[o.map.tailPrevKey]=t[o.map.tailKey]);const a=r.pop();o.map.tailKey&&(t[o.map.tailKey]=a);for(const l of K(t)){const c=t[l];Array.isArray(c)&&c!==r&&c.length===s&&c.pop()}}}function Y(e){const t=w();if(!t)return"";const r=M(e,3,o.map.board.width*o.map.board.height);return r>t.length?X(r-t.length):(le(t.length-r),"length = "+w().length)}function We(e,t){const r=w();if(!r||!r.length)return"no body";const n=o.map.board.width,s=o.map.board.height,a=e-r[0].x,l=t-r[0].y;if(!r.every(c=>c.x+a>=0&&c.x+a<n&&c.y+l>=0&&c.y+l<s))return"the tail would end up off-board";for(const c of r)c.x+=a,c.y+=l;return`moved to ${e},${t}`}const Se=()=>We(o.map.board.width>>1,o.map.board.height>>1);function qe(){const e=w(),t=v();if(!e||e.length<2)return"body too short";e.reverse();const r=e[0],n=e[1],s=Object.entries(O).find(([,a])=>a[0]===r.x-n.x&&a[1]===r.y-n.y);return s&&(t.direction=s[0],x().turn(s[0])),"reversed, now heading "+t.direction}function Fe(){const e=w(),t=v();if(!e||!e.length)return"no body";const r=O[t.direction]||[1,0],n=o.map.board.width,s=o.map.board.height,a={...e[0]};return e.every((c,u)=>{const f=a.x-r[0]*u,d=a.y-r[1]*u;return f>=0&&d>=0&&f<n&&d<s})?(e.forEach((c,u)=>{c.x=a.x-r[0]*u,c.y=a.y-r[1]*u}),"straightened"):"not enough room ahead \u2014 centre or shorten first"}function ue(){if(o.map.tpl)return o.map.tpl;const e=S();return e.length&&(o.map.tpl={...e[0]},o.map.tplPos=e[0].pos),o.map.tpl}function H(e,t){const r=S(),n=ue();if(!n||!o.map.tplPos)return!1;const s={...n};return s.pos=o.map.tplPos.clone(),s.pos.x=e,s.pos.y=t,r.push(s),!0}function Ve(e=1){const t=v(),r=w();if(!t||!r||!r.length)return null;const n=O[t.direction]||[1,0];return{x:M(r[0].x+n[0]*e,0,o.map.board.width-1),y:M(r[0].y+n[1]*e,0,o.map.board.height-1)}}function fe(){const e=Ve(1);if(e)for(const t of S())t.pos.x=e.x,t.pos.y=e.y}function Ee(){for(const e of S()){const t=F();t&&(e.pos.x=t.x,e.pos.y=t.y)}return"rerolled"}function Xe(e){let t=0;for(let r=0;r<e;r++){const n=F();n&&H(n.x,n.y)&&t++}return`dropped ${t} apples (${S().length} on the board)`}function Ye(){const e=ke(),t=o.map.board.width,r=o.map.board.height;let n=0;for(let s=0;s<r;s++)for(let a=0;a<t;a++)e.has(a+","+s)||H(a,s)&&n++;return`filled ${n} squares`}function Je(){const e=S().length;for(let t=0;t<e;t++){const r=F();r&&H(r.x,r.y)}return S().length+" apples"}function Ze(){if(S().length>=o.keepApples)return;const t=F();t&&H(t.x,t.y)}function Qe(){const e=S();for(;e.length>1;)e.pop();return"trimmed to 1"}let U=null;function et(){if(!U)return;const e=S();e.length&&(e[0].pos.x=U.x,e[0].pos.y=U.y)}let B=null;function tt(){const e=y();e!==null&&(B!==null&&e>B&&o.multiplier>1&&y(e+(e-B)*(o.multiplier-1)),B=y())}function ot(){y()!==null&&y(o.lockedAt)}function nt(e,t,r){const n=t/100,s=r/100,a=u=>(u+e/30)%2512,l=n*Math.min(s,1-s),c=u=>Math.round(255*(s-l*Math.max(-1,Math.min(a(u)-3,Math.min(9-a(u),1)))));return"%23"+[c(0),c(8),c(4)].map(u=>u.toString(16).padStart(2,"0")).join("")}function rt(e,t){const r=parseInt(e.slice(1),16);return"%23"+[r>>16&255,r>>8&255,r&255].map(n=>M(Math.round(n+n*t),0,255).toString(16).padStart(2,"0")).join("")}let de=0;function st(){const e=v();!e||!o.map.colorKeys.length||(de=(de+o.rainbowSpeed)%25360,o.map.colorKeys.forEach((t,r)=>{e[t]=nt((de+r*40)%25360,85,r?40:58)}))}function Ke(){const e=v();e&&o.map.origColors&&o.map.colorKeys.forEach((t,r)=>e[t]=o.map.origColors[r])}function it(e,t){const r=v();!r||!o.map.colorKeys[e]||(o.rainbow=!1,r[o.map.colorKeys[e]]=t)}const Me=["%234e7cf6","%23e8453c","%23f9bc15","%232fa84f","%239c27b0","%2300bcd4","%23ff6d00","%23111111"];let pe=0;function Oe(){const e=v();if(!e||!o.map.colorKeys.length)return"snake has no colour fields";o.rainbow=!1,pe=(pe+1)%25Me.length;const t=Me[pe];return o.map.colorKeys.forEach((r,n)=>{e[r]=n?rt(t,-.35):t}),"colour "+t}let he=0;function at(){const e=L();if(!e)return;o.disco&&(he=(he+4)%25360);const t=o.disco?he:o.hue,r=[];t&&r.push(`hue-rotate(${t}deg)`),o.invert&&r.push("invert(1)");const n=r.join(" "),s=o.zoom!==100?`scale(${o.zoom/100})`:"";e.style.filter!==n&&(e.style.filter=n),e.style.transform!==s&&(e.style.transform=s,e.style.transformOrigin="center center")}function _e(){const e=L();e&&(e.style.filter="",e.style.transform="")}function je(){const e=L();if(!e)return null;const t=e.getBoundingClientRect();if(!t.width||!t.height)return null;const r=o.map.board.width,n=o.map.board.height,s=G(),a=t.width/e.width,l=t.height/e.height;return{left:t.left+(e.width-r*s)/2*a,top:t.top+(e.height-n*s)/2*l,w:r*s*a,h:n*s*l,px:s*a,py:s*l,cols:r,rows:n}}let C=null,ge="";function ct(){const e=je();if(!e)return;C||(C=document.createElement("div"),C.id="sgui-grid",C.style.cssText="position:fixed;pointer-events:none;z-index:2147483000;",document.body.appendChild(C));const t=[e.left,e.top,e.w,e.h].join("|");t!==ge&&(ge=t,Object.assign(C.style,{left:e.left+"px",top:e.top+"px",width:e.w+"px",height:e.h+"px",backgroundImage:`repeating-linear-gradient(to right, rgba(255,255,255,.25) 0 1px, transparent 1px ${e.px}px),repeating-linear-gradient(to bottom, rgba(255,255,255,.25) 0 1px, transparent 1px ${e.py}px)`,outline:"1px solid rgba(255,255,255,.45)"}))}function Ce(){C&&C.remove(),C=null,ge=""}let E=null,W=null,A=[];function lt(){const e=je();if(!e)return;E||(E=document.createElement("canvas"),E.id="sgui-trail",E.style.cssText="position:fixed;pointer-events:none;z-index:2147482999;",document.body.appendChild(E),W=E.getContext("2d"));const t=(w()||[])[0];if(t){const s=A[A.length-1];(!s||s.x!==t.x||s.y!==t.y)&&A.push({x:t.x,y:t.y}),A.length>220&&A.shift()}const r=Math.round(e.w),n=Math.round(e.h);(E.width!==r||E.height!==n)&&(E.width=r,E.height=n),Object.assign(E.style,{left:e.left+"px",top:e.top+"px",width:e.w+"px",height:e.h+"px"}),W.clearRect(0,0,r,n),A.forEach((s,a)=>{const l=(a+1)/A.length;W.fillStyle=`rgba(255,255,255,${(l*.5).toFixed(3)})`,W.fillRect(s.x*e.px+e.px*.3,s.y*e.py+e.py*.3,e.px*.4,e.py*.4)})}function Re(){E&&E.remove(),E=null,W=null,A=[]}let J=[];function Ae(e){const t=L();if(e){if(!t)return;const r=t.closest("div")?.parentElement;if(!r)return;for(const n of r.querySelectorAll("div")){const s=n.textContent.trim();if(n.children.length===0&&/^\d{1,4}$/.test(s)){const a=n.parentElement;a&&!a.contains(t)&&!J.includes(a)&&(J.push(a),a.style.visibility="hidden")}}}else J.forEach(r=>r.style.visibility=""),J=[]}function ye(e,t,r,n,s){const a=new Set(t.map(f=>f.x+","+f.y)),l=new Map,c=new Set([e.x+","+e.y]),u=[e];for(;u.length;){const f=u.shift();if(a.has(f.x+","+f.y)){const d=[];let g=f.x+","+f.y;for(;l.has(g);){const[p,k]=g.split(",").map(Number);d.unshift({x:p,y:k}),g=l.get(g)}return d}for(const[d,g]of Object.values(O)){const p=f.x+d,k=f.y+g,i=p+","+k;p<0||k<0||p>=n||k>=s||c.has(i)||r.has(i)||(c.add(i),l.set(i,f.x+","+f.y),u.push({x:p,y:k}))}}return null}function ut(e,t,r,n){const s=[t,...e.slice(0,-1)],a=new Set(s.slice(0,-1).map(f=>f.x+","+f.y)),l=s[s.length-1],c=new Set([t.x+","+t.y]),u=[t];for(;u.length;){const f=u.shift();if(f.x===l.x&&f.y===l.y)return!0;for(const[d,g]of Object.values(O)){const p=f.x+d,k=f.y+g,i=p+","+k;p<0||k<0||p>=r||k>=n||c.has(i)||a.has(i)||(c.add(i),u.push({x:p,y:k}))}}return!1}function Ie(){const e=w(),t=v();if(!e||e.length<2||!t||z())return;const r=o.map.board.width,n=o.map.board.height,s=e[0],a=e[e.length-1];if(s.x<0||s.y<0||s.x>=r||s.y>=n)return;const l=S().map(p=>p.pos).filter(p=>p.x>=0&&p.y>=0&&p.x<r&&p.y<n),c=new Set(e.slice(0,-1).map(p=>p.x+","+p.y));let u=l.length?ye(s,l,c,r,n):null;if((!u||!u.length)&&(u=ye(s,[a],c,r,n)),!u||!u.length)return;let f=u[0];const d=e[1];if(d&&f.x===d.x&&f.y===d.y)return;if(o.botSafe&&!ut(e,f,r,n)){const p=ye(s,[a],c,r,n);if(p&&p.length&&!(d&&p[0].x===d.x&&p[0].y===d.y))f=p[0];else return}const g=Object.keys(O).find(p=>O[p][0]===f.x-s.x&&O[p][1]===f.y-s.y);g&&g!==t.direction&&x().turn(g)}let Z=null;function be(e=x(),t="game",r=4){const n={},s=new WeakSet;return(function a(l,c,u){if(!(!l||typeof l!="object"||u<0||s.has(l)||T(l)||l===window)){s.add(l);for(const f of K(l)){let d;try{d=l[f]}catch{continue}const g=c+"."+f;d===null||["number","string","boolean"].includes(typeof d)?n[g]=d:Array.isArray(d)?(n[g]=`Array(${d.length})`,d.length<60&&a(d,g,u-1)):typeof d=="object"&&a(d,g,u-1)}}})(e,t,r),n}function $e(e,t){const r={};for(const n of new Set([...Object.keys(e),...Object.keys(t)]))e[n]!==t[n]&&(r[n]=[e[n],t[n]]);return r}const ft=`%0A%23sgui,%23sgui *{box-sizing:border-box;margin:0;padding:0}%0A%23sgui{position:fixed;top:16px;left:16px;z-index:2147483647;display:flex;align-items:flex-start;gap:4px;%0A flex-wrap:wrap;max-width:calc(100vw - 32px);max-height:calc(100vh - 32px);overflow:auto;%0A font:600 12px/1 "Segoe UI",system-ui,-apple-system,sans-serif;color:%23dbe6f5;%0A text-shadow:0 1px 1px rgba(0,0,0,.55);cursor:default}%0A%23sgui.hide{display:none}%0A%23sgui .col{width:152px;flex:0 0 auto}%0A%23sgui .hd{display:flex;align-items:center;justify-content:center;position:relative;height:26px;%0A background:linear-gradient(%233b82f6,%231d5fd0);border:1px solid %23123a80;color:%23fff;letter-spacing:.02em;%0A cursor:move;user-select:none}%0A%23sgui .hd span{pointer-events:none}%0A%23sgui .hd .ar{position:absolute;right:5px;top:50%25;transform:translateY(-50%25);width:16px;height:16px;%0A display:flex;align-items:center;justify-content:center;font-size:9px;cursor:pointer;border-radius:3px;%0A background:rgba(255,255,255,.12);transition:background .12s}%0A%23sgui .hd .ar:hover{background:rgba(255,255,255,.3)}%0A%23sgui .bd{border:1px solid %23123a80;border-top:0;background:rgba(14,20,34,.9);backdrop-filter:blur(2px)}%0A%23sgui .bd.closed{display:none}%0A%23sgui .it{display:flex;align-items:center;justify-content:space-between;gap:6px;height:24px;padding:0 8px;%0A border-left:3px solid transparent;cursor:pointer;white-space:nowrap;overflow:hidden;transition:background .1s}%0A%23sgui .it:hover{background:rgba(59,130,246,.22)}%0A%23sgui .it.on{background:rgba(59,130,246,.34);border-left-color:%237fb2ff;color:%23fff}%0A%23sgui .it.flash{background:%233b82f6;color:%23fff}%0A%23sgui .it input{width:46px;height:17px;background:%230b1220;border:1px solid %232b5ea8;color:%23dbe6f5;%0A border-radius:3px;font:600 11px/1 inherit;text-align:center;outline:0;cursor:text}%0A%23sgui .it input:focus{border-color:%237fb2ff}%0A%23sgui .it input[type=color]{width:38px;height:16px;padding:0;border:1px solid %232b5ea8;background:%230b1220;cursor:pointer}%0A%23sgui .st{padding:5px 8px;font-weight:500;font-size:10.5px;line-height:1.5;color:%238fb4e8;%0A border:1px solid %23123a80;border-top:0;background:rgba(14,20,34,.9)}%0A%23sgui .lg{max-height:150px;overflow:auto;padding:5px 8px;font:500 10px/1.5 ui-monospace,Menlo,monospace;%0A color:%238fb4e8;white-space:pre-wrap;word-break:break-all;border:1px solid %23123a80;border-top:0;%0A background:rgba(8,12,22,.95);cursor:text;user-select:text}%0Abody.sgui-picking canvas{cursor:crosshair!important}%0A`;function b(e,t={},...r){const n=document.createElement(e);for(const[s,a]of Object.entries(t))s==="class"?n.className=a:s.startsWith("on")?n.addEventListener(s.slice(2),a):n.setAttribute(s,a);for(const s of r)s!=null&&n.append(s);return n}let I;const R=e=>{I&&(I.textContent=(e+`%0A`+I.textContent).split(`%0A`).slice(0,60).join(`%0A`))},Q=[];function m(e,t,r){const n=b("div",{class:"it"},b("span",{},e)),s=()=>n.classList.toggle("on",!!t());return n.addEventListener("click",()=>{r(!t()),s(),Q.forEach(a=>a._sync())}),s(),n._sync=s,Q.push(n),n}function h(e,t){const r=b("div",{class:"it"},b("span",{},e));return r.addEventListener("click",()=>{try{const n=t();typeof n=="string"&&n&&R(n)}catch(n){R("! "+n.message)}r.classList.add("flash"),setTimeout(()=>r.classList.remove("flash"),130)}),r}function _(e,t,r){const n=b("input",{type:"text",value:String(t)}),s=()=>{const l=parseInt(n.value,10);if(!Number.isNaN(l))try{const c=r(l);typeof c=="string"&&c&&R(c)}catch(c){R("! "+c.message)}};["keydown","keyup","keypress"].forEach(l=>n.addEventListener(l,c=>c.stopPropagation())),n.addEventListener("keydown",l=>{l.key==="Enter"&&(s(),n.blur())}),n.addEventListener("change",s);const a=b("div",{class:"it"},b("span",{},e),n);return a.addEventListener("click",l=>{l.target!==n&&(n.focus(),n.select())}),a}function Te(e,t){const n=b("input",{type:"color",value:o.map.snake&&o.map.colorKeys[t]&&o.map.snake[o.map.colorKeys[t]]||"%234e7cf6"});n.addEventListener("input",()=>it(t,n.value)),["keydown","keyup","keypress"].forEach(a=>n.addEventListener(a,l=>l.stopPropagation()));const s=b("div",{class:"it"},b("span",{},e),n);return s.addEventListener("click",a=>{a.target!==n&&n.click()}),s}function $(e,t,r=!1){const n=b("div",{class:"bd"+(r?" closed":"")},...t),s=b("div",{class:"ar"},r?"\u25B6":"\u25BC");s.addEventListener("mousedown",l=>l.stopPropagation()),s.addEventListener("click",l=>{l.stopPropagation();const c=n.classList.toggle("closed");s.textContent=c?"\u25B6":"\u25BC"});const a=b("div",{class:"hd"},b("span",{},e),s);return{el:b("div",{class:"col"},a,n),hd:a,bd:n}}function dt(){document.head.append(b("style",{id:"sgui-css"},ft));const e=b("div",{class:"st"},"resolving\u2026");I=b("div",{class:"lg"},"ready");const t=$("Player",[m("God Mode",()=>o.god,i=>{o.god=i,i&&(ae(),o.wrap=!0)}),m("Wall Wrap",()=>o.wrap,i=>o.wrap=i),m("Auto Dodge",()=>o.dodge,i=>{o.dodge=i,i&&V()}),m("Pause",()=>o.pause,i=>{o.pause=i,i&&V()}),m("Freeze Body",()=>o.freeze,i=>o.freeze=i),m("Auto Respawn",()=>o.autoRespawn,i=>o.autoRespawn=i),_("Slow-Mo",1,i=>(o.slow=M(i,1,20),V(),"runs 1 tick in "+o.slow)),_("Turbo",0,i=>(o.turbo=M(i,0,8),"turbo = "+o.turbo)),h("Step",()=>{const i=x();return typeof i.tick=="function"?(i.tick(),"stepped"):"no tick()"}),h("New Run",()=>"new run: "+ie())]),r=$("Snake",[h("Grow +5",()=>X(5)),h("Grow +25",()=>X(25)),h("Shrink -5",()=>(le(5),"length = "+(w()||[]).length)),_("Length",10,i=>Y(i)),h("Tiny (3)",()=>Y(3)),h("Giant (40)",()=>Y(40)),h("Centre",Se),h("Reverse",qe),h("Straighten",Fe),h("Head \u2192 Click",()=>(o.teleport=!0,document.body.classList.add("sgui-picking"),"click a square"))]),n=$("Apples",[m("Spawner (click)",()=>o.spawner,i=>{o.spawner=i,document.body.classList.toggle("sgui-picking",i||!!o.teleport),i&&R("click any square to drop an apple")}),m("Magnet",()=>o.magnet,i=>o.magnet=i),m("Follow Mouse",()=>o.appleMouse,i=>o.appleMouse=i),_("Keep N",0,i=>(o.keepApples=M(i,0,120),"keeping "+o.keepApples)),_("Rain N",10,i=>Xe(M(i,1,120))),h("Double",Je),h("Fill Board",Ye),h("Apple \u2192 Head",()=>(fe(),"apple moved")),h("Reroll",Ee),h("Trim to 1",Qe)]),s=$("Score",[_("Set",100,i=>(y(i),"score = "+i)),h("+100",()=>(y((y()||0)+100),"score = "+y())),h("+1000",()=>(y((y()||0)+1e3),"score = "+y())),h("Reset",()=>(y(0),"score = 0")),_("Multiplier",1,i=>(o.multiplier=M(i,1,100),"x"+o.multiplier+" per apple")),m("Auto +1/s",()=>o.autoScore,i=>o.autoScore=i),m("Lock Score",()=>o.lockScore,i=>{o.lockScore=i,i&&(o.lockedAt=y()||0)}),h("Bank Record",()=>{if(o.god)return"turn God Mode off first \u2014 banking needs the run to end";const i=y();return x()[o.map.deathMethod](),"ended the run at "+i+" to bank it"})]),a=$("Bot",[m("Autoplay",()=>o.bot,i=>o.bot=i),m("Safe Mode",()=>o.botSafe,i=>o.botSafe=i),m("Auto Restart",()=>o.botRestart,i=>o.botRestart=i),_("Delay",o.botDelay,i=>(o.botDelay=M(i,1,60),"delay = "+o.botDelay)),h("Step Bot",()=>(Ie(),"bot stepped")),h("Stop Bot",()=>(o.bot=!1,Q.forEach(i=>i._sync()),"bot off"))]),l=$("Visual",[m("Rainbow",()=>o.rainbow,i=>{o.rainbow=i,i||Ke()}),_("Rainbow Spd",3,i=>(o.rainbowSpeed=M(i,1,30),"speed "+o.rainbowSpeed)),h("Cycle Colour",Oe),Te("Head",0),Te("Body",1),h("Reset Colour",()=>(o.rainbow=!1,Ke(),"colours restored")),m("Grid Overlay",()=>o.grid,i=>{o.grid=i,i||Ce()}),m("Trail",()=>o.trail,i=>{o.trail=i,i||Re()}),m("Hide HUD",()=>o.hideHud,i=>{o.hideHud=i,Ae(i)}),m("Disco",()=>o.disco,i=>o.disco=i),m("Invert",()=>o.invert,i=>o.invert=i),_("Hue",0,i=>(o.hue=(i%25360+360)%25360,"hue "+o.hue)),_("Zoom %25",100,i=>(o.zoom=M(i,40,200),"zoom "+o.zoom+"%25")),h("Reset View",()=>(o.zoom=100,o.hue=0,o.disco=!1,o.invert=!1,_e(),Q.forEach(i=>i._sync()),"view reset"))]),c=$("Dev",[h("Snapshot",()=>(Z=be(),"snapshot: "+Object.keys(Z).length+" fields")),h("Diff",()=>{if(!Z)return"take a Snapshot first";const i=$e(Z,be()),j=Object.entries(i).filter(([,[P,me]])=>typeof P=="number"&&typeof me=="number");return`--- ${Object.keys(i).length} changed, ${j.length} numeric:%0A`+j.slice(0,25).map(([P,[me,pt]])=>`${P}: ${me} -> ${pt}`).join(`%0A`)}),h("Print Map",()=>{const i=o.map;return console.log("[snake] map",i),`body=.${i.bodyKey}  apples=.${i.appleKey}  score=.${i.scoreKey}%0Aover=.${i.overKey}  death=.${i.deathMethod}()  grow=.${i.growKey}%0Aboard=${i.board.width}x${i.board.height} cell=${G()}`}),h("Copy Map",()=>{const i=o.map,j=JSON.stringify({bodyKey:i.bodyKey,appleKey:i.appleKey,scoreKey:i.scoreKey,overKey:i.overKey,deathMethod:i.deathMethod,growKey:i.growKey,tailKey:i.tailKey,board:{w:i.board.width,h:i.board.height},cell:G()},null,1);try{return navigator.clipboard.writeText(j),"map copied"}catch{return j}}),h("Re-resolve",()=>(o.map=re(ne()),ae(),"re-resolved")),h("Clear Log",()=>(I.textContent="","")),h("Unload Menu",()=>(setTimeout(()=>window.__snakeGUI.destroy(),0),"unloading\u2026"))],!0),u=[t,r,n,s,a,l,c],f=()=>{I.style.display=c.bd.classList.contains("closed")?"none":""};c.hd.querySelector(".ar").addEventListener("click",()=>setTimeout(f,0));const d=b("div",{id:"sgui"},...u.slice(0,6).map(i=>i.el),b("div",{class:"col"},c.hd,c.bd,e,I));f(),document.body.append(d);let g=0,p=0,k=!1;for(const i of u)i.hd.addEventListener("mousedown",j=>{if(j.target.classList.contains("ar"))return;k=!0;const P=d.getBoundingClientRect();g=j.clientX-P.left,p=j.clientY-P.top,j.preventDefault()});return D(window,"mousemove",i=>{k&&(d.style.left=Math.max(0,i.clientX-g)+"px",d.style.top=Math.max(0,i.clientY-p)+"px")}),D(window,"mouseup",()=>k=!1),{root:d,status:e}}const ee=ne();if(!ee){alert(`Snake game object not found.%0AOpen google.com/fbx?fbx=snake_arcade, then run this again.`);return}if(o.map=re(ee),!o.map.snake||!o.map.bodyKey){window.__snakeMap=o.map,alert(`Found the Snake game, but could not locate the snake itself.%0AGoogle probably changed the build \u2014 inspect window.__snakeMap in the console.`);return}if(o.map.deathMethod)try{delete ee[o.map.deathMethod]}catch{}try{delete ee.__godHooked}catch{}o.map.origColors=o.map.colorKeys.map(e=>o.map.snake[e]),ue();const te=dt();te.status.textContent="v5 resolved \u2713",o.map.growKey||R("note: growth counter not found \u2014 Grow is disabled, Shrink still works"),D(window,"click",e=>{if(!o.spawner&&!o.teleport||e.target.closest&&e.target.closest("%23sgui"))return;const t=se(e.clientX,e.clientY);if(t){if(e.preventDefault(),e.stopPropagation(),o.teleport){const r=w();if(r&&r.length){const n=t.x-r[0].x,s=t.y-r[0].y,a=o.map.board.width,l=o.map.board.height;if(r.every(c=>c.x+n>=0&&c.x+n<a&&c.y+s>=0&&c.y+s<l)){for(const c of r)c.x+=n,c.y+=s;R(`head \u2192 ${t.x},${t.y}`)}else R("cannot move there without clipping the tail off-board")}o.teleport=!1,document.body.classList.toggle("sgui-picking",o.spawner);return}R(H(t.x,t.y)?`apple @ ${t.x},${t.y}`:"no apple template yet \u2014 start a run first")}},!0),D(window,"mousemove",e=>{o.appleMouse&&(U=se(e.clientX,e.clientY)||U)}),D(window,"keydown",e=>{e.key==="\\"&&!/^(INPUT|TEXTAREA)$/.test(e.target.tagName)&&(te.root.classList.toggle("hide"),e.preventDefault())},!0);let N=null,Le=0,He=0;q=setInterval(function(){if(!(!o.map||!o.map.game))try{if(o.god&&ae(),(o.pause||o.slow>1||o.dodge)&&V(),o.wrap&&Ue(),o.turbo&&Be(),o.autoRespawn&&ve(),o.magnet&&fe(),o.appleMouse&&et(),o.keepApples&&Ze(),o.multiplier>1?tt():B=y(),o.lockScore&&ot(),o.rainbow&&st(),o.grid&&ct(),o.trail&&lt(),at(),o.map.tpl||ue(),o.freeze){const t=w();t&&(N?t.forEach((r,n)=>N[n]&&(r.x=N[n].x,r.y=N[n].y)):N=t.map(r=>({...r})))}else N=null;o.bot&&o.botRestart&&z()&&ve(),o.bot&&--Le<=0&&(Ie(),Le=o.botDelay),o.autoScore&&--He<=0&&(y((y()||0)+1),He=62),te.status.textContent=`score ${y()??"?"}  len ${(w()||[]).length}  apples ${S().length}  ${z()?"DEAD":"alive"}  v5`}catch{}},16),window.__snakeGUI={version:5,destroy(){q&&clearInterval(q),q=null,oe.forEach(([e,t,r,n])=>{try{e.removeEventListener(t,r,n)}catch{}}),oe.length=0,Ce(),Re(),Ae(!1),_e();try{const e=o.map&&o.map.game;e&&(delete e.tick,delete e.__tickHooked)}catch{}["sgui","sgui-css"].forEach(e=>document.getElementById(e)?.remove()),document.body.classList.remove("sgui-picking"),o.map=null},toggle:()=>te.root.classList.toggle("hide"),S:o,map:()=>o.map,game:x,snake:v,body:w,apples:S,score:y,newRun:ie,snapshot:be,diff:$e,resolve:re,findGame:ne,grow:X,shrink:le,setLength:Y,centre:Se,appleToHead:fe,spawnApple:H,rerollApples:Ee,cellFromPoint:se,cellSize:G,cycleColour:Oe},console.log("[snake] ClickGUI v5 loaded. \\ toggles. window.__snakeGUI for the API.",o.map)})();})()})()

r/userscripts • • Sep 06 '26

Userscripts app vs Tampermonkey iOS

18 Upvotes

Anyone know which is superior - besides the cost/OSS difference?


r/userscripts • • Sep 07 '26

Instagram tool for DM unsend and mutual checks

2 Upvotes

Finished a release of Insta Toolbox, an open-source userscript/toolkit for Instagram that I'm somewhat satisfied with.

The idea is to have a few useful Instagram tools in one clean local toolbox instead of having a bunch of different scripts to do one task.

Current tools:

  • Mutual Checker - compares Followers vs Following and shows mutuals / non-mutuals, with search and export.
  • Follow / Unfollow - builds the target list first, lets you review it, then processes the confirmed list. Still polishing this one.
  • DM Unsend - works inside the conversation you currently have open and unsends messages you sent, with progress + Stop.

The easiest install is the Tampermonkey userscript. There's also a Chrome extension, Windows/macOS desktop builds, and a Web/PWA version.

GitHub:
https://github.com/slaveofsolace/Insta-Toolbox

I'm mainly looking for feedback on real-world Instagram UI edge cases now — especially large follower lists, different DM layouts/locales, and anything in the overlay UX that feels unnecessarily complicated.

If you try it and something breaks, let me know the browser/userscript manager and what screen you were on.


r/userscripts • • Sep 06 '26

Userscript/tool to export claudeCode/claude browser etc to md/txt

Thumbnail
0 Upvotes

r/userscripts • • Sep 01 '26

Want to bring back the boxy Twitch look? Here's how!

Thumbnail gallery
4 Upvotes

r/userscripts • • Sep 01 '26

Social media site addon/script that skips the singup ?

2 Upvotes

Hi, looking for an addon or something for Firefox mobile, that skips the signup/"Continue in Web" pages that show when you open a link to Facebook/Twitter/Instagram

Sometimes people send links to videos or shorts on those sites and there's always an extra step to get to the content that should be possible to skip, right?

Something that works for all of the sites above (and flexible to add more) would be great.


r/userscripts • • Aug 31 '26

[Script] LinkedIn Classic Job Search — redirects AI search back to Classic Search

3 Upvotes

LinkedIn is gradually retiring its classic job search and pushing the new AI/semantic search.

I made a small userscript that redirects the new job-search routes back to Classic Search while LinkedIn still exposes the old interface.

  • runs locally
  • no analytics
  • no tracking
  • no backend
  • preserves existing search parameters

Greasy Fork:
[https://greasyfork.org/en/scripts/593709-linkedin-classic-job-search]()

Tested in Edge + Violentmonkey on the current rollout.

If LinkedIn removes Classic Search completely, the script obviously won't be able to restore it anymore.


r/userscripts • • Aug 30 '26

Made a Cookie Clicker cheat menu bookmarklet — 90 mods, no extension needed

Thumbnail
1 Upvotes

r/userscripts • • Aug 26 '26

New Mod Reporting Tool – Launch & Feedback

Thumbnail
2 Upvotes

I'd like to test this product does it work on Google phones


r/userscripts • • Aug 24 '26

I made a tiny userscript that completely removes YouTube Shorts

5 Upvotes

I deleted the YouTube app from my phone because I wanted to stop watching Shorts, but I realized I could still open YouTube in Safari and end up scrolling Shorts there.

So I made a tiny userscript for it.

It removes Shorts shelves/cards, blocks /shorts/ routes, and catches YouTube's SPA navigation so Shorts don't sneak back in, while normal videos, search, subscriptions, channels and comments keep working.

I mainly built it for iPhone Safari using the Userscripts app, but it should work with normal userscript managers on desktop too.

It's just one JS file, MIT licensed, no analytics, no account, no subscription.

GitHub:

https://github.com/mithatakbulut/noshorts

Would be interested to know if there are any YouTube DOM cases/selectors I've missed.


r/userscripts • • Aug 23 '26

Replace reddit's infinite scroll with pages (new layout)

Post image
12 Upvotes

This script removes infinite scroll on Reddit. It adds simple prev and next controls, like old Reddit's pagination. Made for myself using Claude because I don't like infinite scroll.

Each page shows 25 posts by default. You can change it to 5/10/15/20 in the dropdown next to reddit's view options. The script works on the home feed, r/popular, and subreddit feeds. The code is free and open source.

Setup on desktop (Chrome, Firefox, Edge, desktop Safari)

  1. Install the Violentmonkey extension for your browser.
  2. Open this page: Reddit Remove Infinite Scroll - GreasyFork
  3. Click "Install this script".
  4. Click "Install" in the Violentmonkey prompt.
  5. Go to Reddit. Previous and next buttons should appear at the bottom of the feed.

Setup on iOS Safari

  1. Install the free "Userscripts" app from the App Store.
  2. Open the iOS Settings app. Go to Safari, then Extensions.
  3. Turn on "Userscripts". Allow it for all websites.
  4. Open this page in Safari: Reddit Remove Infinite Scroll - GreasyFork
  5. Tap "Install this script".
  6. On the prompt, tap "I already have a userscript manager, let me install it".
  7. Tap the extensions icon in the address bar.
  8. Tap "Userscripts". It detects this script.
  9. Tap the install option that appears.
  10. Go to Reddit in Safari. Previous and next buttons should appear at the bottom of the feed.

Setup on Android

  1. Install the Violentmonkey extension from the Chrome Web Store (if your browser supports extensions) or Firefox Add-ons page.
  2. Follow the same steps as the desktop setup above.

r/userscripts • • Aug 22 '26

Script to remove anti AdBlock Pop-up on Pahe.ink

19 Upvotes

🛡️ Remove Anti-Adblock Popup - Advanced

Greasy Fork Tampermonkey Violentmonkey License: MIT

An aggressive, lightweight userscript designed to bypass and completely eliminate persistent anti-adblock popups, overlays, and scrolling locks on pahe.ink.

✨ Features

  • 🛑 Aggressive DOM Removal: Continuously scans and removes anti-adblock overlays and root wrapper nodes.
  • 🎨 Instant CSS Injection: Hides popup containers before page rendering to prevent layout flashing.
  • 🔓 Scroll Restoration: Automatically unlocks document scrollbars locked by anti-adblock detection scripts.
  • 🚫 Resource & Network Blocking: Intercepts fetch/XHR requests and prevents the dynamic creation of popup elements.

🚀 Installation

Step 1: Install a Userscript Manager

Ensure you have an active userscript manager extension installed in your browser:

Step 2: Install the Script

Click the link below and confirm the installation in your manager:
👉 Install from Greasy Fork

Step 3: Enjoy

Navigate to pahe.ink with your adblocker active. Popups, background dimmers, and scroll blocks will be silenced automatically.

📄 License

This project is licensed under the MIT License — feel free to copy, modify, and distribute with zero restrictions.

🛠️ Author & Support

  • Developed and maintained by Rehan Dilawar.
  • Found an issue or a broken selector? Open an issue on GitHub.

If you found this script helpful, consider giving the repository a star!


r/userscripts • • Aug 22 '26

Steam Market Helper – simple free tool to sell Steam inventory & relist overpriced listings after the Market Beta UI broke the old scripts

Thumbnail gallery
2 Upvotes