Passmark CPU/GPU Filter

Passmark CPU/GPU Filter by Brand, Model or Inputed Text. @ cpubenchmark, videocardbenchmark.

当前为 2022-02-18 提交的版本,查看 最新版本

  1. // ==UserScript==
  2. // @namespace ATGT
  3. // @name Passmark CPU/GPU Filter
  4. // @version 2
  5. // @description Passmark CPU/GPU Filter by Brand, Model or Inputed Text. @ cpubenchmark, videocardbenchmark.
  6. // @author StrongOpx
  7. // @match https://www.cpubenchmark.net/cpu_lookup.php*
  8. // @match https://www.cpubenchmark.net/*_cpus.html*
  9. // @match https://www.cpubenchmark.net/mid_range_cpus.html
  10. // @match https://www.videocardbenchmark.net/video_lookup.php*
  11. // @match https://www.videocardbenchmark.net/*_gpus.html
  12. // @grant none
  13. // @icon https://www.cpubenchmark.net/favicon.ico
  14. // @run-at document-end
  15. // ==/UserScript==
  16.  
  17.  
  18. console.log(`=== cpu benchmark filter on '${location.href}' ===`);
  19.  
  20. const active_bg_color = 'bisque';
  21. const inactive_bg_color = 'slategray';
  22. const active_fg_color = 'black';
  23. const inactive_fg_color = 'lightgray';
  24.  
  25. function gen_filter_keyword(kw_regex, prod_map) {
  26. let regex = new RegExp(kw_regex, 'i');
  27. let products = document.querySelectorAll('ul.chartlist .prdname');
  28. for (let prod of products) {
  29. let m = prod.innerText.match(regex);
  30. if (m && m.length >= 2) {
  31. let kw = m[1];
  32. kw = kw.replace(/(AMD|Intel)\s+/i, '').replace('-', '').replace(/\s+/, '\\s+');
  33. //console.log(`gen filter m ${m} kw ${kw}`);
  34. if (!(kw in prod_map))
  35. prod_map[kw] = {};
  36. }
  37. }
  38. return prod_map;
  39. }
  40.  
  41. function gen_filter_map(filter_map) {
  42. let products = document.querySelectorAll('ul.chartlist .prdname');
  43. for (let k of Object.keys(filter_map)) {
  44. let regex = filter_map['regex'];
  45. if (!regex) {
  46. regex = filter_map[k]['regex'] = new RegExp(k);
  47. }
  48. filter_map[k]['products'] = [];
  49. for (let prod of products) {
  50. //console.log('prod', prod.innerText);
  51. if (regex.test(prod.innerText)) {
  52. //console.log('Add prod', prod.innerText);
  53. filter_map[k]['products'].push(prod.parentNode.parentNode);
  54. }
  55. }
  56. }
  57. }
  58.  
  59. function gen_filter_toolbar(toolbar, filter_map) {
  60. function filter_action(event) {
  61. let tool = event.target;
  62. if (tool.className.indexOf('filter_tool') < 0) {
  63. tool = tool.parentNode;
  64. if (tool.className.indexOf('filter_tool') < 0) {
  65. return;
  66. }
  67. }
  68.  
  69. let active = tool.attributes['active'];
  70. // console.log('event on ', event.target, 'active', active);
  71. active = !active;
  72. tool.attributes['active'] = active;
  73. let display = active ? '' : 'none';
  74. for (let node of tool.attributes['map']) {
  75. // console.log('node of map ', node);
  76. node.style.display = display;
  77. }
  78. tool.style.backgroundColor = active ? active_bg_color : inactive_bg_color;
  79. tool.style.color = active ? active_fg_color : inactive_fg_color;
  80. tool.style.border = active ? '1px solid black' : '1px dotted lightgray';
  81. if (node.className.indexOf('filter_all') >= 0) {
  82. for (let node of document.querySelectorAll('.filter_tool.filter_part')) {
  83. //console.log('alter', node);
  84. node.attributes['active'] = active;
  85. node.style.background = active ? active_bg_color : inactive_bg_color;
  86. node.style.color = active ? active_fg_color : inactive_fg_color;
  87. }
  88. }
  89. }
  90.  
  91. let container = document.createElement('DIV');
  92. container.className = 'filter_container';
  93. container.style.borderTop = '6px dotted white';
  94. container.style.textAlign = 'left';
  95. toolbar.appendChild(container);
  96.  
  97. let node;
  98. for (let k of Object.keys(filter_map).sort()) {
  99. node = document.createElement('DIV');
  100. let name = k.replace(/(\\\w\+?|\.)+/i, ' ');
  101. let prod_cnt = filter_map[k]['products'].length;
  102. if (prod_cnt == 0)
  103. continue;
  104. name += ` <span style='color: slateblue;'>(${prod_cnt})</span>`
  105. node.innerHTML = name;
  106. node.style.border = '1px solid black';
  107. node.style.borderRadius = '4px';
  108. node.style.padding = '2px 4px';
  109. node.style.margin = '4px';
  110. node.style.cursor = 'pointer';
  111. node.style.textAlign = 'left';
  112. node.style.background = active_bg_color;
  113. node.style.color = active_fg_color;
  114. //node.style.float = 'left';
  115. node.addEventListener('click', filter_action, { capture: true });
  116. node.attributes['active'] = true;
  117. node.attributes['map'] = filter_map[k]['products'];
  118. if (name.search(/^\s*\.?\*\s*/) < 0)
  119. node.className = 'filter_tool filter_part';
  120. else
  121. node.className = 'filter_tool filter_all';
  122. container.appendChild(node);
  123. }
  124. return container;
  125. }
  126.  
  127. function gen_input_filter(header, all_cpu_map) {
  128. function update_filter(e) {
  129. let flt = e.target.value;
  130. try {
  131. flt = flt.replace(/\s+/, '.*');
  132. let regex = new RegExp(flt, 'i');
  133. let products = all_cpu_map[Object.keys(all_cpu_map)[0]]['products'];
  134. for (let node of products) {
  135. node.style.display = regex.test(node.innerText) ? '' : 'none';
  136. }
  137. } catch (e) {
  138. console.log('update filter for input error', e);
  139. }
  140. }
  141. let input = document.createElement('INPUT');
  142. input.type = 'text';
  143. input.style.margin = '2px 4px 6px 4px';
  144. input.style.width = '90%';
  145. input.addEventListener('input', update_filter);
  146. header.appendChild(input);
  147. }
  148.  
  149. function create_filter_toolbar() {
  150. let toolbar = document.createElement('DIV');
  151. //toolbar.innerText = 'Filter: ';
  152. toolbar.style.borderRadius = '4px';
  153. toolbar.style.lineHeight = '1em';
  154. toolbar.style.position = 'fixed';
  155. toolbar.style.right = '2px';
  156. toolbar.style.top = '120px';
  157. toolbar.style.backgroundColor = inactive_bg_color;
  158. toolbar.style.color = active_fg_color;
  159. toolbar.style.zIndex = '10000';
  160. toolbar.style.fontSize = 'small';
  161. toolbar.style.padding = '4px';
  162. toolbar.style.maxWidth = '10rem';
  163. toolbar.style.maxHeight = '80%';
  164. //toolbar.style.overflowY = 'scroll';
  165.  
  166. function fold_filters(event) {
  167. console.log('Fold Filters');
  168. let target = event.target;
  169. target.attributes['fold'] = !target.attributes['fold'];
  170. for (let node of document.querySelectorAll('.filter_container')) {
  171. node.style.display = target.attributes['fold'] ? 'none' : 'block';
  172. }
  173. }
  174.  
  175. let header_sub_div = document.createElement('DIV');
  176. toolbar.appendChild(header_sub_div);
  177.  
  178. let label = document.createElement('DIV');
  179. label.innerHTML = 'FILTERS';
  180. label.style.borderRadius = '4px';
  181. label.style.textAlign = 'center';
  182. label.style.padding = '2px';
  183. label.style.margin = '2px 2px 10px';
  184. label.style.cursor = 'pointer';
  185. label.style.fontWeight = 'bold';
  186. label.style.background = 'white';
  187. label.attributes['fold'] = false;
  188. label.onclick = fold_filters;
  189. header_sub_div.appendChild(label);
  190.  
  191. let tool_sub_div = document.createElement('DIV');
  192. tool_sub_div.className = 'filter_container';
  193. tool_sub_div.style.maxWidth = '100%';
  194. tool_sub_div.style.maxHeight = '30rem';
  195. tool_sub_div.style.overflowY = 'scroll';
  196. toolbar.appendChild(tool_sub_div);
  197.  
  198. document.body.appendChild(toolbar);
  199.  
  200. return [header_sub_div, tool_sub_div];
  201. }
  202.  
  203. function filter_cpus() {
  204. if (!/cpu/i.test(location.href)) {
  205. return;
  206. }
  207.  
  208. let [header, tools] = create_filter_toolbar();
  209.  
  210. let all_cpu_map = {
  211. '.*': {}
  212. };
  213.  
  214. let apple_cpu_map = {
  215. };
  216.  
  217. let intel_cpu_map = {
  218. 'Intel': {},
  219. };
  220.  
  221. let amd_cpu_map = {
  222. 'AMD': {},
  223. };
  224.  
  225. gen_filter_map(all_cpu_map);
  226. let container = gen_filter_toolbar(header, all_cpu_map);
  227. gen_input_filter(container, all_cpu_map);
  228.  
  229. gen_filter_keyword('(Apple)\\s+([a-zA-Z0-9]+)', apple_cpu_map);
  230. gen_filter_map(apple_cpu_map);
  231. gen_filter_toolbar(tools, apple_cpu_map);
  232.  
  233. gen_filter_keyword('(Intel\\s+(?:[a-zA-Z]+\\s+)(?:[a-zA-Z][\\d-]|\\d|[a-zA-Z]{2,}))', intel_cpu_map);
  234. gen_filter_map(intel_cpu_map);
  235. gen_filter_toolbar(tools, intel_cpu_map);
  236.  
  237. gen_filter_keyword('(AMD\\s+(?:[a-zA-Z]+\\s+)(?:[a-zA-Z][\\d-]|\\d|[a-zA-Z]{2,}))', amd_cpu_map);
  238. gen_filter_map(amd_cpu_map);
  239. gen_filter_toolbar(tools, amd_cpu_map);
  240.  
  241. /*
  242. for (let k of Object.keys(cpu_map)) {
  243. console.log('k', k, cpu_map[k]);
  244. }
  245. */
  246.  
  247. }
  248.  
  249. function filter_gpus() {
  250. if (!/gpu/i.test(location.href)) {
  251. return;
  252. }
  253.  
  254. let [header, tools] = create_filter_toolbar();
  255.  
  256. let all_gpu_map = {
  257. '.*': {}
  258. };
  259.  
  260. let intel_gpu_map = {
  261. };
  262.  
  263. let apple_gpu_map = {
  264. };
  265.  
  266. let nvidia_gpu_map = {
  267. };
  268.  
  269. let amd_gpu_map = {
  270. };
  271.  
  272. gen_filter_map(all_gpu_map);
  273. let container = gen_filter_toolbar(header, all_gpu_map);
  274. gen_input_filter(container, all_gpu_map);
  275.  
  276. gen_filter_keyword('((?:Intel)\\s+(?:[a-zA-Z]+\\s+)?(?:[a-zA-Z][\\d-]|\\d|[a-zA-Z]{2,}))', intel_gpu_map);
  277. gen_filter_map(intel_gpu_map);
  278. gen_filter_toolbar(tools, intel_gpu_map);
  279.  
  280. gen_filter_keyword('((?:Nvidia|Geforce|TITAN|Quadro|Tesla)\\s+(?:[a-zA-Z]+\\s+)?(?:[a-zA-Z][\\d-]|\\d+(?=\\d\\d\\s)|[a-zA-Z]{2,}))', nvidia_gpu_map);
  281. gen_filter_map(nvidia_gpu_map);
  282. gen_filter_toolbar(tools, nvidia_gpu_map);
  283.  
  284. gen_filter_keyword('(Apple)\\s+([a-zA-Z0-9]+)', apple_gpu_map);
  285. gen_filter_map(apple_gpu_map);
  286. gen_filter_toolbar(tools, apple_gpu_map);
  287.  
  288. gen_filter_keyword('((?:AMD|Radeon|FirePro)\\s+(?:[a-zA-Z]+\\s+)?(?:[a-zA-Z][\\d-]|\\d|[a-zA-Z]{2,}))', amd_gpu_map);
  289. gen_filter_map(amd_gpu_map);
  290. gen_filter_toolbar(tools, amd_gpu_map);
  291.  
  292. /*
  293. for (let k of Object.keys(gpu_map)) {
  294. console.log('k', k, gpu_map[k]);
  295. }
  296. */
  297.  
  298. }
  299.  
  300. function refine_layout(e) {
  301. let container = document.querySelector('#block_content > .container') || document.querySelector('.block_content > .container')
  302. let marginLeft = (container.parentNode.clientWidth - container.clientWidth) / 2 - 20;
  303. container.style.marginLeft = marginLeft + 'px';
  304. }
  305.  
  306. try {
  307. refine_layout();
  308. } catch (e) {
  309. console.log('refine_layout error', e);
  310. }
  311. window.addEventListener('resize', refine_layout);
  312.  
  313. filter_cpus();
  314.  
  315. filter_gpus();
  316.  
  317. console.log(`=== /cpu benchmark filter on '${location.href}' ===`);
  318.  
  319.  
  320. /*
  321. let intel_cpu_map = {
  322. 'Atom': {},
  323. 'Celeron': {},
  324. 'Core\\s+i3': {},
  325. 'Core\\s+i5': {},
  326. //'Core\\s+i7': {},
  327. //'Core\\s+i9': {},
  328. 'Core': {},
  329. 'Pentium': {},
  330.  
  331. //'Xeon\\s+X': {},
  332. 'Xeon\\s+D': {},
  333. 'Xeon\\s+E3': {},
  334. 'Xeon\\s+E5': {},
  335. 'Xeon\\s+W': {},
  336. 'Xeon\\s+Silver': {},
  337. 'Xeon\\s+Gold': {},
  338. //'Xeon\\s+Platinum': {},
  339.  
  340. 'Xeon': {},
  341. };
  342.  
  343. let amd_cpu_map = {
  344. 'Athlon': {},
  345.  
  346. 'FX': {},
  347.  
  348. 'Opteron': {},
  349.  
  350. 'Ryzen\\s+3': {},
  351. 'Ryzen\\s+5': {},
  352. 'Ryzen\\s+7': {},
  353.  
  354. 'EPYC\\s+3': {},
  355. 'EPYC\\s+7': {},
  356. 'Threadripper': {},
  357. };
  358. */