bangumi_index_name_search

bangumi 目录名称搜索匹配,在添加新关联时输入名称可返回相应搜索

  1. // ==UserScript==
  2. // @name bangumi_index_name_search
  3. // @namespace http://tampermonkey.net/
  4. // @version 1.1.1
  5. // @description bangumi 目录名称搜索匹配,在添加新关联时输入名称可返回相应搜索
  6. // @author xdy
  7. // @include /https?:\/\/(bgm\.tv|bangumi\.tv|chii\.in)/index/*
  8. // @require http://code.jquery.com/jquery-latest.js
  9. // ==/UserScript==
  10.  
  11. function addCSS(cssText){
  12.  
  13. var style = document.createElement('style'), //创建一个style元素
  14. head = document.head || document.getElementsByTagName('head')[0]; //获取head元素
  15. style.type = 'text/css'; //这里必须显示设置style元素的type属性为text/css,否则在ie中不起作用
  16.  
  17. if(style.styleSheet){ //IE
  18. var func = function(){
  19. try{ //防止IE中stylesheet数量超过限制而发生错误
  20.  
  21. style.styleSheet.cssText = cssText;
  22.  
  23. }catch(e){
  24.  
  25. }
  26. };
  27. //如果当前styleSheet还不能用,则放到异步中则行
  28. if(style.styleSheet.disabled){
  29.  
  30. setTimeout(func,10);
  31. }else{
  32. func();
  33. }
  34. }else{ //w3c
  35. //w3c浏览器中只要创建文本节点插入到style元素中就行了
  36. var textNode = document.createTextNode(cssText);
  37.  
  38. style.appendChild(textNode);
  39.  
  40. }
  41.  
  42. head.appendChild(style); //把创建的style元素插入到head中
  43. }
  44.  
  45. //使用
  46. css = '\
  47. .search_suggest \
  48. {\
  49. position:absolute;\
  50. z-index:999;\
  51. left:10px;\
  52. top:106px;\
  53. width:361px;\
  54. border:1px solid #ccc;\
  55. border-top:none;\
  56. display:none;\
  57. color:#004080;\
  58. }\
  59. .search_suggest li \
  60. { height:24px;\
  61. overflow:hidden;\
  62. padding-left:3px;\
  63. line-height:24px;\
  64. background:#fff;\
  65. cursor:default;\
  66. }\n\
  67. .search_suggest li.hover {background:#ddd;}';
  68.  
  69.  
  70. addCSS(css);
  71. var type_str = ['', '书籍','动画','音乐','游戏','书籍','三次元'];
  72. $("a.add.thickbox").attr('href','#TB_inline?tb&height=80&width=360&inlineId=newIndexRelated');
  73.  
  74. var input = $("input#title");
  75. input.attr('autocomplete','off');
  76. input.after("<div class='search_suggest' id='search_suggest'><ul></ul></div>");
  77. before_str = "<option value='2'>动画</option><option value='1'>书籍</option><option value='4'>游戏</option><option value='3'>音乐</option><option value='6'>三次元</option>";
  78. input.before("<div><span class='tip'>或填入条目名称获得候选ID选项,右侧选择分类:</span><select name='cat' id='indexSearchSelect'><option value='all'>全部</option>"+before_str+"</div>");
  79.  
  80. var indexSelect = $('select#indexSearchSelect');
  81.  
  82. function oSearchSuggest(searchFuc)
  83. {
  84. //var input = $('#gover_search_key');
  85. var suggestWrap = $('#search_suggest');
  86. var key = "";
  87. var init = function(){
  88. input.bind('keyup',sendKeyWord);
  89. input.bind('blur',function(){setTimeout(hideSuggest,100);});
  90. };
  91. var hideSuggest = function(){
  92. suggestWrap.hide();
  93. };
  94. //发送请求,根据关键字到后台查询
  95. var sendKeyWord = function(event){
  96. //键盘选择下拉项
  97. if(suggestWrap.css('display')=='block'&&event.keyCode == 38||event.keyCode == 40)
  98. {
  99. var current = suggestWrap.find('li.hover');
  100. if(event.keyCode == 38)
  101. {
  102. if(current.length>0)
  103. {
  104. var prevLi = current.removeClass('hover').prev();
  105. if(prevLi.length>0)
  106. {
  107. prevLi.addClass('hover');
  108. input.val(prevLi.attr('title'));
  109. }
  110. }
  111. else
  112. {
  113. var last = suggestWrap.find('li:last');
  114. last.addClass('hover');
  115. input.val(last.attr('title'));
  116. }
  117. }
  118. else if(event.keyCode == 40)
  119. {
  120. if(current.length>0)
  121. {
  122. var nextLi = current.removeClass('hover').next();
  123. if(nextLi.length>0)
  124. {
  125. nextLi.addClass('hover');
  126. input.val(nextLi.attr('title'));
  127. }
  128. }
  129. else
  130. {
  131. var first = suggestWrap.find('li:first');
  132. first.addClass('hover');
  133. input.val(first.attr('title'));
  134. }
  135. }
  136. //输入字符
  137. }
  138. else
  139. {
  140. var valText = $.trim(input.val());
  141. if(valText ==''||valText==key)
  142. {
  143. return;
  144. }
  145. var search_type = indexSelect.val();
  146. searchFuc(valText, search_type);
  147. key = valText;
  148. }
  149. };
  150. //请求返回后,执行数据展示
  151. this.dataDisplay = function(data){
  152. if(data.length<=0)
  153. {
  154. suggestWrap.hide();
  155. return;
  156. }
  157.  
  158. //往搜索框下拉建议显示栏中添加条目并显示
  159. var li;
  160. var tmpFrag = document.createDocumentFragment();
  161. suggestWrap.find('ul').html('');
  162. for(var i=0; i<data.length; i++)
  163. {
  164. li = document.createElement('LI');
  165. li.title = data[i].id;
  166. li.innerHTML = type_str[data[i].type] + ':' + data[i].name;
  167. tmpFrag.appendChild(li);
  168. }
  169. suggestWrap.find('ul').append(tmpFrag);
  170. suggestWrap.show();
  171. //为下拉选项绑定鼠标事件
  172. suggestWrap.find('li').hover(function(){
  173. suggestWrap.find('li').removeClass('hover');
  174. $(this).addClass('hover');
  175. },function(){
  176. $(this).removeClass('hover');
  177. }).bind('click',function(){
  178. $(this).find("span").remove();
  179. input.val(this.title);
  180. suggestWrap.hide();
  181. });
  182. };
  183. init();
  184. }
  185. //实例化输入提示的JS,参数为进行查询操作时要调用的函数名
  186. var searchSuggest = new oSearchSuggest(sendKeyWordToBack);
  187. //这是一个模似函数,实现向后台发送ajax查询请求,并返回一个查询结果数据,传递给前台的JS,再由前台JS来展示数据。本函数由程序员进行修改实现查询的请求
  188. //参数为一个字符串,是搜索输入框中当前的内容
  189.  
  190. function sendKeyWordToBack(keyword, type='all'){
  191. var aData = [];
  192. $.get(`${location.origin}/subject_search/${keyword}?cat=${type}`, function (data) {
  193. let content = data.match(/<a href="\/subject\/.*?" class="l">.*?<\/a>/g);
  194. let type_content = data.match(/<span class="ico_subject_type subject_type_\d ll"><\/span>/g);
  195. if(content) {
  196.  
  197. for(var i = 0;i<content.length;i++)
  198. {
  199. let anime = {};
  200. s = content[i].match(/>.*?</)[0];
  201. anime['name'] = s.substring(1, s.length-1);
  202. anime['id'] = content[i].match(/\d+/)[0];
  203. anime['type'] = parseInt(type_content[i].match(/\d/)[0]);
  204. aData.push(anime);
  205. }
  206. //content.forEach(function (item){
  207. // s = item.match(/>.*?</)[0];
  208. // item_name.push(s.substring(1, s.length-1));
  209.  
  210. // anime['id'] = item;
  211. //});
  212. }
  213.  
  214. searchSuggest.dataDisplay(aData);
  215.  
  216.  
  217. });
  218. //将返回的数据传递给实现搜索输入框的输入提示js类
  219.  
  220. }