// ==UserScript== // @name 🔍聚合快搜 // @namespace https://ez118.github.io/ // @version 0.2.2 // @description 为Via设计的第三方聚合搜索栏 // @author ZZY_WISU // @match *://*/* // @license GNU GPLv3 // @icon data:image/svg+xml;charset=utf-8;base64,PHN2ZyB2ZXJzaW9uPSIxLjIiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgdmlld0JveD0iMCAwIDEyOCAxMjgiIHdpZHRoPSI0MCIgaGVpZ2h0PSI0MCI+PHBhdGggZD0iTTY0IDEyOEMyOC42IDEyOCAwIDk5LjQgMCA2NFMyOC42IDAgNjQgMHM2NCAyOC42IDY0IDY0LTI4LjYgNjQtNjQgNjR6IiBzdHlsZT0iZmlsbDojZjJmN2ZmIi8+PHBhdGggZD0iTTM0LjMgNzkuNUMyMy4xIDc5LjUgMTQgNzAuNCAxNCA1OS4yIDE0IDQ4LjEgMjMuMSAzOSAzNC4zIDM5YzExLjEgMCAyMC4yIDkuMSAyMC4yIDIwLjMgMCAxMS4xLTkuMSAyMC4yLTIwLjIgMjAuMnoiIHN0eWxlPSJmaWxsOiMwMGE1ZjYiLz48cGF0aCBkPSJNNTkgMTA0Yy0xMy44IDAtMjUtMTEuMi0yNS0yNXMxMS4yLTI1IDI1LTI1IDI1IDExLjIgMjUgMjUtMTEuMiAyNS0yNSAyNXoiIHN0eWxlPSJmaWxsOiNmZjNlMDAiLz48cGF0aCBkPSJNODguMiA4MC41QzcxLjUgODAuNSA1OCA2NyA1OCA1MC4yIDU4IDMzLjUgNzEuNSAyMCA4OC4yIDIwYzE2LjggMCAzMC4zIDEzLjUgMzAuMyAzMC4yIDAgMTYuOC0xMy41IDMwLjMtMzAuMyAzMC4zeiIgc3R5bGU9ImZpbGw6I2ZmYjcwMCIvPjwvc3ZnPg== // @run-at document-start // @grant GM_registerMenuCommand // @grant GM_addStyle // @grant GM_setValue // @grant GM_getValue // @grant GM_addElement // @grant window.onurlchange // @require https://update.greasyfork.icu/scripts/499192/1402326/jquery_360.js // @downloadURL none // ==/UserScript== /* =====[ 用户自定义 ]===== */ const searchEngine = [ { "id":"google", "name":"Google", "link":"https://www.google.com/search?q=%s" }, { "id":"bing", "name":"Bing", "link":"https://www.bing.com/search?q=%s" }, { "id":"cnbing", "name":"必应", "link":"https://cn.bing.com/search?q=%s" }, { "id":"duckduckgo", "name":"DuckDuckGo", "link":"https://duckduckgo.com/?t=h_&q=%s" }, { "id":"github", "name":"Github", "link":"https://github.com/search?q=%s&type=repositories" }, { "id":"fdroid", "name":"F-Droid", "link":"https://search.f-droid.org/?q=%s&lang=zh_Hans" }, { "id":"baidu", "name":"百度", "link":"https://www.baidu.com/s?wd=%s" } ]; /* =====[ 变量存储 ]===== */ const ICONS = { 'settings': '', 'blank': ' ' }; var currentEngine = null; /* 存储当前正在使用的搜索引擎 */ var currentQuery = null; /* 存储当前检索词 */ /* =====[ 计算反色 ]===== */ function invertHex(hex) { hex = hex.replace("#", ""); // 补全短的 hex 颜色代码 if (hex.length === 3) { hex = hex.split('').map(c => c + c).join(''); } // 确保 hex 长度为 6 if (hex.length !== 6) { throw new Error("Invalid HEX color."); } // 计算反色 let inverted = (Number(`0x${hex}`) ^ 0xFFFFFF).toString(16).toUpperCase(); // 补全不足位数的 0 inverted = ("000000" + inverted).slice(-6); return `#${inverted}`; } function invertRgb(rgb) { // 匹配 rgb(r, g, b) 格式 const match = rgb.match(/^rgb\((\d{1,3}), (\d{1,3}), (\d{1,3})\)$/); if (!match) { throw new Error("Invalid RGB color."); } const r = 255 - parseInt(match[1], 10); const g = 255 - parseInt(match[2], 10); const b = 255 - parseInt(match[3], 10); return `rgb(${r}, ${g}, ${b})`; } function invertRgba(rgba) { // 匹配 rgba(r, g, b, a) 格式 const match = rgba.match(/^rgba\((\d{1,3}), (\d{1,3}), (\d{1,3}), (0|0?\.\d+|1(\.0)?)\)$/); if (!match) { throw new Error("Invalid RGBA color."); } const r = 255 - parseInt(match[1], 10); const g = 255 - parseInt(match[2], 10); const b = 255 - parseInt(match[3], 10); return `rgba(${r}, ${g}, ${b}, 1)`; } function invertColor(color) { if (color.startsWith("#")) { return invertHex(color); } else if (color.startsWith("rgb(")) { return invertRgb(color); } else if (color.startsWith("rgba(")) { return invertRgba(color); } else { throw new Error("Invalid color format."); } } /* ================ */ function findByKeyValue(array, key, value) { /* 在JSON中,以键值匹配项 */ for (let i = 0; i < array.length; i++) { if (array[i][key] === value) { return i; } } return -1; } function isSearchEngine() { /* 判断是否是被记录的搜索页 */ const currentUrl = new URL(window.location.href); return searchEngine.some(engine => { const prefix = engine.link.split('%s')[0]; const engineUrl = new URL(prefix); return currentUrl.hostname === engineUrl.hostname && currentUrl.pathname.startsWith(engineUrl.pathname); }); } function initEle() { // 创建搜索栏元素并添加到页面 var $quickSearchBar = $('
', { class: 'userscript-quickSearchBar', id: 'userscript-quickSearchBar' }).appendTo('body'); let html = ''; const currentURL = window.location.href; $.each(searchEngine, (index, item) => { const link = item.link; const splitLink = link.split('%s'); let prefix = null; let suffix = null; if (splitLink.length === 2) { prefix = splitLink[0]; suffix = splitLink[1]; } else if (splitLink.length > 2) { prefix = splitLink[0]; suffix = splitLink.slice(1).join('%s'); } if (currentURL.startsWith(prefix) && currentURL.endsWith(suffix)) { currentEngine = item; currentQuery = currentURL.slice(prefix.length, currentURL.length - suffix.length); html += `
${item.name}
`; } else { html += `
${item.name}
`; } console.log(`Current Query: ${currentQuery}`); }); // 清理 HTML 内容并插入到搜索栏 $quickSearchBar.append(html + `
` + ICONS.settings + `
`); // 添加点击事件监听器 $("#userscript-quickSearchBar>.item").click((e) => { var seid = $(e.target).attr("seid"); var seIndex = findByKeyValue(searchEngine, "id", seid); location.href = searchEngine[seIndex].link.replace("%s", currentQuery); }); $("#userscript-quickSearchBar-optBtn").click(() => { alert("设置对话框尚未完成") }); } (function () { 'use strict'; var websiteThemeColor = $('body').css('background-color') || "#FFF"; var websiteFontColor = invertColor(websiteThemeColor); websiteThemeColor = invertColor(websiteFontColor); GM_addStyle(` .userscript-quickSearchBar{ user-select:none; background-color:` + websiteThemeColor + `; color:` + websiteFontColor + `; padding:6px 10px; font-size:12px; line-height:20px; width:100vw; height:30px; border-top:1px solid #CCCCCC99; position:fixed; bottom:-1px; left:0; right:0; display:flex; flex-direction:row; overflow-x:auto; overflow-y:hidden; box-sizing: initial; z-index:100000; } .userscript-quickSearchBar>.item{ margin:0px 5px; border-radius:20px; border:1px solid ` + websiteFontColor + `; padding:5px 9px; width:fit-content; flex-basis:fit-content; flex-shrink:0; cursor:pointer; background-color:transparent; } .userscript-quickSearchBar>.active{ border:1px solid #6d7fb4; color:#6d7fb4; } .userscript-quickSearchBar>.blank{ flex-basis:25px; flex-shrink:0; width:25px; } #userscript-quickSearchBar-optBtn{ margin:0px 5px; flex-shrink:0; flex-basis:fit-content; width:fit-content; border-radius:20px; border:1px solid #ddd; padding:4px 6px; cursor:pointer; } #userscript-quickSearchBar-optBtn svg{ fill:` + websiteFontColor + `; } `); if(isSearchEngine()){ console.log("【提示】已保存的搜素引擎"); initEle(); setTimeout(()=>{ if($("#userscript-quickSearchBar").length == 0){ /* 如果在页面加载时未完成初始化 */ initEle(); } }, 600); setTimeout(()=>{ if($("#userscript-quickSearchBar").length == 0){ /* 如果在页面加载时未完成初始化 */ initEle(); } }, 1200) } })();