RU AdList JS Fixes

try to take over the world!

目前為 2016-08-19 提交的版本,檢視 最新版本

  1. // ==UserScript==
  2. // @name RU AdList JS Fixes
  3. // @namespace ruadlist_js_fixes
  4. // @version 1.0.40
  5. // @description try to take over the world!
  6. // @author lainverse & dimisa
  7. // @match *://*/*
  8. // @grant unsafeWindow
  9. // @grant window.close
  10. // @run-at document-start
  11. // ==/UserScript==
  12.  
  13. (function() {
  14. 'use strict';
  15. var win = unsafeWindow || window;
  16. function inIFrame() {
  17. try {
  18. return win.self !== win.top;
  19. } catch (ignore) {
  20. return true;
  21. }
  22. }
  23.  
  24. if (!(/firefox/i.test(navigator.userAgent))) { // scripts for non-Firefox browsers
  25.  
  26. // https://greasyfork.org/scripts/19144-websuckit/
  27. (function() {
  28. // check if the browser supports Proxy and WebSocket
  29. if (typeof Proxy !== 'function' ||
  30. typeof WebSocket !== 'function') {
  31. return;
  32. }
  33. var to_block = [
  34. '||bgrndi.com^',
  35. '||brokeloy.com^',
  36. '||dreadfula.ru^',
  37. '||et-code.ru^',
  38. '||gocdn.ru^',
  39. '||hghit.com^',
  40. '||kuveres.com^',
  41. '||lepubs.com^',
  42. '||mail.ru^',
  43. '||marketgid.com^',
  44. '||mxtads.com^',
  45. '||psma01.com^',
  46. '||psma02.com^',
  47. '||psma03.com^',
  48. '||recreativ.ru^',
  49. '||regpole.com^',
  50. '||skidl.ru^',
  51. '||torvind.com^',
  52. '||trafmag.com^',
  53. '||xxuhter.ru^',
  54. '||yuiout.online^'
  55. ];
  56. var masks = [];
  57. to_block.forEach(function(m){
  58. masks.push(new RegExp(
  59. m.replace(/([\\\/\[\].*+?(){}$])/g, '\\$1')
  60. .replace(/\^(?!$)/g,'\\.?[^\\w%._-]')
  61. .replace(/\^$/,'\\.?([^\\w%._-]|$)')
  62. .replace(/^\|\|/,'^wss?:\\/+([^\/.]+\\.)*'),
  63. 'i'));
  64. });
  65. var ws = win.WebSocket,
  66. closingFunctions = ['close', 'send'];
  67. function wsGetter(tgt, nm) {
  68. console.log('[WSI] Registered call to property "', nm, '"');
  69. try {
  70. if (typeof ws.prototype[nm] === 'function') {
  71. if (closingFunctions.indexOf(nm) > -1) {
  72. tgt.readyState = ws.CLOSED;
  73. }
  74. return function(){return;};
  75. }
  76. if (typeof ws.prototype[nm] === 'number') {
  77. return ws[nm];
  78. }
  79. } catch(ignore) {}
  80. return tgt[nm];
  81. }
  82. win.WebSocket = new Proxy(ws, {
  83. construct: function(target, args) {
  84. var url = args[0];
  85. console.log('[WSI] Opening socket on', url, '…');
  86. var i = masks.length;
  87. while(i--) {
  88. if (masks[i].test(url)) {
  89. console.log("[WSI] Blocked.");
  90. return new Proxy({url: url, readyState: ws.OPEN}, {
  91. get: wsGetter
  92. });
  93. }
  94. }
  95. return new target(args[0], args[1]);
  96. }
  97. });
  98. })();
  99.  
  100. // https://greasyfork.org/scripts/14720-it-s-not-important
  101. (function(){
  102. var imptt = /((display|(margin|padding)(-top|-bottom)?)\s*:[^;!]*)!\s*important/ig;
  103.  
  104. function unimportanter(el, si) {
  105. if (!imptt.test(si) || el.style.display === 'none') {
  106. return 0; // get out if we have nothing to do here
  107. }
  108. if (el.nodeName === 'IFRAME' && el.src &&
  109. el.src.slice(0,17) === 'chrome-extension:') {
  110. return 0; // Web of Trust uses this method to add their frame
  111. }
  112. var so = si.replace(imptt, function(){return arguments[1];}), ret = 0;
  113. if (si !== so) {
  114. ret = 1;
  115. el.setAttribute('style', so);
  116. }
  117. return ret;
  118. }
  119.  
  120. function logger(c) {
  121. if (c) {
  122. console.log('Some page elements became a bit less important.');
  123. }
  124. }
  125.  
  126. function checkTarget(m, c) {
  127. var si = m.getAttribute ? m.getAttribute('style') : null;
  128. if (si && si.indexOf('!') > -1) {
  129. c += unimportanter(m, si);
  130. }
  131. return c;
  132. }
  133.  
  134. function checkNodes(m, c) {
  135. var i = m.length;
  136. while(i--) {
  137. c = checkTarget(m[i], c);
  138. }
  139. return c;
  140. }
  141.  
  142. var observer = new MutationObserver(function(mutations) {
  143. setTimeout(function(m) {
  144. var i = m.length, c = 0;
  145. while(i--) {
  146. if (m[i].target) {
  147. c = checkTarget(m[i].target, c);
  148. }
  149. if (m[i].addedNodes.length) {
  150. c = checkNodes(m[i].addedNodes, c);
  151. }
  152. }
  153. logger(c);
  154. },0,mutations);
  155. });
  156.  
  157. observer.observe(document, { childList : true, attributes : true, attributeFilter : ['style'], subtree : true });
  158.  
  159. win.addEventListener ("load", function(){
  160. var c = 0, imp = document.querySelectorAll('[style*="!"]'), i = imp.length;
  161. while(i--) {
  162. c+= checkTarget(imp[i], c);
  163. }
  164. logger(c);
  165. }, false);
  166. })();
  167.  
  168. }
  169.  
  170. if (/^https?:\/\/(news\.yandex\.|(www\.)?yandex\.[^\/]+\/(yand)?search[\/?])/i.test(win.location.href)) {
  171. // https://greasyfork.org/en/scripts/809-no-yandex-ads
  172. (function(){
  173. // Generic ads removal and fixes
  174. function removeGenericAds() {
  175. var s, i;
  176. s = document.querySelector('.serp-header');
  177. if (s) {
  178. s.style.marginTop='0';
  179. }
  180. s = document.querySelectorAll('.serp-adv__head + .serp-item');
  181. i = s.length;
  182. while(i--) {
  183. s[i].parentNode.removeChild(s[i]);
  184. }
  185. s = document.querySelectorAll('#adbanner, .serp-adv, .b-spec-adv, div[class*="serp-adv__"]');
  186. i = s.length;
  187. while(i--) {
  188. s[i].parentNode.removeChild(s[i]);
  189. }
  190. }
  191. // Search ads
  192. function removeSearchAds() {
  193. var s = document.querySelectorAll('.serp-block, .serp-item, .search-item');
  194. var i = s.length, item;
  195. while(i--) {
  196. item = s[i].querySelector('.label, .serp-item__label, .document__provider-name');
  197. if (item && (
  198. item.textContent.indexOf('Реклама') > -1 ||
  199. item.textContent.indexOf('Яндекс.Директ') > -1)) {
  200. s[i].parentNode.removeChild(s[i]);
  201. console.log('Ads removed.');
  202. }
  203. }
  204. }
  205. // News ads
  206. function removeNewsAds() {
  207. var s = document.querySelectorAll('.story[id], .document[id], .story__group[id]');
  208. var i = s.length;
  209. while(i--) {
  210. if (win.getComputedStyle(s[i]).position === 'absolute') {
  211. s[i].parentNode.removeChild(s[i]);
  212. console.log('Ads removed.');
  213. }
  214. }
  215. }
  216. // News fixes
  217. function removePageAdsClass() {
  218. if (document.body.classList.contains("b-page_ads_yes")){
  219. document.body.classList.remove("b-page_ads_yes");
  220. console.log('Page ads class removed.');
  221. }
  222. }
  223. // Function to attach an observer to monitor dynamic changes on the page
  224. function pageUpdateObserver(func, obj, params) {
  225. if (obj) {
  226. var o = new MutationObserver(func);
  227. o.observe(obj,(params || {childList:true}));
  228. }
  229. }
  230. // Cleaner
  231. document.addEventListener ("DOMContentLoaded", function() {
  232. removeGenericAds();
  233. if (win.location.hostname.search(/^news\./i) === 0) {
  234. pageUpdateObserver(removeNewsAds, document.querySelector('BODY'));
  235. pageUpdateObserver(removePageAdsClass, document.body, {attributes:true, attributesFilter:['class']});
  236. removeNewsAds();
  237. removePageAdsClass();
  238. } else {
  239. pageUpdateObserver(removeSearchAds, document.querySelector('.main__content'));
  240. removeSearchAds();
  241. }
  242. });
  243. })();
  244. return; //skip fixes for other sites
  245. }
  246.  
  247. // https://greasyfork.org/en/scripts/21937-moonwalk-hdgo-kodik-fix
  248. (function () {
  249. if (!inIFrame) {
  250. return;
  251. }
  252.  
  253. document.addEventListener ("DOMContentLoaded", function() {
  254. var player;
  255. if (win.iframe_adv_enabled !== undefined) {
  256. win.iframe_adv_enabled = false;
  257. } else if (win.banner_second !== undefined) {
  258. win.banner_second = 0;
  259. player = document.getElementById('play-player-hd');
  260. if (player) {
  261. player.onclick = function() {
  262. var adsdiv = document.getElementById("ads-player-hd");
  263. adsdiv.parentNode.removeChild(adsdiv);
  264. win.setPlayer();
  265. };
  266. }
  267. } else if (win.MXoverrollCallback !== undefined) {
  268. player = document.getElementsByClassName('play_button')[0];
  269. if (player) {
  270. player.onclick = win.MXoverrollCallback.bind(window);
  271. }
  272. }
  273. },false);
  274. })();
  275.  
  276. document.addEventListener ("DOMContentLoaded", function() {
  277. // function to search and remove nodes by content
  278. // selector - standard CSS selector to define set of nodes to check
  279. // words - regular expression to check content of the suspicious nodes
  280. // params - object with multiple extra parameters:
  281. // .parent - parent node to remove if content is found in the child node
  282. // .siblings - number of simling nodes to remove (excluding text nodes)
  283. function scissors (selector, words, scope, params) {
  284. var nodes = scope.querySelectorAll(selector),
  285. i = nodes.length,
  286. toRemove = [],
  287. siblings = Math.abs(params.siblings) || 0,
  288. iterFunc = params.siblings > 0 ? 'nextSibling' : 'previousSibling',
  289. node;
  290. while(i--) {
  291. node = nodes[i];
  292. if (words.test(node.innerHTML) || !node.childNodes.length) {
  293. // drill up to the specified parent node if required
  294. if (params.parent) {
  295. while(node !== scope && !(node.matches(params.parent))) {
  296. node = node.parentNode;
  297. }
  298. }
  299. if (node === scope) {
  300. break;
  301. }
  302. toRemove.push(node);
  303. // add multiple nodes if defined more than one sibling
  304. while (siblings) {
  305. node = node[iterFunc];
  306. toRemove.push(node);
  307. if (node.tagName) {
  308. siblings -= 1; //don't count text nodes
  309. }
  310. }
  311. }
  312. }
  313. i = toRemove.length;
  314. while(i--) {
  315. toRemove[i].parentNode.removeChild(toRemove[i]);
  316. }
  317.  
  318. return toRemove.length;
  319. }
  320.  
  321. // function to perform multiple checks if ads inserted with a delay
  322. // by default does 30 checks withing a 3 seconds unless nonstop mode specified
  323. // also does 1 extra check when a page completely loads
  324. // selector and words - passed dow to scissors
  325. // params - object with multiple extra parameters:
  326. // .root - selector to narrow down scope to scan;
  327. // .observe - if true then check will be performed continuously;
  328. // .parent - passed down to scissors;
  329. // .siblings - passed down to scissors;
  330. function gardener(selector, words, params) {
  331. params = params || {};
  332. var scope = document.body,
  333. nonstop = false;
  334. // narrow down scope to a specific element
  335. if (params.root) {
  336. scope = scope.querySelector(params.root);
  337. if (!scope) {// exit if the root element is not present on the page
  338. return 0;
  339. }
  340. }
  341. // add observe mode if required
  342. if (params.observe) {
  343. if (typeof MutationObserver === 'function') {
  344. var o = new MutationObserver(function(ms){
  345. ms.forEach(function(m){
  346. if (m.addedNodes.length) {
  347. scissors(selector, words, scope, params);
  348. }
  349. });
  350. });
  351. o.observe(document.querySelector(params.root),
  352. {childList:true, subtree: true});
  353. } else {
  354. nonstop = true;
  355. }
  356. }
  357. // wait for a full page load to do one extra cut
  358. win.addEventListener('load',function(){
  359. scissors(selector, words, scope, params);
  360. });
  361. // do multiple cuts until ads removed
  362. function cut(sci, s, w, sc, p, i) {
  363. if (i > 0) {
  364. i -= 1;
  365. }
  366. if (i && !sci(s, w, sc, p)) {
  367. setTimeout(cut, 100, sci, s, w, sc, p, i);
  368. }
  369. }
  370. cut(scissors, selector, words, scope, params, (nonstop ? -1 : 30));
  371. }
  372.  
  373. function preventBackgroundRedirect() {
  374. console.log("Background redirect prevention enabled.");
  375. var orgOpen = win.open;
  376. win.open = function(){
  377. var loc = arguments[0];
  378. if (loc.indexOf(win.location.host) > -1 ||
  379. loc.indexOf('://') === -1) {
  380. win.addEventListener('unload',function(){
  381. win.close();
  382. }, true);
  383. }
  384. orgOpen.apply(window, arguments);
  385. };
  386. }
  387.  
  388. var scripts = {};
  389. scripts['fs.to'] = function() {
  390. function skipClicker(i) {
  391. if (!i) {
  392. return;
  393. }
  394. var skip = document.querySelector('.b-aplayer-banners__close');
  395. if (skip) {
  396. skip.click();
  397. } else {
  398. setTimeout(skipClicker, 100, i-1);
  399. }
  400. }
  401. setTimeout(skipClicker, 100, 30);
  402.  
  403. var divs = document.getElementsByTagName('div'),
  404. re = /\w{1,5}\d{1,5}\w{1,5}\d{1,5}/,
  405. i = divs.length;
  406. while(i--) {
  407. if (re.test(divs[i].className)) {
  408. divs[i].style.display = 'none';
  409. }
  410. }
  411.  
  412. var style = document.head.appendChild( document.createElement('style') );
  413. style.type = 'text/css';
  414.  
  415. var toHide = [
  416. '.b-aplayer-teasers > a',
  417. '.b-player-popup__content > div[class][style="position: relative;"]',
  418. 'div[class^="b-adproxy"]',
  419. 'div[id^="admixer_async_"]'
  420. ];
  421. style.sheet.insertRule(toHide.join(',')+'{display:none!important}', 0);
  422.  
  423. if (/\/view_iframe\//i.test(document.location.pathname)) {
  424. var p = document.querySelector('#player:not([preload="auto"])'),
  425. m = document.querySelector('.main'),
  426. adStepper = function(p) {
  427. if (p.currentTime < p.duration) {
  428. p.currentTime += 1;
  429. }
  430. },
  431. adSkipper = function(f, p) {
  432. f.click();
  433. p.waitAfterSkip = false;
  434. console.log('Пропущена.');
  435. },
  436. cl = function(p) {
  437. var faster = document.querySelector('.b-aplayer__html5-desktop-skip');
  438.  
  439. function skipListener() {
  440. if (p.waitAfterSkip) {
  441. console.log('Доступен быстрый пропуск рекламы…');
  442. return;
  443. }
  444. p.pause();
  445. if (!p.classList.contains('m-hidden')) {
  446. p.classList.add('m-hidden');
  447. }
  448. if (faster &&
  449. win.getComputedStyle(faster).display === 'block' &&
  450. !faster.querySelector('.b-aplayer__html5-desktop-skip-timer')) {
  451. p.waitAfterSkip = true;
  452. setTimeout(adSkipper, 1000, faster, p);
  453. } else {
  454. setTimeout(adStepper, 1000, p);
  455. }
  456. }
  457.  
  458. p.addEventListener('timeupdate', skipListener, false);
  459. },
  460. o = new MutationObserver(function (mut) {
  461. mut.forEach(function (e) {
  462. var i = e.addedNodes.length;
  463. while(i--) {
  464. if (e.addedNodes[i].id === 'player' &&
  465. e.addedNodes[i].nodeName === 'VIDEO' &&
  466. e.addedNodes[i].getAttribute('preload') !== 'auto') {
  467. cl(e.addedNodes[i]);
  468. }
  469. }
  470. });
  471. });
  472. if (p.nodeName === 'VIDEO') {
  473. cl(p);
  474. } else {
  475. o.observe(m, {childList: true});
  476. }
  477. }
  478. };
  479. scripts['brb.to'] = scripts['fs.to'];
  480. scripts['cxz.to'] = scripts['fs.to'];
  481.  
  482. scripts['drive2.ru'] = function() {
  483. gardener('.g-column-wide > .c-block', /Реклама|\.relap\./i);
  484. };
  485.  
  486. scripts['pikabu.ru'] = function() {
  487. gardener('.story', /story__sponsor|profile\/ads"/i, {root:'.stories,.page-story', observe: true});
  488. };
  489.  
  490. scripts['fishki.net'] = function() {
  491. gardener('.main-post', /543769|Реклама/);
  492. };
  493.  
  494. scripts['hdrezka.me'] = function() {
  495. gardener('div[id][onclick][onmouseup][onmousedown]', /onmouseout/i);
  496. };
  497.  
  498. scripts['naruto-base.tv'] = function() {
  499. gardener('div[id^="entryID"],center', /\/goo.gl\//i);
  500. };
  501.  
  502. scripts['pb.wtf'] = function() {
  503. gardener('a[href$="=="]', /img/i, {root:'#page_container .containe', observe:true, parent:'div[class]'});
  504. gardener('a[href^="/"]', /<img\s.*<br>/i, {root:'#main_content', observe:true, parent:'div[class]'});
  505. };
  506. scripts['piratbit.org'] = scripts['pb.wtf'];
  507. scripts['piratbit.ru'] = scripts['pb.wtf'];
  508.  
  509. scripts['sports.ru'] = function() {
  510. gardener('.aside-news-list__item', /aside-news-list__advert/i, {root:'.aside-news-block'});
  511. };
  512.  
  513. scripts['rustorka.com'] = function() {
  514. var s = document.head.childNodes, i = s.length;
  515. if (i < 5) {
  516. while(i--) {
  517. if (s[i].httpEquiv && s[i].httpEquiv === 'refresh') {
  518. win.close();
  519. }
  520. }
  521. }
  522. gardener('span[class],ul[class],span[id],ul[id]', /\/\d{12,}\.php/i, {root:'#sidebar1', observe:true});
  523. gardener('div[id][style*="!important"]', /!important/i);
  524. };
  525. scripts['rumedia.ws'] = scripts['rustorka.com'];
  526.  
  527. scripts['yap.ru'] = function() {
  528. var words = /member1438|Administration/;
  529. gardener('form > table[id^="p_row_"]', words);
  530. gardener('tr > .holder.newsbottom', words, {parent:'tr', siblings:-2});
  531. };
  532. scripts['yaplakal.com'] = scripts['yap.ru'];
  533.  
  534. scripts['reactor.cc'] = preventBackgroundRedirect;
  535. scripts['joyreactor.cc'] = preventBackgroundRedirect;
  536. scripts['pornreactor.cc'] = preventBackgroundRedirect;
  537.  
  538. scripts['auto.ru'] = function() {
  539. var words = /Реклама|Яндекс.Директ|yandex_ad_/;
  540. var userAdsListAds = [
  541. '.listing-list > .listing-item',
  542. '.listing-item_type_fixed.listing-item'
  543. ];
  544. var catalogAds = [
  545. 'div[class*="layout_catalog-inline"]',
  546. 'div[class$="layout_horizontal"]'
  547. ];
  548. var otherAds = [
  549. '.advt_auto',
  550. '.sidebar-block',
  551. '.pager-listing + div[class]',
  552. '.card > div[class][style]',
  553. '.sidebar > div[class]',
  554. '.main-page__section + div[class]',
  555. '.listing > tbody'];
  556. gardener(userAdsListAds.join(','), words, {root:'.listing-wrap', observe:true});
  557. gardener(catalogAds.join(','), words, {root:'.catalog__page,.content__wrapper', observe:true});
  558. gardener(otherAds.join(','), words);
  559. };
  560.  
  561. scripts['online.anidub.com'] = function() {
  562. var script = document.createElement('script');
  563. script.type = "text/javascript";
  564. script.innerHTML = "function ogonekstart1() {}";
  565. document.getElementsByTagName('head')[0].appendChild(script);
  566.  
  567. var style = document.createElement('style');
  568. style.type = 'text/css';
  569. style.appendChild(document.createTextNode('.background {background: none!important;}'));
  570. style.appendChild(document.createTextNode('.background > script + div, .background > script ~ div:not([id]):not([class]) + div[id][class] {display:none!important}'));
  571. document.head.appendChild(style);
  572. };
  573.  
  574. scripts['rsload.net'] = function() {
  575. win.addEventListener('load', function() {
  576. var dis = document.querySelector('.cb-disable');
  577. if (dis) {
  578. dis.click();
  579. }
  580. });
  581. document.addEventListener('click',function(e){
  582. var t = e.target;
  583. if (t && t.href && (/:\/\/\d+\.\d+\.\d+\.\d+\//.test(t.href))) {
  584. t.href = t.href.replace('://','://rsload.net:rsload.net@');
  585. }
  586. });
  587. };
  588.  
  589. var domain = document.domain;
  590. while (domain.indexOf('.') !== -1) {
  591. if (scripts.hasOwnProperty(domain)) {
  592. scripts[domain]();
  593. break;
  594. }
  595. domain = domain.slice(domain.indexOf('.') + 1);
  596. }
  597. });
  598. })();