🏠 Home 

RARBG Assistant

Userscript for RARBG.to to make it more user friendly.


安装此脚本?
// ==UserScript==
// @name         RARBG Assistant
// @namespace    https://github.com/PoLaKoSz
// @version      1.8.3
// @description  Userscript for RARBG.to to make it more user friendly.
// @author       Tom PoLáKoSz
// @grant        none
// @icon         https://raw.githubusercontent.com/PoLaKoSz/RARBG-Assistant/master/assets/icon.png
// @run-at       document-start
// @include      https://rarbg.to/trailers.php*
// ==/UserScript==
'use strict';
class KeyDetector {
isEscPressed(event) {
event = event || window.event;
if ("key" in event) {
return event.key === "Escape" || event.key === "Esc";
}
return event.keyCode === 27;
}
}
class RarbgAssistant {
constructor() {
this.requestCatcher = new XMLHttpRequestCatcher();
this.trailersPage = new TrailersPage();
}
initalize() {
this.requestCatcher.register("/ajax.php?mode=trailers&mode2=list", this.trailersPage);
document.addEventListener('DOMContentLoaded', function() {
const trailerWindow = new TrailerWindow();
trailerWindow.float();
trailerWindow.onOpen([
{
instance: trailerWindow,
method: trailerWindow.addSearchButton,
},
{
instance: trailerWindow,
method: trailerWindow.fixOverlayForAdblockers,
},
{
instance: trailerWindow,
method: trailerWindow.hideScrollbar,
},
]);
trailerWindow.onClose([
{
instance: trailerWindow,
method: trailerWindow.showScrollbar,
},
]);
document.onkeydown = function(event) {
const keyDetector = new KeyDetector();
if (keyDetector.isEscPressed(event)) {
trailerWindow.close();
}
};
});
}
}
class TrailersPage {
invoke(payload) {
const trailerIds = payload.match(/(?<=id="trailer_)(\d+)/g);
if (!trailerIds) {
const message = 'Couldn\'t find any trailer Id!';
console.log(message, { payload: payload });
throw message;
}
trailerIds.forEach(id => {
let trailerContainerNode = document.querySelector(`#trailer_${id}`);
const anchors = trailerContainerNode.querySelectorAll("a");
anchors.forEach(anchor => {
let proxiedClick = anchor.onclick;
anchor.onclick = function() {
proxiedClick();
return false;
}
})
});
}
}
class TrailerWindow {
constructor() {
this.trailerModalNode = document.querySelector("#trailer_modal");
this.openEventSubscribers = [];
this.closeEventSubscribers = [];
}
float() {
document.body.appendChild(this.trailerModalNode);
this.trailerModalNode.classList.add("trailer-modal");
}
close() {
this.getCloseFunction()("#");
}
onOpen(actions) {
this.openEventSubscribers = actions;
this.attachEventToWindowOpen();
}
addSearchButton(self) {
const titleContainerNode = self.trailerModalNode.querySelector("table:nth-child(3) > tbody > tr > td:nth-child(1)");
const titleNode = titleContainerNode.querySelector("b");
const button = `
<span>
<a href="https://rarbg.to/torrents.php?search=${titleNode.innerText}" target="_blank">
<i class="icon-search"></i>
Search for ${titleNode.innerText}
</a>
</span>
`;
titleContainerNode.innerHTML += button;
}
attachEventToWindowOpen() {
const proxied = jQuery.fn.jqm;
const eventSubscribers = this.openEventSubscribers;
jQuery.fn.jqm = function() {
arguments[0]['onLoad'] = function() {
eventSubscribers.forEach(subscriber => {
subscriber.method(subscriber.instance);
});
}
return proxied.apply(this, arguments);
};
}
fixOverlayForAdblockers() {
const overlayNode = document.querySelector(".jqmOverlay");
overlayNode.classList.remove("jqmOverlay");
overlayNode.setAttribute("id", "jqmOverlay");
overlayNode.style.backgroundColor = "#000";
const instance = this.instance;
overlayNode.onclick = function() {
instance.close();
}
}
hideScrollbar() {
const originalWidth = document.body.clientWidth;
document.body.style.overflow = "hidden";
document.body.style.width = `${originalWidth}px`;
}
showScrollbar() {
document.body.style.overflow = "visible";
document.body.style.width = "auto";
}
onClose(actions) {
this.closeEventSubscribers = actions;
this.attachEventToWindowClose();
}
attachEventToWindowClose() {
const eventSubscribers = this.closeEventSubscribers;
const proxied = this.getCloseFunction();
window.closejqm = function() {
eventSubscribers.forEach(subscriber => {
subscriber.method(subscriber.instance);
});
return proxied.apply(this, arguments);
};
}
getCloseFunction() {
const closeFunction = window.closejqm;
if (closeFunction === undefined) {
throw "RARBG developers removed closejqm global function!";
}
return closeFunction;
}
}
class XMLHttpRequestCatcher {
constructor() {
const proxied = window.XMLHttpRequest.prototype.send;
const requestCatcher = this;
window.XMLHttpRequest.prototype.send = function() {
const request = this;
const intervalId = window.setInterval(function() {
if(request.readyState != 4) {
return;
}
requestCatcher.invokeActionIfExists(request);
clearInterval(intervalId);
}, 1);
return proxied.apply(this, [].slice.call(arguments));
};
this.lookupTable = {};
}
register(url, action) {
url = new URL(`https://rarbg.to${url}`);
this.lookupTable[url] = action;
}
invokeActionIfExists(request) {
// sometimes responseURL is empty
if (!request.responseURL) {
return;
}
const requestURL = new URL(request.responseURL);
Object.keys(this.lookupTable).forEach(key => {
const registeredURL = new URL(key);
if (registeredURL.pathname !== requestURL.pathname) {
return;
}
const registeredSearchParams = Array.from(registeredURL.searchParams.keys());
const requestSearchParams = Array.from(requestURL.searchParams.keys());
if (registeredSearchParams.length > requestSearchParams.length) {
return;
}
let matchCount = 0;
registeredSearchParams.forEach(registeredSearchParam => {
matchCount += registeredURL.searchParams.get(registeredSearchParam) === requestURL.searchParams.get(registeredSearchParam);
});
if (matchCount != registeredSearchParams.length) {
return;
}
this.lookupTable[key].invoke(request.responseText);
});
}
}
const rarbgAssistant = new RarbgAssistant();
rarbgAssistant.initalize();
const styleNode = document.createElement('style');
styleNode.type = 'text/css';
styleNode.innerText = '.trailer-modal{position:fixed!important}';
document.head.appendChild(styleNode);