Skip to content

Instantly share code, notes, and snippets.

@plu5
Last active January 20, 2026 12:20
Show Gist options
  • Select an option

  • Save plu5/acac697b0bc172d4905179f284bffdf1 to your computer and use it in GitHub Desktop.

Select an option

Save plu5/acac697b0bc172d4905179f284bffdf1 to your computer and use it in GitHub Desktop.
greasemonkey bilibili login wall blocker userscript (but it's a mess)
// ==UserScript==
// @name bilibli login wall blocker
// @namespace Violentmonkey Scripts
// @match https://www.bilibili.com/*
// @grant none
// @version 1.0
// @author -
// @description 24/10/2025, 18:11:04
// ==/UserScript==
// NOTE:
// I couldn't get around the automatic pausing so it's a hack
// where pressing space forces it to keep playing and pressing it
// again stops forcing it.
// I also do something more; it annoys me that on first page load
// the video starts playing and you have to pause it manually,
// plus it starts muted, plus on the wrong speed, so I set up
// these things automatically on first page load. You can configure
// this below.
(function() {
'use strict';
// USER CONFIGURATION:
unsafeWindow.blwbInitialMuted = false;
unsafeWindow.blwbPlaybackRate = 1.5;
unsafeWindow.blwbClickPlaybackRate = true; // makes playback rate persist to next video in playlist
unsafeWindow.blwbDisableForceIfLoggedIn = true;
unsafeWindow.blwbForceToggleKey = " "; // space
// ADVANCED:
unsafeWindow.blwbForceInterval = 1000;
unsafeWindow.blwbPsecsThreshold = 20;
unsafeWindow.blwbLoginWallContainerSelector = '.bili-mini-mask';
unsafeWindow.blwbPlaybackSelector = '.bpx-player-ctrl-playbackrate-menu-item';
unsafeWindow.blwbPlaybackItemAttribute = 'data-value';
// TRANSIENT:
unsafeWindow.blwbKeepPlaying = false;
unsafeWindow.blwbPsecs = 0;
unsafeWindow.blwbFirstLoad = true;
unsafeWindow.blwbIntervalId = null;
const unpauseVideo = () => {
const video = document.querySelector('video');
// workaround for getting stuck at the end of a video in a playlist
if (unsafeWindow.blwbPsecs > unsafeWindow.blwbPsecsThreshold) {
video.pause();
unsafeWindow.blwbPsecs = 0;
}
video.play();
unsafeWindow.blwbPsecs += 1;
console.log('[bilibili login wall blocker] Unpausing video.', video);
};
const setupVideo = () => {
const video = document.querySelector('video');
video.pause();
video.muted = unsafeWindow.blwbInitialMuted;
video.playbackRate = unsafeWindow.blwbPlaybackRate;
};
const isVideoPlaying = () => {
const video = document.querySelector('video');
return video ? !video.paused : false;
};
const mutationHappened = () => {
if (unsafeWindow.blwbFirstLoad && isVideoPlaying()) {
console.log('[bilibili login wall blocker] first page load pause, unmute, playback speed');
setupVideo();
unsafeWindow.blwbFirstLoad = false;
}
if (unsafeWindow.blwbClickPlaybackRate) {
const playbackNodes = document.querySelectorAll(unsafeWindow.blwbPlaybackSelector);
console.log('[bilibili login wall blocker] playback selectors:', playbackNodes);
if (playbackNodes.length) {
unsafeWindow.blwbClickPlaybackRate = false; // in order to not enter this codepath again
for (const node of playbackNodes) {
if (node.getAttribute(unsafeWindow.blwbPlaybackItemAttribute) == unsafeWindow.blwbPlaybackRate) {
node.click();
console.log('[bilibili login wall blocker] clicked playback rate item', node);
}
}
}
}
const containers = document.querySelectorAll(unsafeWindow.blwbLoginWallContainerSelector);
for (const container of containers) {
console.log('[bilibili login wall blocker] Found the login wall pop-up. Removing it.', container);
container.remove();
const htmlElement = document.documentElement; // ???
// container.style.visibility = 'none';
if (!document.hidden) unpauseVideo();
break;
}
};
const maybeUnpause = () => {
if (unsafeWindow.blwbKeepPlaying && !document.hidden) unpauseVideo();
};
const clearUnpauseInterval = () => {
if (unsafeWindow.blwbIntervalId !== null) {
clearInterval(unsafeWindow.blwbIntervalId);
unsafeWindow.blwbIntervalId = null;
}
};
window.toggleForcefulPlay = () => {
clearUnpauseInterval()
if (unsafeWindow.blwbKeepPlaying) {
unsafeWindow.blwbIntervalId = setInterval(maybeUnpause, unsafeWindow.blwbForceInterval);
}
unsafeWindow.blwbKeepPlaying = !unsafeWindow.blwbKeepPlaying;
console.log("[bilibili login wall blocker] @@ toggleForcefulPlay", unsafeWindow.blwbKeepPlaying);
}
const observer = new MutationObserver(mutationHappened);
observer.observe(document.documentElement, {
childList: true,
subtree: true
});
if (unsafeWindow.blwbDisableForceIfLoggedIn && document.cookie.includes('DedeUserID')) {
console.log("[bilibili login wall blocker] user is logged in, no need to force play");
} else {
document.querySelector('body').addEventListener("keydown", (event) => {
if (event.key === unsafeWindow.blwbForceToggleKey) {
window.toggleForcefulPlay();
}
});
}
mutationHappened();
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment