RU AdList JS Fixes

try to take over the world!

目前為 2016-09-15 提交的版本,檢視 最新版本

  1. // ==UserScript==
  2. // @name RU AdList JS Fixes
  3. // @namespace ruadlist_js_fixes
  4. // @version 2016-09-15:1
  5. // @description try to take over the world!
  6. // @author lainverse & dimisa
  7. // @match *://*/*
  8. // @grant unsafeWindow
  9. // @grant window.close
  10. // @grant GM_addStyle
  11. // @run-at document-start
  12. // ==/UserScript==
  13.  
  14. (function() {
  15. 'use strict';
  16. var win = unsafeWindow || window;
  17. function inIFrame() {
  18. try {
  19. return win.self !== win.top;
  20. } catch (ignore) {
  21. return true;
  22. }
  23. }
  24.  
  25. // https://greasyfork.org/scripts/19144-websuckit/
  26. (function() {
  27. function getWrappedCode(removeSelf) {
  28. var text = getWrappedCode.toString()+WSI.toString();
  29. text = (
  30. '(function(){"use strict";'+
  31. text.replace(/\/\/[^\r\n]*/g,'').replace(/[\s\r\n]+/g,' ')+
  32. '(new WSI(self||window)).init();'+
  33. '})();'+
  34. (removeSelf?'var s = document.currentScript; if (s) {s.parentNode.removeChild(s);}':'')
  35. );
  36. return text;
  37. }
  38.  
  39. function WSI(win, safeWin) {
  40. safeWin = safeWin || win;
  41. var masks = [];
  42. [// blacklist to generate masks regexps
  43. '||24video.xxx^',
  44. '||adlabs.ru^',
  45. '||bgrndi.com^',
  46. '||brokeloy.com^',
  47. '||cnamerutor.ru^',
  48. '||docfilms.info^',
  49. '||dreadfula.ru^',
  50. '||et-code.ru^',
  51. '||free-torrent.org^',
  52. '||free-torrent.pw^',
  53. '||free-torrents.org^',
  54. '||free-torrents.pw^',
  55. '||game-torrent.info^',
  56. '||gocdn.ru^',
  57. '||hdkinoshka.com^',
  58. '||hghit.com^',
  59. '||kinotochka.net^',
  60. '||kuveres.com^',
  61. '||lepubs.com^',
  62. '||luxadv.com^',
  63. '||luxup.ru^',
  64. '||mail.ru^',
  65. '||marketgid.com^',
  66. '||mxtads.com^',
  67. '||oconner.biz^',
  68. '||abbp1.website',
  69. '||psma01.com^',
  70. '||psma02.com^',
  71. '||psma03.com^',
  72. '||recreativ.ru^',
  73. '||regpole.com^',
  74. '||ruttwind.com^',
  75. '||skidl.ru^',
  76. '||torvind.com^',
  77. '||trafmag.com^',
  78. '||xxuhter.ru^',
  79. '||yuiout.online^'
  80. ].forEach(function(m){
  81. masks.push(new RegExp(
  82. m.replace(/([\\\/\[\].*+?(){}$])/g, '\\$1')
  83. .replace(/\^(?!$)/g,'\\.?[^\\w%._-]')
  84. .replace(/\^$/,'\\.?([^\\w%._-]|$)')
  85. .replace(/^\|\|/,'^wss?:\\/+([^\/.]+\\.)*'),
  86. 'i'));
  87. });
  88.  
  89. function isBlocked(url) {
  90. var i = masks.length;
  91. while(i--) {
  92. if (masks[i].test(url)) {
  93. return true;
  94. }
  95. }
  96. return false;
  97. }
  98.  
  99. function WebSocketWrapper() {
  100. var realWebSocket = win.WebSocket;
  101. // check does browser support Proxy and WebSocket
  102. if (typeof Proxy !== 'function' ||
  103. typeof WebSocket !== 'function') {
  104. return;
  105. }
  106.  
  107. function wsGetter (target, name) {
  108. console.log('[WSI] Registered call to property "', name, '"');
  109. try {
  110. if (typeof realWebSocket.prototype[name] === 'function') {
  111. if (name === 'close' || name === 'send') { // send also closes connection
  112. target.readyState = realWebSocket.CLOSED;
  113. }
  114. return function(){return;};
  115. }
  116. if (typeof realWebSocket.prototype[name] === 'number') {
  117. return realWebSocket[name];
  118. }
  119. } catch(ignore) {}
  120. return target[name];
  121. }
  122.  
  123. win.WebSocket = new Proxy(realWebSocket, {
  124. construct: function (target, args) {
  125. var url = args[0];
  126. console.log('[WSI] Opening socket on', url, '\u2026');
  127. if (isBlocked(url)) {
  128. console.log("[WSI] Blocked.");
  129. return new Proxy({url: url, readyState: realWebSocket.OPEN}, {
  130. get: wsGetter
  131. });
  132. }
  133. return new target(args[0], args[1]);
  134. }
  135. });
  136. }
  137.  
  138. function WorkerWrapper() {
  139. var realWorker = win.Worker;
  140. function wrappedWorker(resourceURI) {
  141. var _worker = null,
  142. _terminate = false,
  143. _onerror = null,
  144. _onmessage = null,
  145. _messages = [],
  146. _events = [],
  147. _self = this;
  148.  
  149. (new Promise(function(resolve,reject){
  150. var xhrLoadEnd = function() {
  151. resolve(new realWorker(URL.createObjectURL(
  152. new Blob([getWrappedCode(false)+this.result])
  153. )));
  154. };
  155. var xhr = new XMLHttpRequest();
  156. xhr.open('GET', resourceURI, true);
  157. xhr.responseType = 'blob';
  158. xhr.onload = function(){
  159. if (this.status === 200) {
  160. var reader = new FileReader();
  161. reader.addEventListener("loadend", xhrLoadEnd);
  162. reader.readAsText(this.response);
  163. }
  164. };
  165. xhr.send();
  166. })).then(function(val) {
  167. _worker = val;
  168. _worker.onerror = _onerror;
  169. _worker.onmessage = _onmessage;
  170. var _e;
  171. while(_events.length) {
  172. _e = _events.shift();
  173. _worker[_e[0]].apply(_worker, _e[1]);
  174. }
  175. while(_messages.length) {
  176. _worker.postMessage(_messages.shift());
  177. }
  178. if (_terminate) {
  179. _worker.terminate();
  180. }
  181. });
  182.  
  183. _self.terminate = function(){
  184. _terminate = true;
  185. if (_worker) {
  186. _worker.terminate();
  187. }
  188. };
  189. Object.defineProperty(_self, 'onmessage', {
  190. get:function(){
  191. return _onmessage;
  192. },
  193. set:function(val){
  194. _onmessage = val;
  195. if (_worker) {
  196. _worker.onmessage = val;
  197. }
  198. }
  199. });
  200. Object.defineProperty(_self, 'onerror', {
  201. get:function(){
  202. return _onerror;
  203. },
  204. set:function(val){
  205. _onerror = val;
  206. if (_worker) {
  207. _worker.onmessage = val;
  208. }
  209. }
  210. });
  211. _self.postMessage = function(message){
  212. if (_worker) {
  213. _worker.postMessage(message);
  214. } else {
  215. _messages.push(message);
  216. }
  217. };
  218. _self.terminate = function() {
  219. _terminate = true;
  220. if (_worker) {
  221. _worker.terminate();
  222. }
  223. };
  224. _self.addEventListener = function(){
  225. if (_worker) {
  226. _worker.addEventListener.apply(_worker, arguments);
  227. } else {
  228. _events.push(['addEventListener',arguments]);
  229. }
  230. };
  231. _self.removeEventListener = function(){
  232. if (_worker) {
  233. _worker.removeEventListener.apply(_worker, arguments);
  234. } else {
  235. _events.push(['removeEventListener',arguments]);
  236. }
  237. };
  238. }
  239. win.Worker = wrappedWorker.bind(safeWin);
  240. }
  241.  
  242. function CreateElementWrapper() {
  243. var realCreateElement = document.createElement.bind(document),
  244. code = escape('<scr'+'ipt>'+getWrappedCode(true)+'</scr'+'ipt>');
  245.  
  246. function frameRewrite(e) {
  247. var f = e.target;
  248. if (f.src && /^data:text/i.test(f.src) && f.src.indexOf(code) < 0) {
  249. f.src = f.src.replace(',',',' + code);
  250. }
  251. }
  252.  
  253. function wrappedCreateElement(name) {
  254. if (name && name.toUpperCase &&
  255. name.toUpperCase() === 'IFRAME') {
  256. var ifr = realCreateElement.apply(document, arguments);
  257. ifr.addEventListener('load', frameRewrite, false);
  258. return ifr;
  259. }
  260. return realCreateElement.apply(document, arguments);
  261. }
  262. document.createElement = wrappedCreateElement.bind(document);
  263.  
  264. document.addEventListener('DOMContentLoaded', function(){
  265. var ifs = document.getElementsByTagName('IFRAME'), i = ifs.length;
  266. while(i--) {
  267. ifs[i].addEventListener('load', frameRewrite, false);
  268. }
  269. }, false);
  270. }
  271.  
  272. this.init = function() {
  273. WebSocketWrapper();
  274. WorkerWrapper();
  275. if (typeof document !== 'undefined') {
  276. CreateElementWrapper();
  277. }
  278. };
  279. }
  280.  
  281. if (/firefox/i.test(navigator.userAgent)) {
  282. var script = document.createElement('script');
  283. script.appendChild(document.createTextNode(getWrappedCode()));
  284. document.head.insertBefore(script, document.head.firstChild);
  285. return; //we don't want to call functions on page from here in Fx, so exit
  286. }
  287.  
  288. (new WSI((unsafeWindow||self||window),(self||window))).init();
  289. })();
  290.  
  291. if (!(/firefox/i.test(navigator.userAgent))) { // scripts for non-Firefox browsers
  292.  
  293. // https://greasyfork.org/scripts/14720-it-s-not-important
  294. (function(){
  295. var imptt = /((display|(margin|padding)(-top|-bottom)?)\s*:[^;!]*)!\s*important/ig;
  296.  
  297. function unimportanter(el, si) {
  298. if (!imptt.test(si) || el.style.display === 'none') {
  299. return 0; // get out if we have nothing to do here
  300. }
  301. if (el.nodeName === 'IFRAME' && el.src &&
  302. el.src.slice(0,17) === 'chrome-extension:') {
  303. return 0; // Web of Trust uses this method to add their frame
  304. }
  305. var so = si.replace(imptt, function(){return arguments[1];}), ret = 0;
  306. if (si !== so) {
  307. ret = 1;
  308. el.setAttribute('style', so);
  309. }
  310. return ret;
  311. }
  312.  
  313. function logger(c) {
  314. if (c) {
  315. console.log('Some page elements became a bit less important.');
  316. }
  317. }
  318.  
  319. function checkTarget(m, c) {
  320. var si = m.getAttribute ? m.getAttribute('style') : null;
  321. if (si && si.indexOf('!') > -1) {
  322. c += unimportanter(m, si);
  323. }
  324. return c;
  325. }
  326.  
  327. function checkNodes(m, c) {
  328. var i = m.length;
  329. while(i--) {
  330. c = checkTarget(m[i], c);
  331. }
  332. return c;
  333. }
  334.  
  335. var observer = new MutationObserver(function(mutations) {
  336. setTimeout(function(m) {
  337. var i = m.length, c = 0;
  338. while(i--) {
  339. if (m[i].target) {
  340. c = checkTarget(m[i].target, c);
  341. }
  342. if (m[i].addedNodes.length) {
  343. c = checkNodes(m[i].addedNodes, c);
  344. }
  345. }
  346. logger(c);
  347. },0,mutations);
  348. });
  349.  
  350. observer.observe(document, { childList : true, attributes : true, attributeFilter : ['style'], subtree : true });
  351.  
  352. win.addEventListener ("load", function(){
  353. var c = 0, imp = document.querySelectorAll('[style*="!"]'), i = imp.length;
  354. while(i--) {
  355. c+= checkTarget(imp[i], c);
  356. }
  357. logger(c);
  358. }, false);
  359. })();
  360.  
  361. }
  362.  
  363. if (/^https?:\/\/(news\.yandex\.|(www\.)?yandex\.[^\/]+\/(yand)?search[\/?])/i.test(win.location.href)) {
  364. // https://greasyfork.org/en/scripts/809-no-yandex-ads
  365. (function(){
  366. var adWords = ['Яндекс.Директ','Реклама','Ad'];
  367. function remove(node) {
  368. node.parentNode.removeChild(node);
  369. }
  370. // Generic ads removal and fixes
  371. function removeGenericAds() {
  372. var s, i;
  373. s = document.querySelector('.serp-header');
  374. if (s) {
  375. s.style.marginTop='0';
  376. }
  377. s = document.querySelectorAll('.serp-adv__head + .serp-item');
  378. i = s.length;
  379. while(i--) {
  380. s[i].parentNode.removeChild(s[i]);
  381. }
  382. s = document.querySelectorAll('#adbanner, .serp-adv, .b-spec-adv, div[class*="serp-adv__"]');
  383. i = s.length;
  384. while(i--) {
  385. remove(s[i]);
  386. }
  387. }
  388. // Search ads
  389. function removeSearchAds() {
  390. var s = document.querySelectorAll('.serp-block, .serp-item, .search-item');
  391. var i = s.length, item;
  392. while(i--) {
  393. item = s[i].querySelector('.label, .serp-item__label, .document__provider-name');
  394. if (item && adWords.indexOf(item.textContent) > -1) {
  395. remove(s[i]);
  396. console.log('Ads removed.');
  397. }
  398. }
  399. }
  400. // News ads
  401. function removeNewsAds() {
  402. var s = document.querySelectorAll('.page-content__left > *,.page-content__right > *:not(.page-content__col),.page-content__right > .page-content__col > *');
  403. var i = s.length;
  404. while(i--) {
  405. if (s[i].textContent.indexOf(adWords[0]) > -1) {
  406. remove(s[i]);
  407. console.log('Ads removed.');
  408. }
  409. }
  410. }
  411. // News fixes
  412. function removePageAdsClass() {
  413. if (document.body.classList.contains("b-page_ads_yes")){
  414. document.body.classList.remove("b-page_ads_yes");
  415. console.log('Page ads class removed.');
  416. }
  417. }
  418. // Function to attach an observer to monitor dynamic changes on the page
  419. function pageUpdateObserver(func, obj, params) {
  420. if (obj) {
  421. var o = new MutationObserver(func);
  422. o.observe(obj,(params || {childList:true, subtree:true}));
  423. }
  424. }
  425. // Cleaner
  426. document.addEventListener ("DOMContentLoaded", function() {
  427. removeGenericAds();
  428. if (win.location.hostname.search(/^news\./i) === 0) {
  429. pageUpdateObserver(removeNewsAds, document.querySelector('BODY'));
  430. pageUpdateObserver(removePageAdsClass, document.body, {attributes:true, attributesFilter:['class']});
  431. removeNewsAds();
  432. removePageAdsClass();
  433. } else {
  434. pageUpdateObserver(removeSearchAds, document.querySelector('.main__content'));
  435. removeSearchAds();
  436. }
  437. });
  438. })();
  439. return; //skip fixes for other sites
  440. }
  441.  
  442. // https://greasyfork.org/en/scripts/14470-4pda-unbrender
  443. if (/(^|\.)4pda\.ru$/i.test(window.location.hostname)) {
  444. (function(){
  445. var isForum = document.location.href.search('/forum/') !== -1,
  446. isSafari = (/Safari/i.test(navigator.userAgent)) && (/Apple\sComputer/i.test(navigator.vendor)),
  447. hStyle;
  448.  
  449. function remove(n) {
  450. if (n) {
  451. n.parentNode.removeChild(n);
  452. }
  453. }
  454.  
  455. function afterClean() {
  456. hStyle.disabled = true;
  457. remove(hStyle);
  458. }
  459.  
  460. function beforeClean() {
  461. // attach styles before document displayed
  462. hStyle = document.createElement('style');
  463. hStyle.id = 'ubrHider';
  464. hStyle.type = 'text/css';
  465. document.head.appendChild(hStyle);
  466.  
  467. hStyle.sheet.insertRule('html { overflow-y: scroll }', 0);
  468. hStyle.sheet.insertRule('article + aside * { display: none !important }', 0);
  469. hStyle.sheet.insertRule('#header + div:after {'+(
  470. 'content: "";'+
  471. 'position: fixed;'+
  472. 'top: 0;'+
  473. 'left: 0;'+
  474. 'width: 100%;'+
  475. 'height: 100%;'+
  476. 'background-color: #E6E7E9'
  477. )+'}', 0);
  478. // http://codepen.io/Beaugust/pen/DByiE
  479. hStyle.sheet.insertRule('@keyframes spin { 100% { transform: rotate(360deg) } }', 0);
  480. hStyle.sheet.insertRule('article + aside:after {'+(
  481. 'content: "";'+
  482. 'position: absolute;'+
  483. 'width: 150px;'+
  484. 'height: 150px;'+
  485. 'top: 150px;'+
  486. 'left: 50%;'+
  487. 'margin-top: -75px;'+
  488. 'margin-left: -75px;'+
  489. 'box-sizing: border-box;'+
  490. 'border-radius: 100%;'+
  491. 'border: 10px solid rgba(0, 0, 0, 0.2);'+
  492. 'border-top-color: rgba(0, 0, 0, 0.6);'+
  493. 'animation: spin 2s infinite linear'
  494. )+'}', 0);
  495.  
  496. // display content of a page if time to load a page is more than 2 seconds to avoid
  497. // blocking access to a page if it is loading for too long or stuck in a loading state
  498. setTimeout(2000, afterClean);
  499. }
  500.  
  501. GM_addStyle('#nav .use-ad {display: block !important;} ' +
  502. 'article:not(.post) + article:not(#id) { display: none !important }');
  503. if (!isForum && !isSafari) {
  504. beforeClean();
  505. }
  506.  
  507. // clean the page
  508. window.addEventListener('DOMContentLoaded', function(){
  509. var rem, si, lst, i;
  510. function width(){ return window.innerWidth||document.documentElement.clientWidth||document.body.clientWidth||0; }
  511. function height(){ return window.innerHeight||document.documentElement.clientHeight||document.body.clientHeight||0; }
  512.  
  513.  
  514. if (isForum) {
  515. si = document.querySelector('#logostrip');
  516. if (si) {
  517. remove(si.parentNode.nextSibling);
  518. }
  519. }
  520.  
  521. if (document.location.href.search('/forum/dl/') !== -1) {
  522. lst = document.querySelectorAll('body>div');
  523. i = lst.length;
  524. document.body.setAttribute('style', (document.body.getAttribute('style')||'')+
  525. ';background-color:black!important');
  526. while (i--) {
  527. if (!lst[i].querySelector('.dw-fdwlink')) {
  528. remove(lst[i]);
  529. }
  530. }
  531. }
  532.  
  533. if (isForum) { // Do not continue if it's a forum
  534. return;
  535. }
  536.  
  537. si = document.querySelector('#header');
  538. if (si) {
  539. rem = si.previousSibling;
  540. while (rem) {
  541. si = rem.previousSibling;
  542. remove(rem);
  543. rem = si;
  544. }
  545. }
  546.  
  547. lst = document.querySelectorAll('#nav li[class]');
  548. i = lst.length;
  549. while (i--) {
  550. if (lst[i] && lst[i].querySelector('a[href^="/tag/"]')) {
  551. remove(lst[i]);
  552. }
  553. }
  554.  
  555. lst = document.querySelectorAll('DIV');
  556. i = lst.length;
  557. var style, result;
  558. while (i--) {
  559. if (lst[i].offsetWidth > 0.95 * width() && lst[i].offsetHeight > 0.9 * height()) {
  560. style = window.getComputedStyle(lst[i], null);
  561. result = [];
  562. if(style.backgroundImage !== 'none') {
  563. result.push('background-image:none!important');
  564. }
  565. if(style.backgroundColor !== 'transparent') {
  566. result.push('background-color:transparent!important');
  567. }
  568. if (result.length) {
  569. if (lst[i].getAttribute('style')) {
  570. result.unshift(lst[i].getAttribute('style'));
  571. }
  572. lst[i].setAttribute('style', result.join(';'));
  573. }
  574. }
  575. }
  576.  
  577. lst = document.querySelectorAll('ASIDE>DIV');
  578. i = lst.length;
  579. while (i--) {
  580. if ( ((lst[i].querySelector('script, iframe, a[href*="/ad/www/"]') ||
  581. lst[i].querySelector('img[src$=".gif"]:not([height="0"]), img[height="400"]')) &&
  582. !lst[i].classList.contains('post') ) || !lst[i].childNodes.length ) {
  583. remove(lst[i]);
  584. }
  585. }
  586.  
  587. document.body.setAttribute('style', (document.body.getAttribute('style')||'')+';background-color:#E6E7E9!important');
  588.  
  589. // display content of the page
  590. afterClean();
  591. });
  592. })();
  593. return;
  594. }
  595.  
  596. // moonwalk.cc/hdgo.cc/couber.be/kodik.cc skip/fix
  597. (function(){
  598. if (!inIFrame()) {
  599. return;
  600. }
  601. // https://greasyfork.org/en/scripts/21937-moonwalk-hdgo-kodik-fix
  602. // v0.6 + my fixes
  603. document.addEventListener ("DOMContentLoaded",function() {
  604. var tmp;
  605. function log (e) {
  606. console.log('Moonwalk&HDGo&Kodik FIX: ' + e + ' player in ' + win.location.href);
  607. }
  608. if (win.adv_enabled !== undefined && win.condition_detected !== undefined) {
  609. log('Moonwalk');
  610. win.adv_enabled = false;
  611. win.condition_detected = false;
  612. // added from https://greasyfork.org/en/scripts/18847-delay-removal-moonwalk
  613. win.request_host_id = "19804";
  614. tmp = document.getElementById('player');
  615. if (tmp) {
  616. tmp.onclick = function() {
  617. window.showVideo();
  618. };
  619. }
  620. } else if (win.banner_second !== undefined && win.$banner_ads !== undefined) {
  621. log('HDGo');
  622. win.banner_second = 0;
  623. win.$banner_ads = false;
  624. win.$new_ads = false;
  625. win.canRunAds = true;
  626. tmp = document.body.querySelector('#swtf');
  627. if (tmp) {
  628. tmp.style.display = 'none';
  629. }
  630. } else if (win.MXoverrollCallback !== undefined && win.iframeSearch !== undefined) {
  631. log('Kodik');
  632. win.IsAdBlock = false;
  633. win.iframeSearch = null;
  634. tmp = document.getElementsByClassName('play_button')[0];
  635. if (tmp) {
  636. tmp.onclick = win.MXoverrollCallback.bind(win);
  637. }
  638. }
  639. }, false);
  640. })();
  641.  
  642. // function to search and remove nodes by content
  643. // selector - standard CSS selector to define set of nodes to check
  644. // words - regular expression to check content of the suspicious nodes
  645. // params - object with multiple extra parameters:
  646. // .hide - set display to none instead of removing from the page
  647. // .parent - parent node to remove if content is found in the child node
  648. // .siblings - number of simling nodes to remove (excluding text nodes)
  649. function scRemove(e) {e.parentNode.removeChild(e);}
  650. function scHide(e) {
  651. var s = e.getAttribute('style')||'',
  652. h = ';display:none!important;';
  653. if (s.indexOf(h) < 0) {
  654. e.setAttribute('style', s+h);
  655. }
  656. }
  657. function scissors (selector, words, scope, params) {
  658. var remFunc = (params.hide ? scHide : scRemove),
  659. iterFunc = (params.siblings > 0 ?
  660. 'nextSibling' :
  661. 'previousSibling'),
  662. nodes = scope.querySelectorAll(selector),
  663. i = nodes.length,
  664. toRemove = [],
  665. siblings,
  666. node;
  667. while(i--) {
  668. node = nodes[i];
  669. if (words.test(node.innerHTML) || !node.childNodes.length) {
  670. // drill up to the specified parent node if required
  671. if (params.parent) {
  672. while(node !== scope && !(node.matches(params.parent))) {
  673. node = node.parentNode;
  674. }
  675. }
  676. if (node === scope) {
  677. break;
  678. }
  679. toRemove.push(node);
  680. // add multiple nodes if defined more than one sibling
  681. siblings = Math.abs(params.siblings) || 0;
  682. while (siblings) {
  683. node = node[iterFunc];
  684. toRemove.push(node);
  685. if (node.nodeType === 1) {
  686. siblings -= 1; //count only element nodes
  687. }
  688. }
  689. }
  690. }
  691. i = toRemove.length;
  692. while(i--) {
  693. remFunc(toRemove[i]);
  694. }
  695.  
  696. return toRemove.length;
  697. }
  698.  
  699. // function to perform multiple checks if ads inserted with a delay
  700. // by default does 30 checks withing a 3 seconds unless nonstop mode specified
  701. // also does 1 extra check when a page completely loads
  702. // selector and words - passed dow to scissors
  703. // params - object with multiple extra parameters:
  704. // .root - selector to narrow down scope to scan;
  705. // .observe - if true then check will be performed continuously;
  706. // Other parameters passed down to scissors.
  707. function gardener(selector, words, params) {
  708. params = params || {};
  709. var scope = document.body,
  710. nonstop = false;
  711. // narrow down scope to a specific element
  712. if (params.root) {
  713. scope = scope.querySelector(params.root);
  714. if (!scope) {// exit if the root element is not present on the page
  715. return 0;
  716. }
  717. }
  718. // add observe mode if required
  719. if (params.observe) {
  720. if (typeof MutationObserver === 'function') {
  721. var o = new MutationObserver(function(ms){
  722. ms.forEach(function(m){
  723. if (m.addedNodes.length) {
  724. scissors(selector, words, scope, params);
  725. }
  726. });
  727. });
  728. o.observe(scope, {childList:true, subtree: true});
  729. } else {
  730. nonstop = true;
  731. }
  732. }
  733. // wait for a full page load to do one extra cut
  734. win.addEventListener('load',function(){
  735. scissors(selector, words, scope, params);
  736. });
  737. // do multiple cuts until ads removed
  738. function cut(sci, s, w, sc, p, i) {
  739. if (i > 0) {
  740. i -= 1;
  741. }
  742. if (i && !sci(s, w, sc, p)) {
  743. setTimeout(cut, 100, sci, s, w, sc, p, i);
  744. }
  745. }
  746. cut(scissors, selector, words, scope, params, (nonstop ? -1 : 30));
  747. }
  748.  
  749. function preventBackgroundRedirect() {
  750. // create "cose_me" event to call high-level window.close()
  751. var key = Math.random().toString(36).substr(2);
  752. window.addEventListener('close_me_'+key, function(e) {
  753. console.log('event!');
  754. window.close();
  755. });
  756.  
  757. // window.open wrapper
  758. function pbrLander() {
  759. var orgOpen = window.open.bind(window);
  760. function closeWindow(){
  761. // site went to a new tab and attempts to unload
  762. // call for high-level close through event
  763. var event = new CustomEvent("close_me_%key%", {});
  764. window.dispatchEvent(event);
  765. }
  766. function open(){
  767. var loc = arguments[0];
  768. if (loc && loc.indexOf &&
  769. (loc.indexOf(window.location.host) > -1 ||
  770. loc.indexOf('://') === -1)) {
  771. window.addEventListener('unload', closeWindow, true);
  772. }
  773. orgOpen.apply(window, arguments);
  774. }
  775. window.open = open.bind(window);
  776. var s = document.currentScript;
  777. if (s) {s.parentNode.removeChild(s);}
  778. }
  779.  
  780. // land wrapper on the page
  781. var script = document.createElement('script');
  782. script.appendChild(document.createTextNode('('+pbrLander.toString().replace(/%key%/g,key)+')();'));
  783. document.head.insertBefore(script,document.head.firstChild);
  784. console.log("Background redirect prevention enabled.");
  785. }
  786.  
  787. function forbidServiceWorker() {
  788. if (!("serviceWorker" in navigator)) {
  789. return;
  790. }
  791. var svr = navigator.serviceWorker.ready;
  792. Object.defineProperty(navigator, 'serviceWorker', {
  793. value: {
  794. register: function(){
  795. console.log('Registration of serviceWorker', arguments[0], 'blocked.');
  796. return new Promise(function(){});
  797. },
  798. ready: new Promise(function(){}),
  799. addEventListener:function(){}
  800. }
  801. });
  802. document.addEventListener('DOMContentLoaded', function() {
  803. if (!svr) {
  804. return;
  805. }
  806. svr.then(function(sw) {
  807. console.log('Found existing serviceWorker:', sw);
  808. console.log('Attempting to unregister...');
  809. sw.unregister().then(function() {
  810. console.log('Unregistered! :)');
  811. }).catch(function(err) {
  812. console.log('Unregistration failed. :(', err);
  813. console.log('Try to remove it manually:');
  814. console.log(' 1. Open: chrome://serviceworker-internals/ (Google Chrome and alike) or about:serviceworkers (Mozilla Firefox) in a new tab.');
  815. console.log(' 2. Search there for one with "'+document.domain+'" in the name.');
  816. console.log(' 3. Use buttons in the same block with service you found to stop it and uninstall/unregister.');
  817. });
  818. }).catch(function(err) {
  819. console.log("Lol, it failed on it's own. -_-", err);
  820. });
  821. }, false);
  822. }
  823.  
  824. var scripts = {};
  825. scripts['fs.to'] = function() {
  826. function skipClicker(i) {
  827. if (!i) {
  828. return;
  829. }
  830. var skip = document.querySelector('.b-aplayer-banners__close');
  831. if (skip) {
  832. skip.click();
  833. } else {
  834. setTimeout(skipClicker, 100, i-1);
  835. }
  836. }
  837. setTimeout(skipClicker, 100, 30);
  838.  
  839. (function appendStyle(observer){
  840. var style = document.head.appendChild(document.createElement('style'));
  841. style.type = 'text/css';
  842. style.sheet.insertRule(
  843. '.l-body-branding *,'+
  844. '.b-styled__item-central,'+
  845. '.b-styled__content-right,'+
  846. '.b-styled__section-central,'+
  847. 'div[id^="adsProxy-"]'+
  848. '{display:none!important}', 0);
  849. style.sheet.insertRule(
  850. 'body {background-image:url(data:image/png;base64,'+
  851. 'iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAACXBIWXMAAC4jAAAuIwF4pT92AAAADUlEQVR42mOQUdL5DwACMgFqBC3ttwAAAABJRU5ErkJggg=='+
  852. ')!important}');
  853. Object.defineProperty(style, 'sheet', {
  854. value: style.sheet,
  855. configurable: false,
  856. enumerable: true,
  857. writable: false
  858. });
  859. if(!observer) {
  860. return;
  861. }
  862. var o = new MutationObserver(function(ms){
  863. ms.forEach(function(m){
  864. m.removedNodes.forEach(function(n){
  865. if (n === style) {
  866. appendStyle(false);
  867. }
  868. });
  869. });
  870. });
  871. o.observe(style.parentNode,{childList:true});
  872. })(true);
  873.  
  874. if (/\/(view_iframe|iframeplayer)\//i.test(document.location.pathname)) {
  875. var p = document.querySelector('#player:not([preload="auto"])'),
  876. m = document.querySelector('.main'),
  877. adStepper = function(p) {
  878. if (p.currentTime < p.duration) {
  879. p.currentTime += 1;
  880. }
  881. },
  882. adSkipper = function(f, p) {
  883. f.click();
  884. p.waitAfterSkip = false;
  885. p.longerSkipper = false;
  886. console.log('Пропустили.');
  887. },
  888. cl = function(p) {
  889. var faster = document.querySelector('.b-aplayer__html5-desktop-skip'),
  890. series = document.querySelector('.b-aplayer__actions-series');
  891.  
  892. function clickSelected() {
  893. var s = document.querySelector('.b-aplayer__popup-series-episodes .selected a');
  894. if (s) {
  895. s.click();
  896. }
  897. }
  898.  
  899. if ((!faster || faster.style.display !== 'block') && series && !p.seriesClicked) {
  900. series.click();
  901. p.seriesClicked = true;
  902. p.longerSkipper = true;
  903. setTimeout(clickSelected, 1000);
  904. p.pause();
  905. }
  906.  
  907. function skipListener() {
  908. if (p.waitAfterSkip) {
  909. console.log('В процессе пропуска…');
  910. return;
  911. }
  912. p.pause();
  913. if (!p.classList.contains('m-hidden')) {
  914. p.classList.add('m-hidden');
  915. }
  916. if (faster && p.currentTime &&
  917. win.getComputedStyle(faster).display === 'block' &&
  918. !faster.querySelector('.b-aplayer__html5-desktop-skip-timer')) {
  919. p.waitAfterSkip = true;
  920. setTimeout(adSkipper, (p.longerSkipper?3:1)*1000, faster, p);
  921. console.log('Доступен быстрый пропуск…');
  922. } else {
  923. setTimeout(adStepper, 1000, p);
  924. }
  925. }
  926.  
  927. p.addEventListener('timeupdate', skipListener, false);
  928. },
  929. o = new MutationObserver(function (mut) {
  930. mut.forEach(function (e) {
  931. var i = e.addedNodes.length;
  932. while(i--) {
  933. if (e.addedNodes[i].id === 'player' &&
  934. e.addedNodes[i].nodeName === 'VIDEO' &&
  935. e.addedNodes[i].getAttribute('preload') !== 'auto') {
  936. cl(e.addedNodes[i]);
  937. }
  938. }
  939. });
  940. });
  941. if (p.nodeName === 'VIDEO') {
  942. cl(p);
  943. } else {
  944. o.observe(m, {childList: true});
  945. }
  946. }
  947. };
  948. scripts['brb.to'] = scripts['fs.to'];
  949. scripts['cxz.to'] = scripts['fs.to'];
  950.  
  951. scripts['drive2.ru'] = function() {
  952. gardener('.c-block', />Реклама<\/|\.relap\..*display:\s?none/i);
  953. };
  954.  
  955. scripts['fishki.net'] = function() {
  956. gardener('.main-post', /543769|Реклама/);
  957. };
  958.  
  959. scripts['hdgo.cc'] = {
  960. 'now': function(){
  961. var o = new MutationObserver(function(ms){
  962. ms.forEach(function(m){
  963. m.addedNodes.forEach(function(n){
  964. if (n.tagName === 'SCRIPT' && n.getAttribute('onerror') !== null) {
  965. n.removeAttribute('onerror');
  966. }
  967. });
  968. });
  969. });
  970. o.observe(document, {childList:true, subtree: true});
  971. }
  972. };
  973. scripts['couber.be'] = scripts['hdgo.cc'];
  974. scripts['46.30.43.38'] = scripts['hdgo.cc'];
  975.  
  976. scripts['hdrezka.me'] = function() {
  977. gardener('div[id][onclick][onmouseup][onmousedown]', /onmouseout/i);
  978. };
  979.  
  980. scripts['naruto-base.su'] = function() {
  981. gardener('div[id^="entryID"],.block', /href="http.*?target="_blank"/i);
  982. };
  983.  
  984. scripts['pb.wtf'] = function() {
  985. GM_addStyle('#result,tbody.row1:not([id]) {display: none !important}');
  986. gardener('a[href$="=="]', /img/i, {root:'#page_container .containe', observe:true, parent:'div[class]'});
  987. gardener('a[href^="/"]', /<img\s.*<br>/i, {root:'#main_content', observe:true, parent:'div[class]'});
  988. gardener('.re_top1', /./, {root:'#main_content', parent:'table.border'});
  989. };
  990. scripts['piratbit.org'] = scripts['pb.wtf'];
  991. scripts['piratbit.ru'] = scripts['pb.wtf'];
  992.  
  993. scripts['pikabu.ru'] = function() {
  994. gardener('.story', /story__sponsor|story__gag|profile\/ads"/i, {root: '.inner_wrap', observe: true});
  995. };
  996.  
  997. scripts['rustorka.com'] = function() {
  998. var s = document.head.childNodes, i = s.length;
  999. if (i < 5) {
  1000. while(i--) {
  1001. if (s[i].httpEquiv && s[i].httpEquiv === 'refresh') {
  1002. win.close();
  1003. }
  1004. }
  1005. }
  1006. gardener('span[class],ul[class],span[id],ul[id]', /\/\d{12,}\.php/i, {root:'#sidebar1', observe:true});
  1007. gardener('div[id][style*="!important"]', /!important/i);
  1008. };
  1009. scripts['rumedia.ws'] = scripts['rustorka.com'];
  1010.  
  1011. scripts['sports.ru'] = function() {
  1012. gardener('.aside-news-list__item', /aside-news-list__advert/i, {root:'.aside-news-block'});
  1013. };
  1014.  
  1015. scripts['turbobit.net'] = {'now': preventBackgroundRedirect};
  1016.  
  1017. scripts['yap.ru'] = function() {
  1018. var words = /member1438|Administration/;
  1019. gardener('form > table[id^="p_row_"]', words);
  1020. gardener('tr > .holder.newsbottom', words, {parent:'tr', siblings:-2});
  1021. };
  1022. scripts['yaplakal.com'] = scripts['yap.ru'];
  1023.  
  1024. scripts['reactor.cc'] = {
  1025. 'now': preventBackgroundRedirect,
  1026. 'DOMContentLoaded': function() {
  1027. var words = new RegExp(
  1028. 'блокировщика рекламы'
  1029. .split('')
  1030. .map(e => e+'[\u200b\u200c\u200d]*')
  1031. .join('')
  1032. .replace(' ', '\\s*')
  1033. .replace(/[аоре]/g, e=>['[аa]','[оo]','[рp]','[еe]']['аоре'.indexOf(e)]),
  1034. 'i'),
  1035. can;
  1036. function deeper(spider) {
  1037. var c, l, n;
  1038. if (words.test(spider.innerText)) {
  1039. if (spider.nodeType === Node.TEXT_NODE) {
  1040. return true;
  1041. }
  1042. c = spider.childNodes;
  1043. l = c.length;
  1044. n = 0;
  1045. while(l--) {
  1046. if (deeper(c[l]), can) {
  1047. n++;
  1048. }
  1049. }
  1050. if (n > 0 && n === c.length && spider.offsetHeight < 750) {
  1051. can.push(spider);
  1052. }
  1053. return false;
  1054. }
  1055. return true;
  1056. }
  1057. function probe(){
  1058. if (words.test(document.body.innerText)) {
  1059. can = [];
  1060. deeper(document.body);
  1061. var i = can.length, j, spider;
  1062. while(i--) {
  1063. spider = can[i];
  1064. if (spider.offsetHeight > 10 && spider.offsetHeight < 750) {
  1065. spider.setAttribute('style', 'background:none!important');
  1066. }
  1067. }
  1068. }
  1069. }
  1070. var o = new MutationObserver(probe);
  1071. o.observe(document,{childList:true, subtree:true});
  1072. }
  1073. };
  1074. scripts['joyreactor.cc'] = scripts['reactor.cc'];
  1075. scripts['pornreactor.cc'] = scripts['reactor.cc'];
  1076.  
  1077. scripts['auto.ru'] = function() {
  1078. var words = /Реклама|Яндекс.Директ|yandex_ad_/;
  1079. var userAdsListAds = [
  1080. '.listing-list > .listing-item',
  1081. '.listing-item_type_fixed.listing-item'
  1082. ];
  1083. var catalogAds = [
  1084. 'div[class*="layout_catalog-inline"]',
  1085. 'div[class$="layout_horizontal"]'
  1086. ];
  1087. var otherAds = [
  1088. '.advt_auto',
  1089. '.sidebar-block',
  1090. '.pager-listing + div[class]',
  1091. '.card > div[class][style]',
  1092. '.sidebar > div[class]',
  1093. '.main-page__section + div[class]',
  1094. '.listing > tbody'];
  1095. gardener(userAdsListAds.join(','), words, {root:'.listing-wrap', observe:true});
  1096. gardener(catalogAds.join(','), words, {root:'.catalog__page,.content__wrapper', observe:true});
  1097. gardener(otherAds.join(','), words);
  1098. };
  1099.  
  1100. scripts['online.anidub.com'] = function() {
  1101. var script = document.createElement('script');
  1102. script.type = "text/javascript";
  1103. script.innerHTML = "function ogonekstart1() {}";
  1104. document.getElementsByTagName('head')[0].appendChild(script);
  1105.  
  1106. var style = document.createElement('style');
  1107. style.type = 'text/css';
  1108. style.appendChild(document.createTextNode('.background {background: none!important;}'));
  1109. style.appendChild(document.createTextNode('.background > script + div, .background > script ~ div:not([id]):not([class]) + div[id][class] {display:none!important}'));
  1110. document.head.appendChild(style);
  1111. };
  1112.  
  1113. scripts['rsload.net'] = function() {
  1114. win.addEventListener('load', function() {
  1115. var dis = document.querySelector('.cb-disable');
  1116. if (dis) {
  1117. dis.click();
  1118. }
  1119. });
  1120. document.addEventListener('click',function(e){
  1121. var t = e.target;
  1122. if (t && t.href && (/:\/\/\d+\.\d+\.\d+\.\d+\//.test(t.href))) {
  1123. t.href = t.href.replace('://','://rsload.net:rsload.net@');
  1124. }
  1125. });
  1126. };
  1127.  
  1128. scripts['imageban.ru'] = {
  1129. 'now': preventBackgroundRedirect,
  1130. 'DOMContentLoaded': function() {
  1131. win.addEventListener('unload', function() {
  1132. if (!window.location.hash) {
  1133. window.location.replace(window.location+'#');
  1134. } else {
  1135. window.location.hash = '';
  1136. }
  1137. }, true);
  1138. }
  1139. };
  1140.  
  1141. var domain = document.domain, name;
  1142. while (domain.indexOf('.') !== -1) {
  1143. if (scripts.hasOwnProperty(domain)) {
  1144. if (typeof scripts[domain] === 'function') {
  1145. document.addEventListener ('DOMContentLoaded', scripts[domain], false);
  1146. }
  1147. for (name in scripts[domain]) {
  1148. if (name !== 'now') {
  1149. document.addEventListener (name, scripts[domain][name], false);
  1150. } else {
  1151. scripts[domain].now();
  1152. }
  1153. }
  1154. }
  1155. domain = domain.slice(domain.indexOf('.') + 1);
  1156. }
  1157. })();