您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
Search AnyWhere in Luogu!
当前为
- // ==UserScript==
- // @name Luogu Search AnyWhere
- // @version 0.2
- // @description Search AnyWhere in Luogu!
- // @author tiger2005
- // @match https://www.luogu.com.cn/*
- // @icon https://cdn.luogu.com.cn/upload/usericon/3.png
- // @grant none
- // @license MIT
- // @require https://code.jquery.com/jquery-3.6.0.min.js
- // @namespace https://greasyfork.org/users/829530
- // ==/UserScript==
- (function() {
- 'use strict';
- var addedContent = false;
- let majorInterval = setInterval(function(){
- if($(".user-nav .search-wrap").length == 0)
- return;
- // clearInterval(majorInterval);
- var sicon = $(".user-nav .search-wrap").next();
- $(".user-nav .search-wrap").remove();
- sicon.css("margin-left", "10px");
- if(! addedContent){
- $("body").append(`
- <style>
- .searchAnywhere{
- position: fixed;
- top: 0px;
- left: 0px;
- height: 100%;
- width: 100%;
- background-color: rgba(0, 0, 0, 0.8);
- z-index: 999;
- transition: 0.2s;
- color: white;
- }
- .searchAnywhereMain{
- height: 600px;
- width: 750px;
- position: absolute;
- top: 50%;
- left: 50%;
- transform: translate(-50%, -50%);
- display: flex;
- flex-direction: column;
- }
- .inputArea{
- display: block;
- width: 100%;
- height: 48px;
- color: #aaa;
- position: relative;
- transition: 0.2s;
- margin-bottom: 10px;
- }
- .inputArea > input{
- border-radius: 5px;
- border: 2px solid #aaa;
- height: 48px;
- width: 100%;
- font-size: 18px;
- color: #aaa;
- padding: 14px 24px;
- outline: 0;
- background: transparent;
- box-sizing: border-box;
- }
- .inputArea.onHover > input, .inputArea.onFocus > input{
- border: 2px solid white;
- }
- .inputArea.onHover, .inputArea.onFocus, .inputArea.withContent{
- color: white !important;
- }
- .inputArea.onHover > input, .inputArea.onFocus > input, .inputArea.withContent > input{
- color: white !important;
- }
- .inputArea.withIconLeft > input{
- padding-left: 42px;
- }
- .inputArea.withIconRight > input{
- padding-right: 42px;
- }
- .inputArea > div.iconLeft{
- height: 48px;
- width: 48px;
- position: absolute;
- display: grid;
- place-items: center;
- top: 0px;
- left: 0px;
- }
- .inputArea > div.iconLeft > svg{
- width: 20px !important;
- height: 20px !important;
- }
- .userPurple{
- color: #cf5bff;
- font-weight: bold;
- }
- .userRed{
- color: #e74c3c;
- font-weight: bold;
- }
- .userOrange{
- color: #e67e22;
- font-weight: bold;
- }
- .userYellow{
- color: #d9a71d;
- font-weight: bold;
- }
- .userGreen{
- color: #5eb95e;
- font-weight: bold;
- }
- .userGray{
- color: #aaa;
- font-weight: bold;
- }
- .userCheater{
- color: #d3961c;
- font-weight: bold;
- }
- .userBlue{
- color: #07a2f1;
- font-weight: bold;
- }
- .userGold{
- color: #f1c40f;
- font-weight: bold;
- }
- .badgePurple{
- background-color: #cf5bff;
- }
- .badgeRed{
- background-color: #e74c3c;
- }
- .badgeOrange{
- background-color: #e67e22;
- }
- .badgeYellow{
- background-color: #d9a71d;
- }
- .badgeGreen{
- background-color: #5eb95e;
- }
- .badgeGray{
- background-color: #999;
- }
- .badgeCheater{
- background-color: #d3961c;
- }
- .badgeBlue{
- background-color: #07a2f1;
- }
- .badgeBlack{
- background-color: #0e1d69;
- }
- .badgeGold{
- background-color: #f1c40f;
- }
- .searchAnywhereContent{
- color: white;
- flex: 1;
- scrollbar-width: none;
- -ms-overflow-style: none;
- overflow-x: hidden;
- overflow-y: auto;
- }
- .searchAnywhereContent::-webkit-scrollbar { width: 0 !important; }
- .searchUserCard{
- background: #444;
- border-radius: 10px;
- display: flex;
- flex-direction: column;
- cursor: pointer;
- color: white;
- padding: 10px;
- line-height: 1;
- margin-bottom: 10px;
- border: 2px solid #888;
- box-sizing: border-box;
- }
- .searchUserCard:hover{
- border: 2px solid white;
- }
- .searchUserCard > div{
- width: 100%;
- }
- .searchUserCardBody{
- display: flex;
- flex-direction: row;
- }
- .searchUserCardImg{
- height: 36px;
- width: 36px;
- border-radius: 50%;
- margin-right: 10px;
- }
- .searchUserCardInfo > span:first-child{
- font-size: 14px;
- margin-bottom: 3px;
- display: inline-block;
- color: #bbb;
- }
- .searchUserCardInfo > span:last-child{
- font-size: 20px;
- }
- .searchUserCardMedia{
- display: flex;
- flex-direction: row;
- }
- .searchUserCardMedia > div{
- margin-top: 5px;
- flex: 1;
- display: inline-block;
- height: 23px;
- verticle-align: center;
- }
- .searchUserCardMedia > div > div{
- padding: 4px;
- position: relative;
- display: inline-block;
- background: #777;
- margin-right: 15px;
- }
- .searchUserCardMedia > div > div:after{
- width: 10px;
- height: 100%;
- content: "";
- border: 5px;
- position: absolute;
- top: 0px;
- left: 100%;
- clip-path: polygon(0 0,100% 50%,0 100%);
- background-color: inherit;
- }
- .userBadgeInfo{
- font-size: 14px;
- padding: 2px 5px;
- border-radius: 5px;
- color: white;
- font-weight: bold;
- margin: 0px 3px;
- display: inline-block;
- }
- .searchProblemCard{
- background: #444;
- border-radius: 10px;
- display: flex;
- flex-direction: column;
- cursor: pointer;
- color: white;
- padding: 10px;
- line-height: 1;
- margin-bottom: 10px;
- border: 2px solid #888;
- box-sizing: border-box;
- }
- .searchProblemCard:hover{
- border: 2px solid white;
- }
- .searchProblemCard > div{
- width: 100%;
- display: flex;
- flex-direction: row;
- }
- .searchProblemCard > div:last-child{
- margin-top: 5px;
- }
- .searchProblemCardTag{
- margin-right: 12px;
- }
- .searchProblemCardTag > div{
- padding: 4px;
- position: relative;
- display: inline-block;
- background: #777;
- margin-right: 15px;
- }
- .searchProblemCardTag > div:after{
- width: 10px;
- height: 100%;
- content: "";
- border: 5px;
- position: absolute;
- top: 0px;
- left: 100%;
- clip-path: polygon(0 0,100% 50%,0 100%);
- background-color: inherit;
- }
- .problemTagInfo{
- font-size: 16px;
- padding: 4px 7px;
- border-radius: 5px;
- color: white;
- display: inline-block;
- }
- .searchProblemCardBody > div:first-child{
- margin-right: 5px;
- }
- </style>
- <div class='searchAnywhere' style="opacity: 0; display: none;">
- <div class='searchAnywhereMain'>
- <div class='inputArea withIconLeft'>
- <input spellcheck="false" placeholder="Search AnyWhere"/>
- <div class="iconLeft"><svg data-v-1ad550c8="" data-v-303bbf52="" aria-hidden="true" focusable="false" data-prefix="fas" data-icon="search" role="img" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512" class="svg-inline--fa fa-search fa-w-24"><path data-v-1ad550c8="" data-v-303bbf52="" fill="currentColor" d="M505 442.7L405.3 343c-4.5-4.5-10.6-7-17-7H372c27.6-35.3 44-79.7 44-128C416 93.1 322.9 0 208 0S0 93.1 0 208s93.1 208 208 208c48.3 0 92.7-16.4 128-44v16.3c0 6.4 2.5 12.5 7 17l99.7 99.7c9.4 9.4 24.6 9.4 33.9 0l28.3-28.3c9.4-9.4 9.4-24.6.1-34zM208 336c-70.7 0-128-57.2-128-128 0-70.7 57.2-128 128-128 70.7 0 128 57.2 128 128 0 70.7-57.2 128-128 128z" class=""></path></svg></div>
- </div>
- <div class='searchAnywhereContent'>
- </div>
- </div>
- </div>
- `);
- addedContent = true;
- $(".inputArea > input").focus(function(){
- $(this).parent().addClass("onFocus");
- });
- $(".inputArea > input").blur(function(){
- $(this).parent().removeClass("onFocus");
- if($(this).val().length != 0)
- $(this).parent().addClass("withContent");
- else
- $(this).parent().removeClass("withContent");
- });
- $(".inputArea").mouseenter(function(){
- $(this).addClass("onHover");
- });
- $(".inputArea").mouseleave(function(){
- $(this).removeClass("onHover");
- });
- }
- const problemColors = [ "Gray", "Red", "Orange", "Yellow", "Green", "Blue", "Purple", "Black" ];
- const problemNames = [ "暂无评定", "入门", "普及-", "普及/提高-", "普及+/提高", "提高+/省选-", "省选/NOI-", "NOI/NOI+/CTSC" ];
- var searchTimeout = null;
- const searchInfo = () => {
- searchTimeout = null;
- var info = $(".inputArea > input").val();
- info = $.trim(info);
- if(info == ""){
- $(".searchAnywhereContent").html("");
- return;
- }
- $(".searchAnywhereContent").html(`<div><div style='text-align: center; margin-bottom: 10px; width: 100%; font-size: 20px;'>加载中……</div></div>`);
- $(".searchAnywhereContent > div").unbind('click').click((event) => {
- event.stopPropagation();
- })
- var userHtml = "";
- var problemHtml = "";
- var finishWorks = 0;
- const finishWork = () => {
- ++ finishWorks;
- if(finishWorks == 2){
- if(userHtml == "" && problemHtml == "")
- $(".searchAnywhereContent").html(`<div><div style='text-align: center; margin-bottom: 10px; width: 100%; font-size: 20px;'>未搜索到相关内容</div></div>`);
- else{
- $(".searchAnywhereContent").html(`<div>` + userHtml + problemHtml + `</div>`);
- $(".searchShowProblems").unbind("click").click(function(event){
- window.open(`https://www.luogu.com.cn/problem/list?keyword=${info}&page=1&type=P%7CB%7CCF%7CSP%7CAT%7CUVA`, "_blank");
- });
- $(".searchUserCard").unbind("click").click(function(event){
- window.open(`https://www.luogu.com.cn/user/${$(this).attr("uid")}`, "_blank");
- })
- $(".searchProblemCard").unbind("click").click(function(event){
- window.open(`https://www.luogu.com.cn/problem/${$(this).attr("pid")}`, "_blank");
- })
- $(".searchAnywhereContent > div").unbind('click').click((event) => {
- event.stopPropagation();
- })
- }
- }
- };
- const getProblemStatus = (x, y) => {
- if(!x && !y)
- return `<svg data-v-1b44b3e6="" data-v-c06fccc2="" aria-hidden="true" focusable="false" data-prefix="fas" data-icon="minus" role="img" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 448 512" class="icon svg-inline--fa fa-minus fa-w-14" data-v-303bbf52="" style="width: 16px; height: 16px; color: #aaa"><path data-v-1b44b3e6="" fill="currentColor" d="M416 208H32c-17.67 0-32 14.33-32 32v32c0 17.67 14.33 32 32 32h384c17.67 0 32-14.33 32-32v-32c0-17.67-14.33-32-32-32z" class=""></path></svg>`;
- if(!y)
- return `<svg data-v-1b44b3e6="" data-v-c06fccc2="" aria-hidden="true" focusable="false" data-prefix="fas" data-icon="times" role="img" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 352 512" class="icon svg-inline--fa fa-times fa-w-11" data-v-303bbf52="" style="transform: scale(1.2); width: 16px; height: 16px; color: rgb(231, 76, 60);"><path data-v-1b44b3e6="" fill="currentColor" d="M242.72 256l100.07-100.07c12.28-12.28 12.28-32.19 0-44.48l-22.24-22.24c-12.28-12.28-32.19-12.28-44.48 0L176 189.28 75.93 89.21c-12.28-12.28-32.19-12.28-44.48 0L9.21 111.45c-12.28 12.28-12.28 32.19 0 44.48L109.28 256 9.21 356.07c-12.28 12.28-12.28 32.19 0 44.48l22.24 22.24c12.28 12.28 32.2 12.28 44.48 0L176 322.72l100.07 100.07c12.28 12.28 32.2 12.28 44.48 0l22.24-22.24c12.28-12.28 12.28-32.19 0-44.48L242.72 256z" class=""></path></svg>`;
- return `<svg data-v-1b44b3e6="" data-v-c06fccc2="" aria-hidden="true" focusable="false" data-prefix="fas" data-icon="check" role="img" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512" class="icon svg-inline--fa fa-check fa-w-16" data-v-303bbf52="" style="width: 16px; height: 16px; color: rgb(82, 196, 26);"><path data-v-1b44b3e6="" fill="currentColor" d="M173.898 439.404l-166.4-166.4c-9.997-9.997-9.997-26.206 0-36.204l36.203-36.204c9.997-9.998 26.207-9.998 36.204 0L192 312.69 432.095 72.596c9.997-9.997 26.207-9.997 36.204 0l36.203 36.204c9.997 9.997 9.997 26.206 0 36.204l-294.4 294.401c-9.998 9.997-26.207 9.997-36.204-.001z" class=""></path></svg>`;
- }
- const getCCFLevel = (x) => {
- if(x == null || x < 3)
- return "";
- var color = "";
- if(x <= 5)
- color = "#5eb95e";
- else if(x <= 7)
- color = "#07a2f1";
- else
- color = "#f1c40f";
- return `<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 16 16" style="margin: 0px 3px;" fill="${color}" style="margin-bottom: -3px;"><path d="M16 8C16 6.84375 15.25 5.84375 14.1875 5.4375C14.6562 4.4375 14.4688 3.1875 13.6562 2.34375C12.8125 1.53125 11.5625 1.34375 10.5625 1.8125C10.1562 0.75 9.15625 0 8 0C6.8125 0 5.8125 0.75 5.40625 1.8125C4.40625 1.34375 3.15625 1.53125 2.34375 2.34375C1.5 3.1875 1.3125 4.4375 1.78125 5.4375C0.71875 5.84375 0 6.84375 0 8C0 9.1875 0.71875 10.1875 1.78125 10.5938C1.3125 11.5938 1.5 12.8438 2.34375 13.6562C3.15625 14.5 4.40625 14.6875 5.40625 14.2188C5.8125 15.2812 6.8125 16 8 16C9.15625 16 10.1562 15.2812 10.5625 14.2188C11.5938 14.6875 12.8125 14.5 13.6562 13.6562C14.4688 12.8438 14.6562 11.5938 14.1875 10.5938C15.25 10.1875 16 9.1875 16 8ZM11.4688 6.625L7.375 10.6875C7.21875 10.8438 7 10.8125 6.875 10.6875L4.5 8.3125C4.375 8.1875 4.375 7.96875 4.5 7.8125L5.3125 7C5.46875 6.875 5.6875 6.875 5.8125 7.03125L7.125 8.34375L10.1562 5.34375C10.3125 5.1875 10.5312 5.1875 10.6562 5.34375L11.4688 6.15625C11.5938 6.28125 11.5938 6.5 11.4688 6.625Z"></path></svg>`
- }
- $.ajax({
- url: `/api/user/search?keyword=${info}`,
- type: 'GET',
- success: function(json){
- json = json.users;
- if(json.length != 0 && json[0] != null){
- userHtml = `
- <div style='text-align: left; margin-bottom: 10px; width: 100%; font-size: 18px; font-weight: bold'>用户</div>
- `;
- json.forEach((item) => {
- if(item == null)
- return;
- if(item.color == "Cheater")
- item.badge = "作弊者";
- userHtml += `
- <div class="searchUserCard" uid=${item.uid}>
- <div class="searchUserCardBody">
- <div class="searchUserCardImg" style="background: url(https://cdn.luogu.com.cn/upload/usericon/${item.uid}.png); background-size: 36px 36px;"></div>
- <div class="searchUserCardInfo"><span>UID ${item.uid}</span><br/><div style='display: flex; flex-direction: row'><span class="user${item.color}" style="line-height: 20px">${item.name}</span>${getCCFLevel(item.ccfLevel)}${item.badge != null && item.badge != "" ? `<div class='userBadgeInfo badge${item.color}'>${item.badge}</div>` : ""}</div></div>
- </div>
- </div>`
- });
- }
- finishWork();
- }
- });
- $.ajax({
- url: `/problem/list`,
- type: 'GET',
- headers: {"x-luogu-type": "content-only"},
- data: {
- keyword: info,
- page: 1,
- type: "P|B|CF|SP|AT|UVA"
- },
- success: function(json){
- json = json.currentData.problems;
- if(json.count != 0){
- problemHtml = `
- <div style='text-align: left; margin-bottom: 10px; width: 100%; font-size: 18px; font-weight: bold'>题目<div style="cursor: pointer; float: right; font-weight: normal !important" class="searchShowProblems">查看所有 ${json.count} 道题目</div></div>
- `;
- for(var i=0; i<json.result.length; i++){
- let item = json.result[i];
- problemHtml += `
- <div class="searchProblemCard" pid=${item.pid}>
- <div class="searchProblemCardBody">
- <div>${getProblemStatus(item.submitted, item.accepted)}</div>
- <div>${item.title}</div>
- </div>
- <div>
- <div class='searchProblemCardTag'><div>题号</div>${item.pid}</div>
- <div class='searchProblemCardTag'><div>尝试</div>${item.totalSubmit}</div>
- <div class='searchProblemCardTag'><div>通过</div>${item.totalAccepted}</div>
- <div style='flex: 1; text-align: right'>
- <div class="problemTagInfo badge${problemColors[item.difficulty]}">${problemNames[item.difficulty]}</div>
- </div>
- </div>
- </div>
- `;
- };
- }
- finishWork();
- }
- });
- };
- $(".inputArea > input").unbind('input propertychange').on('input propertychange', function(){
- if(searchTimeout != null)
- clearTimeout(searchTimeout);
- searchTimeout = setTimeout(searchInfo, 500);
- });
- let searchAnywhereOpen = false;
- sicon.unbind('click').click(function(){
- if(! searchAnywhereOpen){
- $(".searchAnywhere").css("display", "block");
- setTimeout(() => {
- $(".searchAnywhere").css("opacity", "1");
- }, 20);
- }
- else{
- $(".searchAnywhere").css("opacity", "0");
- setTimeout(() => {
- $(".searchAnywhere").css("display", "none");
- }, 200);
- }
- searchAnywhereOpen = !searchAnywhereOpen;
- });
- $(".searchAnywhere").unbind('click').click(() => {
- $(".searchAnywhere").css("opacity", "0");
- setTimeout(() => {
- $(".searchAnywhere").css("display", "none");
- }, 200);
- searchAnywhereOpen = false;
- })
- $(".inputArea").unbind('click').click((event) => {
- event.stopPropagation();
- })
- }, 500);
- })();