TGFC ban troll

让讨厌的苍蝇走开!屏蔽指定用户的主帖和回帖,感谢原作者 taxidriver、jun4rui

当前为 2016-10-16 提交的版本,查看 最新版本

  1. // ==UserScript==
  2. // @name TGFC ban troll
  3. // @namespace http://club.tgfcer.com/20060602
  4. // @version 0.54.1
  5. // @description 让讨厌的苍蝇走开!屏蔽指定用户的主帖和回帖,感谢原作者 taxidriver、jun4rui
  6. // @author 20060602
  7. // @supportURL housekeeper1997@gmail.com
  8. // @include http://*.tgfcer.com/*
  9. // @grant none
  10. // ==/UserScript==
  11.  
  12. // console.log('Hello Tgfcer from "tgfc-ban-troll.js".');
  13.  
  14. // global datas for storage
  15. var BanList, BanListArray, ShowBanTip, checked, BanTip, BanNegJisao, JisaoMin;
  16.  
  17. // URL prefixes
  18. var wapURLPrefix1 = 'http://club.tgfcer.com/wap/';
  19. var wapURLPrefix2 = 'http://wap.tgfcer.com/';
  20.  
  21. var webURLPrefix = 'http://club.tgfcer.com/';
  22.  
  23. // console.log('The Begin of logic.');
  24.  
  25. Array.prototype.contains = contains;
  26. loadData();
  27. //console.log('Data loaded.');
  28. if (underURL(wapURLPrefix1, wapURLPrefix2)){
  29. processWap();
  30. }else if (underURL(webURLPrefix)){
  31. // console.log('gonna execute processWeb.');
  32. processWeb();
  33. }
  34.  
  35. //console.log('The End of logic.');
  36.  
  37.  
  38. function initLocalStorage(name, defaultValue){
  39. if (typeof(localStorage[name])==='undefined'){
  40. localStorage[name] = defaultValue;
  41. // console.log(name + ' initialed with:' + defaultValue);
  42. }
  43. }
  44.  
  45. function loadData(){
  46. //先判断有没有localStorage保存的设置数据,没有则新建
  47. initLocalStorage('BanList', '');
  48. initLocalStorage('ShowBanTip', true);
  49. initLocalStorage('BanTip', 'Blocked!!!!!');
  50. initLocalStorage('BanNegJisao', false);
  51. initLocalStorage('JisaoMin', 0);
  52.  
  53. BanList = localStorage.BanList;
  54. BanListArray = BanList.split(',');
  55. ShowBanTip = localStorage.ShowBanTip === 'true';
  56. checked = ShowBanTip ? "checked" : "";
  57. BanTip = localStorage.BanTip;
  58. BanNegJisao = localStorage.BanNegJisao === 'true';
  59. JisaoMin = parseInt(localStorage.JisaoMin);
  60. //console.log(localStorage);
  61. }
  62.  
  63. function saveData(banList,showTip, banTip, banNegJisao, jisaoMin){
  64. BanList = banList;
  65. ShowBanTip = showTip;
  66. BanListArray = BanList.split(',');
  67. localStorage.BanList = BanList;
  68. localStorage.ShowBanTip = ShowBanTip;
  69. localStorage.BanTip = banTip;
  70. if( banNegJisao !== undefined){
  71. localStorage.BanNegJisao = banNegJisao;
  72. }
  73. if( jisaoMin !== undefined){
  74. localStorage.JisaoMin = jisaoMin;
  75. }
  76. BanTip = localStorage.BanTip;
  77. }
  78.  
  79. function processWap(){
  80. //不让图片尺寸超过屏幕的最大宽度,有时候图片太大了看起来好累
  81. addGlobalStyle('div.message>img {max-width:100%;}');
  82. //让顶部导航栏浮动固定
  83. addGlobalStyle('#scroller>.navbar {position:fixed;height:28px;line-height:28px;width:100%;top:0;left:0;box-shadow: 5px 1px 5px #888888;} body {padding-top:36px;}');
  84. addWapLink();
  85.  
  86. //在原生导航栏中加入设置模块
  87. //console.log($('#wrapper'));
  88. $('div.navbar').append('&nbsp;|&nbsp;<a href="#" class="nav_link" id="tgbs-btn" title="让TGFCER更美好的设置,由 taxidriver、jun4rui 两位坛友原创">TGGM</a>');
  89. //点击模块的处理
  90. $('#scroller').delegate('#tgbs-btn', 'click', function(){
  91. if ($('#tgbs').css('display')=='none'){
  92. loadData();
  93. $('#tgbs').css({'display':''});
  94. $('#tgbs').css('top',$('#tgbs-btn').position().top+20);
  95. $('#tgbs').css('left',2);
  96. $('#tgbs textarea').focus();
  97. $('#ban-tip').val(BanTip);
  98. //添加"加入到ban"按钮
  99. $('#scroller .infobar').each(function(){
  100. $(this).find('a').eq(1).after('<button class="add-to-ban" value="'+$(this).find('a').eq(1).text()+'">+屏蔽</button>');
  101. });
  102. }else{
  103. //关闭设置菜单时,清除所有"加入到ban"按钮并关闭设置面板
  104. $('.add-to-ban').remove();
  105. $('#tgbs').css({'display':'none'});
  106. // 保存数据到localStorage
  107. localStorage.BanList = $('#banlist-textarea').val();
  108. localStorage.ShowBanTip = document.getElementById("showBanTip").checked;
  109. localStorage.BanTip = $('#ban-tip').val();
  110. BanList = localStorage.BanList;
  111. BanListArray = BanList.split(',');
  112. ShowBanTip = localStorage.ShowBanTip === 'true';
  113. checked = ShowBanTip ? "checked" : "";
  114. BanTip = $('#ban-tip').val();
  115. }
  116. });
  117. //处理点击'.add-to-ban'按钮
  118. $('.infobar').delegate('.add-to-ban', 'click', function(){
  119. $('#banlist-textarea').val($('#banlist-textarea').val()+','+$(this).attr('value'));
  120. });
  121. //在原生导航栏下面加入设置表单
  122. $('div.navbar').append('<div id="tgbs" style="color:#FFF; width:400px;padding:.5em;position:fixed; display:none; overflow:hidden;box-shadow: rgb(51, 51, 51) 1px 1px 19px;background-color: #436193;">屏蔽ID列表:'
  123. + '<br/><textarea id=\"banlist-textarea\" style="width:100%;height:160px;">'+BanList+'</textarea>'
  124. +'<form><input id="showBanTip" type="checkbox" name="showBanTip" '+checked+' />显示屏蔽提示&nbsp;|&nbsp;'
  125. +'提示信息&nbsp;<input id="ban-tip" style="font-size : 1em; padding : 0px; margin : 0px; margin-top: 5px; width : 200px;"/></form></div>');
  126.  
  127. //点击屏蔽区将展开屏蔽内容
  128. $('#scroller').delegate('.list-ban-section', 'click', function(){
  129. if ($(this).css('height')=='21px'){
  130. $(this).css({'height':'auto'});
  131. }else{
  132. $(this).css({'height':'21px'});
  133. }
  134. });
  135.  
  136. //列表页面
  137. var ForumPagePart = 'index.php?action=forum';
  138. //帖子内文页面
  139. var ThreadPagePart = 'index.php?action=thread';
  140.  
  141. //如果当前页面是列表页面的处理
  142. if (hasURLPart(ForumPagePart)){
  143. //console.log('当前在列表页面');
  144. $('.dTitle').each(function(){
  145. var author = $(this).find('span.author').text();
  146. for (var i in BanListArray){
  147. //判断发帖人是否在屏蔽列表中
  148. if (author.indexOf(BanListArray[i])==1){
  149. //console.log(BanListArray[i]);
  150. if(!ShowBanTip){
  151. $(this).css({display:'none'});
  152. continue;
  153. }
  154. //console.log(author.indexOf(BanListArray[i]),BanListArray[i]);
  155. $(this).addClass('list-ban-section');
  156. $(this).prepend('<div style="width:auto;text-align:center;border:1px dashed #DEDEDE;color:#DEDEDE; line-height:19px;"><strong><s>'+BanListArray[i]+'</s></strong>'+BanTip+'</div>');
  157. $(this).css({'height':'21px','overflow':'hidden'});
  158. }
  159. }
  160. });
  161. }
  162.  
  163.  
  164. $('#scroller').delegate('.info-ban-section', 'click', function(){
  165. if ($(this).next().css('display')=='none'){
  166. $(this).next().css({'display':'inherit'});
  167. $(this).next().next().css({'display':'inherit'});
  168. $(this).next().next().next().css({'display':'inherit'});
  169. $(this).next().next().next().next().css({'display':'inherit'});
  170. $(this).next().next().next().next().next().css({'display':'inherit'});
  171. }else{
  172. $(this).next().css({'display':'none'});
  173. $(this).next().next().css({'display':'none'});
  174. $(this).next().next().next().css({'display':'none'});
  175. $(this).next().next().next().next().css({'display':'none'});
  176. $(this).next().next().next().next().next().css({'display':'none'});
  177. }
  178. });
  179.  
  180. //如果当前页面是内容页的处理
  181. if (hasURLPart(ThreadPagePart)){
  182. markJiSao();
  183. $('.infobar').each(function(){
  184. var author = $(this).find('a').eq(1).text();
  185. for (var i in BanListArray){
  186. //判断发帖人是否在屏蔽列表中
  187. if (author==BanListArray[i]){
  188. console.log(author.indexOf(BanListArray[i]),BanListArray[i]);
  189. $(this).css({'display':'none'});
  190. if(ShowBanTip){
  191. $(this).before('<div class="info-ban-section" style="cursor:pointer;width:auto;text-align:center;border:1px dashed #DEDEDE;color:#DEDEDE; line-height:19px;"><strong><s>'+BanListArray[i]+'</s></strong>'+BanTip+'</div>');
  192. }
  193. //$(this).addClass('ban-section');
  194. //依次连续隐藏5个(含自己)元素
  195. $(this).next().css({'display':'none'});
  196. $(this).next().next().css({'display':'none'});
  197. $(this).next().next().next().css({'display':'none'});
  198. $(this).next().next().next().next().css({'display':'none'});
  199. }
  200. }
  201. });
  202. }
  203. }
  204.  
  205. function processWeb(){
  206. console.log('processWeb begin');
  207. // 调整 “最后发表” 列的宽度,避免部分较长的 ID 导致此栏换行
  208. addGlobalStyle('.threadlist td.lastpost {width:160px;}');
  209. closeLeftAdv();
  210. console.log('processWeb end');
  211. jisaoEditable();
  212. //在原生导航栏中加入设置模块
  213. var newSpan = document.createElement('span');
  214. newSpan.innerHTML = '<a href="#" class="nav_link" id="tgbs-btn" title="让TGFCER更美好的设置,由 taxidriver、jun4rui 两位坛友原创">TGGM</a>&nbsp;|&nbsp;';
  215. // console.log(newSpan);
  216. var hookPoint = document.getElementById('my').parentNode.parentNode;
  217. // console.log(hookPoint);
  218. hookPoint.appendChild(newSpan);
  219. // console.log(navP);
  220. var btn = document.getElementById('tgbs-btn');
  221. // console.log(btn);
  222.  
  223.  
  224. var floatDiv = createFloatDiv();
  225. newSpan.appendChild(floatDiv);
  226.  
  227. var banlistTextarea = document.getElementById('ban-list');
  228. var showCheckbox = document.getElementById('show-ban-info');
  229. var banTip = document.getElementById('ban-tip');
  230. var banNegJisaoCheckbox = document.getElementById('ban-neg-jisao');
  231. var jisaoMin = document.getElementById('jisao-min');
  232.  
  233. //console.log(floatDiv);
  234.  
  235. btn.onclick = function (){
  236. // console.log('showCheckbox.checked:' + showCheckbox.checked + ' ShowBanTip:' + ShowBanTip);
  237. if(floatDiv.style.display==='none'){
  238. loadData();
  239. floatDiv.style.display='';
  240. floatDiv.style.top = getElementTop(newSpan) + 20 + 'px';
  241. floatDiv.style.left = getElementLeft(newSpan) - 365 +'px';
  242. showCheckbox.checked = ShowBanTip;
  243. banlistTextarea.value = BanList;
  244. banlistTextarea.focus();
  245. }else{
  246. floatDiv.style.display='none';
  247. saveData(banlistTextarea.value, showCheckbox.checked, banTip.value, banNegJisaoCheckbox.checked, jisaoMin.value);
  248. }
  249. };
  250. filterBlackList(
  251. function(){return document.getElementsByTagName('tbody');},
  252. 2,
  253. function (author, reason){
  254. return '<tr><td style="background-color:#e5e5e5" class="folder"></td><td style="background-color:#e5e5e5" class="icon"></td><th class=""><label></label><span><s>' +
  255. author +
  256. '</s> '+ BanTip +
  257. reason +
  258. '</span></th><td style="background-color:#e5e5e5;text-align:center" class="author"></td><td class="nums"></td><td style="background-color:#e5e5e5" class="lastpost"></td></tr>';
  259. },
  260. '<tr><td style="background-color:#e5e5e5" class="folder"></td><td style="background-color:#e5e5e5" class="icon"></td><th class=""><label></label><span><s>',
  261. '</s> '+BanTip+'</span></th><td style="background-color:#e5e5e5;text-align:center" class="author"></td><td class="nums"></td><td style="background-color:#e5e5e5" class="lastpost"></td></tr>'
  262. );
  263.  
  264. filterBlackList(
  265. function(){return document.getElementsByClassName('viewthread');},
  266. 1,
  267. function (author, reason){
  268. return '<div class="mainbox viewthread"><table cellspacing="0" cellpadding="0"><tbody><tr><td class="postauthor"></td><td class="postcontent"><s>' +
  269. author +
  270. '</s> '+ BanTip +
  271. reason +
  272. '</td></tr></tbody></table></div>';
  273. },
  274. '<div class="mainbox viewthread"><table cellspacing="0" cellpadding="0"><tbody><tr><td class="postauthor"></td><td class="postcontent"><s>',
  275. '</s> '+BanTip+'</td></tr></tbody></table></div>'
  276. );
  277. }
  278.  
  279. //添加全局CSS样式的方法
  280. function addGlobalStyle(css) {
  281. var head, style;
  282. head = document.getElementsByTagName('head')[0];
  283. if (!head) { return; }
  284. style = document.createElement('style');
  285. style.type = 'text/css';
  286. style.innerHTML = css;
  287. head.appendChild(style);
  288. }
  289.  
  290. function markJiSao(){
  291. //正激骚
  292. addGlobalStyle('a.positive-sao {color:#f00;}');
  293. //负激骚
  294. addGlobalStyle('a.negative-sao {color:#00bb00;}');
  295.  
  296. var regex = /^骚\((-?\d+)\)$/g;
  297. $('a').each(function(){
  298. var atag = $(this);
  299. var match = regex.exec(atag.text());
  300. if(match && match[1] != '0'){
  301. //console.log(match[1]);
  302. if(match[1].indexOf('-')===0){
  303. atag.addClass("negative-sao");
  304. }else{
  305. atag.addClass("positive-sao");
  306. }
  307. }
  308. });
  309. }
  310.  
  311.  
  312. function addWapLink(){
  313. var webLink = /^http:\/\/club\.tgfcer\.com\/thread-([\d]+)-.+html/ig;
  314. var tidStr = 'http://wap.tgfcer.com/index.php?action=thread&tid=TidDummy&sid=&vt=1&tp=100&pp=100&sc=0&vf=0&sm=0&iam=&css=&verify=&fontsize=0';
  315.  
  316. var tags = document.getElementsByTagName('a');
  317. for(var i=0; i<tags.length; ++i){
  318. var tag = tags[i];
  319. var href = tag.href;
  320. var execResult = webLink.exec(href);
  321. if(execResult){
  322. var threadId = execResult[1];
  323. var wapLink = tidStr.replace('TidDummy',threadId);
  324. //console.log(wapLink);
  325. var newSpan = document.createElement('span');
  326. newSpan.innerHTML = '&nbsp;&nbsp;<a href="'+wapLink+'" title="">(wap点我)</a>&nbsp;';
  327. tag.parentNode.insertBefore(newSpan ,tag.nextSibling);
  328. }
  329. }
  330. }
  331.  
  332. function getElementTop(element){
  333. var actualTop = element.offsetTop;
  334. var current = element.offsetParent;
  335. while (current !== null){
  336. actualTop += current.offsetTop;
  337. current = current.offsetParent;
  338. }
  339. return actualTop;
  340. }
  341.  
  342. function getElementLeft(element){
  343. var actualLeft = element.offsetLeft;
  344. var current = element.offsetParent;
  345. while (current !== null){
  346. actualLeft += current.offsetLeft;
  347. current = current.offsetParent;
  348. }
  349. return actualLeft;
  350. }
  351.  
  352. function createFloatDiv(){
  353. var floatDiv = document.createElement('div');
  354. floatDiv.setAttribute('id', 'tgbs');
  355. floatDiv.setAttribute('style', 'color:#FFF; width:400px;padding:.5em;position:fixed; display:none; overflow:hidden;box-shadow: rgb(51, 51, 51) 1px 1px 19px;background-color: #00b23d;text-align:left;');
  356. var titleText = document.createElement('div');
  357. titleText.innerHTML = '屏蔽ID列表:';
  358. floatDiv.appendChild(titleText);
  359. banlistTextarea = document.createElement('textarea');
  360. banlistTextarea.setAttribute('id', 'ban-list');
  361. banlistTextarea.style.width = '99%';
  362. banlistTextarea.style.height = '160px';
  363. banlistTextarea.style.marginBottom = '4px';
  364. floatDiv.appendChild(banlistTextarea);
  365.  
  366.  
  367. var form = document.createElement('form');
  368. floatDiv.appendChild(form);
  369. showCheckbox = document.createElement('input');
  370. form.appendChild(showCheckbox);
  371. showCheckbox.setAttribute('type','checkbox');
  372. showCheckbox.setAttribute('id', 'show-ban-info');
  373. showCheckbox.checked = ShowBanTip;
  374.  
  375. var checkText = document.createElement('span');
  376. checkText.innerHTML = '显示屏蔽提示&nbsp;&nbsp;|&nbsp;&nbsp;提示信息&nbsp;';
  377. form.appendChild(checkText);
  378. banTip = document.createElement('input');
  379. form.appendChild(banTip);
  380. banTip.setAttribute('type','text');
  381. banTip.setAttribute('id', 'ban-tip');
  382. banTip.style.fontSize = '1em';
  383. banTip.style.padding = '0px';
  384. banTip.style.margin = '0px';
  385. banTip.style.width = '200px';
  386. // banTip.style.color = '#cc0000';
  387. banTip.value = BanTip;
  388. var lineBreak = document.createElement('hr');
  389. form.appendChild(lineBreak);
  390. showCheckbox = document.createElement('input');
  391. form.appendChild(showCheckbox);
  392. showCheckbox.setAttribute('type','checkbox');
  393. showCheckbox.setAttribute('id', 'ban-neg-jisao');
  394. showCheckbox.checked = BanNegJisao;
  395. var checkText = document.createElement('span');
  396. checkText.innerHTML = '屏蔽,如果该用户激骚小于&nbsp;';
  397. form.appendChild(checkText);
  398. banTip = document.createElement('input');
  399. form.appendChild(banTip);
  400. banTip.setAttribute('type','number');
  401. banTip.setAttribute('id', 'jisao-min');
  402. banTip.style.fontSize = '1em';
  403. banTip.style.padding = '0px';
  404. banTip.style.margin = '0px';
  405. banTip.style.width = '112px';
  406. // banTip.style.color = '#cc0000';
  407. banTip.value = JisaoMin;
  408. lineBreak = document.createElement('hr');
  409. form.appendChild(lineBreak);
  410. var btnJisaoEdit = document.createElement('BUTTON');
  411. var t = document.createTextNode('让“激骚理由”可编辑'); // Create a text node
  412. btnJisaoEdit.appendChild(t); // Append the text to <button>
  413. form.appendChild(btnJisaoEdit);
  414. btnJisaoEdit.onclick = jisaoEditable;
  415. return floatDiv;
  416. }
  417.  
  418. function jisaoNoPM(event){
  419. var taReason = document.getElementsByName('sendreasonpm');
  420. //console.log(taReason);
  421. if(taReason){
  422. for (var i = 0, len = taReason.length; i < len; i++) {
  423. var ta = taReason[i];
  424. ta.removeAttribute('disabled');
  425. }
  426. }
  427. //event.preventDefault();
  428. return false;
  429. }
  430.  
  431. function jisaoEditable(event){
  432. var taReason = document.getElementsByName('reason');
  433. //console.log(taReason);
  434. if(taReason){
  435. for (var i = 0, len = taReason.length; i < len; i++) {
  436. var ta = taReason[i];
  437. ta.removeAttribute('readonly');
  438. }
  439. }
  440. jisaoNoPM();
  441. return false;
  442. }
  443.  
  444. function filterBlackList(nodeFunc, citeCount, tipFunc, preT, postT){
  445. var allTextareas,cite, author;
  446. allTextareas = nodeFunc();
  447. // console.log(allTextareas.length);
  448. if (!allTextareas.length) {
  449. return;
  450. }
  451.  
  452. for (var index = 0; index < allTextareas.length; index++) {
  453. var node = allTextareas[index];
  454. cite = node.getElementsByTagName('cite');
  455. if (cite.length < citeCount)
  456. continue;
  457.  
  458. // author = cite[0].getElementsByTagName('a')[0].innerHTML;
  459. //console.log(author);
  460. var reason = banReason(node, cite);
  461. if (reason !== null) {
  462. // console.log("kill " + author);
  463. // console.log("ShowBanTip("+typeof(ShowBanTip)+") " + ShowBanTip);
  464. if(ShowBanTip){
  465. node.innerHTML = tipFunc(author, reason);
  466. }
  467. else{
  468. node.style.display = 'none';
  469. }
  470. }
  471. function banReason(node, cite){
  472. if(cite[0].getElementsByTagName('a')[0] == null){
  473. return null;
  474. }
  475. author = cite[0].getElementsByTagName('a')[0].innerHTML;
  476. if (BanListArray.contains(author)){
  477. return '';
  478. }
  479. if(BanNegJisao){
  480. var dl = node.getElementsByTagName('dl');
  481. if(dl){
  482. dl = dl[0];
  483. var dds = dl.getElementsByTagName('dd');
  484. var jisaoText = dds[3].innerText;
  485. var jisao = parseInt(jisaoText);
  486. // console.log(jisao);
  487. if(jisao < JisaoMin){
  488. return ' 激骚值:' + jisao;
  489. }
  490. }
  491. }
  492. return null;
  493. }
  494. }
  495. }
  496.  
  497. function underURL(){
  498. //console.log('underURL begin')
  499. var PageCurrent = window.location.href;
  500.  
  501. var result = false;
  502. for (var i = 0; i < arguments.length; i++) {
  503. var prefix = arguments[i];
  504. if(PageCurrent.indexOf(prefix)===0){
  505. result = true;
  506. break;
  507. //return true;
  508. }
  509. }
  510.  
  511. //console.log('underURL returned with: ' + result);
  512. return result;
  513. }
  514.  
  515. function hasURLPart(part){
  516. var PageCurrent = window.location.href;
  517. return PageCurrent.indexOf(part) >= 0;
  518. }
  519.  
  520. function contains(obj) {
  521. var index = this.length;
  522. while (index--) {
  523. if (this[index] === obj) {
  524. return true;
  525. }
  526. }
  527. return false;
  528. }
  529.  
  530.  
  531. function closeLeftAdv(){
  532. return; //
  533. console.log('closeLeftAdv begin');
  534. writeCookie('leftadv1','1',700);
  535. document.getElementById('leftadv').style.display='none';
  536. document.getElementById('content_main').style.margin='0 0 0 0';
  537. console.log('closeLeftAdv end');
  538. }