Greasy Fork

Greasy Fork is available in English.

BiliBili Tags Blocker

眼不见为净,耳不听为清,心不想则静

当前为 2022-06-10 提交的版本,查看 最新版本

// ==UserScript==
// @name         BiliBili Tags Blocker
// @namespace    http://tampermonkey.net/
// @version      0.1
// @description  眼不见为净,耳不听为清,心不想则静
// @author       xiaoxi
// @license      MIT
// @include      *://www.bilibili.com/*
// @include      *://search.bilibili.com/*
// @icon         https://www.google.com/s2/favicons?sz=64&domain=bilibili.com
// @require      https://cdn.bootcdn.net/ajax/libs/jquery/2.2.4/jquery.min.js
// @require      http://greasyfork.icu/scripts/407543-block-obj/code/Block_Obj.js?version=963893
// @grant        GM_xmlhttpRequest
// @grant        unsafeWindow
// @grant        GM_getValue
// @grant        GM.getValue
// @grant        GM_setValue
// @grant        GM.setValue
// @grant        GM_setClipboard
// @grant        GM.setClipboard
// @grant        GM_registerMenuCommand
// @grant        GM_addValueChangeListener
// @run-at       document-start
// ==/UserScript==
// http://greasyfork.icu/zh-CN/scripts/417760-checkjquery
var BiliBiliTagsBlocker = {
    functionEnable: true,
    tagsArray: [],
};
const BASIC_STYLE = `
     .block_obj_checkbox_label {
         padding-left: 13px;
     }
  `;
let blockObj = new Block_Obj('BiliBili_Tags_Blocker');
function initSettingUI(){
    blockObj.init({
        id: 'BiliBiliTagsBlocker',
        menu: 'Tags屏蔽设置',
        style: BASIC_STYLE,
        field: [
            {
                id: 'functionEnable',
                label: '启用屏蔽功能',
                title: '总开关',
                type: 'c',
                default: true,
            },
            {
                label: 'Tag设置',
                type: 's',
            },
            {
                id: 'tagInput',
                label: '输入:',
                placeholder: ' 同时输入多个时以英文逗号分隔 ',
                type: 'i',
                list_id: 'tagsArray',
                //classname: MODULE.WHITELIST.className,
            },
            {
                id: 'tagsArray',
                type: 'l',
                default: [],
                //classname: MODULE.WHITELIST.className,
            },
        ],
        events: {
            save: config => {
                BiliBiliTagsBlocker = config;
            },
            change: config => {
                BiliBiliTagsBlocker = config;
            },
        },
    });
}
var scrollTop = 0;
//视频信息
var videoInfo = [];
var oldVideoInfo = [];
var isLoading = false;
let href = location.href;
let matchSearch = href.match(/search.bilibili/);
let matchPopular = href.match(/popular/);
//=======================通用=========================
//当前搜索区域id
var currentSectionId;

//获取视频信息
function initvideoInfo(match)
{
    let loaded = 0;
    if(match == "popular"){
        let videoCardList = $(".video-card__content");
        videoCardList.each(function(i){
            let href = $(this).children("a").attr("href");
            let bvInfo = {
                bv : getBvcountber(href),
                index : i
            }
            loaded++;
            videoInfo.push(bvInfo);
        });
        // let videoCardInfoList = $(".video-card__info");
        //videoCardInfoList.each(function(i){
        //    let title = $(this).children("p").attr("title");
        //    videoInfo[i]["title"]=title;
        // });
        console.log(videoInfo);

    }
    if(match == "search"){
        //let videoCardList = $("li.video-item");
        let videoCardList = $(".video-item");
        videoCardList.each(function(i){
            let href = $(this).children("a").attr("href");
            let title;
            let isBanner;
            if($(this).children("a").attr("title") != undefined)
            {
                title = $(this).children("a").attr("title");
                isBanner = false;

            }
            else{
                var t = $(this).children("a").context.innerText.split("\n");
                title = t[1];
                isBanner = true;
            }

            let bvInfo = {
                bv : getBvcountber(href),
                index : i,
                title : title,
                isBanner : isBanner,
                context : $(this)
            }
            loaded++;
            videoInfo.push(bvInfo);
        });

    }

    return new Promise(function (isLoad) {
        let checkvideoInfo = setInterval(function () {
            $.each(videoInfo, function(i, v){
                if(loaded == videoInfo.length){
                    clearInterval(checkvideoInfo);
                    isLoad(true);
                }
            });
        }, 500);
    });

}
//获取视频Tag信息
function initVideoTagInfo() {
    let loaded = false;
    $.each(videoInfo, function(i, b){
        $.ajax("https://api.bilibili.com/x/web-interface/view/detail/tag?bvid=BV"+b.bv, {
            method: 'GET',
            headers: {
                "content-type": "application/json"
            },
            async: true,
            success: function (tags) {
                let tagInfo = {
                    tags : tags
                }
                b["Tags"] = tagInfo;
                let r = {
                    isRemove : false
                }
                b["isRemove"] = r;
            },
        });
    });
    return new Promise(function (isLoad) {
        let checkTagsInfo = setInterval(function () {
            $.each(videoInfo, function(i, v){
                if (v.hasOwnProperty("Tags") && v.Tags.hasOwnProperty("tags") && videoInfo[0].hasOwnProperty("isRemove")) {
                    if (v.Tags.tags.hasOwnProperty("data")) {
                        if(i == videoInfo.length-1){
                            clearInterval(checkTagsInfo);
                            isLoad(true);
                        }
                    }
                }

            });
        }, 500);
    });
}
//设置需要删除的视频
function setRemoveVideo(){
    let loaded = 0;
    $.each(videoInfo, function(i, v){
        loaded++;
        if (v.hasOwnProperty("Tags") && v.Tags.hasOwnProperty("tags") && videoInfo[0].hasOwnProperty("isRemove")) {
            if (v.Tags.tags.hasOwnProperty("data") && v.Tags.tags.data.length > 0) {
                $.each(v.Tags.tags.data, function(i, t){
                    $.each(BiliBiliTagsBlocker.tagsArray, function(i, bt){
                        if(bt == t.tag_name){
                            let r = {
                                isRemove : true
                            }
                            v["isRemove"] = r;
                        }
                    });
                });
            }
        }
    });
    return new Promise(function (isLoad) {
        let checkTagsInfo = setInterval(function () {
            if (videoInfo.length == loaded) {
                clearInterval(checkTagsInfo);
                isLoad(true);
            }
        }, 500);
    });

}
//删除网页中的视频
function removeVideo(match){
    let Removed = 1;
    $.each(videoInfo, function(i, v){
        if(v.hasOwnProperty("isRemove") && v.isRemove.hasOwnProperty("isRemove")  && v.isRemove.isRemove && oldVideoInfo != videoInfo){
            if(match == "popular"){
                $(".video-card:nth-of-type("+(v.index+Removed)+")").remove();
                console.log((v.index+Removed)+"  "+ v.bv+ "  "+Removed);
                Removed--;
            }
            if(match == "search"){

                v.context.css({"display":"none"});
                //v.context.css({"background":"blue"})

            }
        }
    });
}
//视频板块监听器
function initBodyContainListener(){

    var targetNode = $('.body-contain')[0];
    //options:监听的属性
    var options = {childList: true,attributes :true};
    //回调事件
    console.log("init 板块监听");

    function callback(mutationsList, observer) {
        if(currentSectionId != $(".body-contain").children("div").attr("id"))
        {
            currentSectionId = $(".body-contain").children("div").attr("id");
            console.log("搜索区域变为"+currentSectionId);
            //console.log("板块监听 callback");

            initSearchSectionListener();
            initSearchListener()
            if(currentSectionId == "all-list" || currentSectionId == "video-list"){
                setTimeout(function(){
                    oldVideoInfo = videoInfo;
                    videoInfo = [];
                    //SearchLoading()
                    initvideoInfo("search").then(function (resolve) {
                        initVideoTagInfo().then(function (resolve) {
                            setRemoveVideo().then(function (resolve) {
                                //console.log(videoInfo);
                                removeVideo("search")
                                //stopSearchLoading()
                            });
                        });
                    });
                },1200);
            }
        }

    }
    let mutationObserver = new MutationObserver(callback);
    let checkTarget = setInterval(function () {
        currentSectionId = $(".body-contain").children("div").attr("id");
        console.log("等待搜索区域");
        targetNode = $('.body-contain')[0];
        if(targetNode !=  undefined && targetNode !=  null && currentSectionId != undefined){
            mutationObserver.observe(targetNode, options);
            console.log("搜索区域变为"+currentSectionId);
            // initSearchLoading() BUG
            initSearchSectionListener();
            initSearchListener()
            //SearchLoading() BUG
            setTimeout(function(){
                oldVideoInfo = videoInfo;
                videoInfo = [];
                initvideoInfo("search").then(function (resolve) {
                    initVideoTagInfo().then(function (resolve) {
                        setRemoveVideo().then(function (resolve) {
                            //console.log(videoInfo);
                            removeVideo("search")
                            // stopSearchLoading() BUG
                        });
                    });
                });
            },500);
            clearInterval(checkTarget);
        }

    }, 500);
}


//=======================热门页面=========================
//设置监听器,监听新加载的视频
function initPopularListener(){
    var targetNode = $('.card-list')[0];
    //options:监听的属性
    var options = {childList: true,subtree:true};
    //回调事件

    function callback(mutationsList, observer) {
        if(mutationsList[0].addedNodes.length!=0 && videoInfo.length>=20 && isLoading == false){
            isLoading = true;
            oldVideoInfo = videoInfo;
            scrollTop = $(document).scrollTop();
            Loading();
            $(document).scrollTop(0);
            videoInfo = [];
            initvideoInfo("popular").then(function (resolve) {
                initVideoTagInfo().then(function (resolve) {
                    setRemoveVideo().then(function (resolve) {
                        removeVideo("popular");
                        //console.log(videoInfo);
                        stopLoading()
                        scrollTop = $(document).scrollTop(scrollTop);
                        isLoading = false;
                    });
                });
            });
        }
    }
    var mutationObserver = new MutationObserver(callback);
    mutationObserver.observe(targetNode, options);
}
//初始化加载动画
function initLoading(){
    let g_loadingImage = 'https://pp-1252089172.cos.ap-chengdu.myqcloud.com/loading.gif';
    $('.popular-list').prepend('<div id="loading" style="background-color: white;width:100%;text-align:center;position:sticky;z-index:999999;top: 200px;left: 0;"><img style="text-align:center;position:-webkit-sticky;position:sticky;z-index:999999;top: 0;left: 0;" src="' + g_loadingImage + '" /><p id="progress" style="display:none;text-align: center;font-size: large;font-weight: bold;padding-top: 10px;">0%</p></div>');
    $("head").append('<style type="text/css">.no-more{ display: none; } .scroll-loading{ display: none; } .popular-tips{ display: none; }</style>');
    $(".card-list").css({'display': 'none'});
    $(document).scrollTop(0);
}
//进行加载动画
function Loading(){
    $("#loading").css({'display': 'block'});
    $(".card-list").css({'display': 'none'});
    $(document).scrollTop(0);
}
//停止加载动画
function stopLoading(){
    $("#loading").css({'display': 'none'});
    $(".card-list").css({'display': 'flex'});
    $(document).scrollTop(scrollTop)
}

//==================搜索页面=======================
function disConnectListener(){
    console.log(33333333333);

    //videoListListener.disconnect();
}

//初始化加载动画
function initSearchLoading(){
    let g_loadingImage = 'https://pp-1252089172.cos.ap-chengdu.myqcloud.com/loading.gif';
    $('.body-contain').children("div").prepend('<div id="loadingSearch" style="background-color: white;width:100%;height:92px;text-align:center;position:absolute;z-index:999999;top: 150px;left: 0;"><img style="text-align:center;position:-webkit-sticky;position:sticky;z-index:999999;top: 0;left: 0;" src="' + g_loadingImage + '" /><p id="progress" style="display:none;text-align: center;font-size: large;font-weight: bold;padding-top: 10px;">0%</p></div>');
    //$("head").append('<style type="text/css">.no-more{ display: none; } .scroll-loading{ display: none; } .popular-tips{ display: none; }</style>');
    $(".video-list").css({'display': 'none'});
    //$(document).scrollTop(0);
}
//进行加载动画
function SearchLoading(){
    $("#loadingSearch").css({'display': 'block'});
    $(".video-list").css({'display': 'none'});
    //$(document).scrollTop(0);
}
//停止加载动画
function stopSearchLoading(){
    $("#loadingSearch").css({'display': 'none'});
    $(".video-list").css({'display': 'block'});
    //$(document).scrollTop(scrollTop)
}
//页码监听
function initSearchListener(){

    var targetNode = $('.flow-loader')[0];
    //options:监听的属性
    var options = {childList: true,attributes :true};
    //回调事件
    console.log("init 页码监听");
    function callback(mutationsList, observer) {
        if(mutationsList[0].addedNodes.length!=0 && videoInfo.length>=20 && isLoading == false)
        {
            console.log("页码监听 callback");
            initSearchSectionListener()
            let c = [];
            $.each(mutationsList, function(i, m){
                if(m.addedNodes[0] != undefined && m.addedNodes[0] != null){
                    if(m.addedNodes[0].className != undefined && m.addedNodes[0].className != null){
                        c = m.addedNodes[0].className.split(" ")
                    }
                }
                if(m.addedNodes[0] != undefined && m.addedNodes[0].previousSibling != undefined && c.includes("video-list")){
                    isLoading = true;
                    oldVideoInfo = videoInfo;
                    videoInfo = [];
                    //SearchLoading() BUG
                    initvideoInfo("search").then(function (resolve) {
                        initVideoTagInfo().then(function (resolve) {
                            setRemoveVideo().then(function (resolve) {
                                removeVideo("search")
                                //stopSearchLoading() BUG
                                isLoading = false;
                            });
                        });
                    });
                }
            });
        }
    }
    var mutationObserver = new MutationObserver(callback);
    let checkTarget = setInterval(function () {
        if(targetNode !=  undefined && targetNode !=  null){
            mutationObserver.observe(targetNode, options);
            clearInterval(checkTarget);
        }

    }, 500);
}

//选项监听
function initSearchSectionListener(){

    var targetNode = $('.video-list')[0];
    //options:监听的属性
    var options = {childList: true,attributes :true};
    //回调事件
    console.log("init 选项监听");

    function callback(mutationsList, observer) {
        console.log("选项监听 callback");
        oldVideoInfo = videoInfo;
        videoInfo = [];
        initvideoInfo("search").then(function (resolve) {
            // SearchLoading() BUG
            initVideoTagInfo().then(function (resolve) {
                setRemoveVideo().then(function (resolve) {
                    //console.log(videoInfo);
                    removeVideo("search")
                    //stopSearchLoading() BUG
                });
            });
        });
    }
    let mutationObserver = new MutationObserver(callback);
    let checkTarget = setInterval(function () {
        if(targetNode !=  undefined && targetNode !=  null){
            mutationObserver.observe(targetNode, options);
            clearInterval(checkTarget);
        }

    }, 500);
}
//通过url获得BV号
function getBvcountber(video_link) {
    let bvcount = '';
    try {
        bvcount = /\/video\/(?:av|bv)(\w+)/i.exec(video_link)[1];
    } catch (e) {
        bvcount = null;
    }
    return bvcount;
}

//检查jQuery
var checkJQuery = function () {
    let jqueryCdns = [
        'http://code.jquery.com/jquery-2.1.4.min.js',
        'https://ajax.aspnetcdn.com/ajax/jquery/jquery-2.1.4.min.js',
        'https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js',
        'https://cdn.staticfile.org/jquery/2.1.4/jquery.min.js',
        'https://apps.bdimg.com/libs/jquery/2.1.4/jquery.min.js',
    ];
    function isJQueryValid() {
        try {
            let wd = unsafeWindow;
            if (wd.jQuery && !wd.$) {
                wd.$ = wd.jQuery;
            }
            $();
            return true;
        } catch (exception) {
            return false;
        }
    }
    function insertJQuery(url) {
        let script = document.createElement('script');
        script.src = url;
        document.head.appendChild(script);
        return script;
    }
    function converProtocolIfNeeded(url) {
        let isHttps = location.href.indexOf('https://') != -1;
        let urlIsHttps = url.indexOf('https://') != -1;

        if (isHttps && !urlIsHttps) {
            return url.replace('http://', 'https://');
        } else if (!isHttps && urlIsHttps) {
            return url.replace('https://', 'http://');
        }
        return url;
    }
    function waitAndCheckJQuery(cdnIndex, resolve) {
        if (cdnIndex >= jqueryCdns.length) {
            iLog.e('无法加载 JQuery,正在退出。');
            resolve(false);
            return;
        }
        let url = converProtocolIfNeeded(jqueryCdns[cdnIndex]);
        iLog.i('尝试第 ' + (cdnIndex + 1) + ' 个 JQuery CDN:' + url + '。');
        let script = insertJQuery(url);
        setTimeout(function () {
            if (isJQueryValid()) {
                iLog.i('已加载 JQuery。');
                resolve(true);
            } else {
                iLog.w('无法访问。');
                script.remove();
                waitAndCheckJQuery(cdnIndex + 1, resolve);
            }
        }, 100);
    }
    return new Promise(function (resolve) {
        if (isJQueryValid()) {
            iLog.i('已加载 jQuery。');
            resolve(true);
        } else {
            iLog.i('未发现 JQuery,尝试加载。');
            waitAndCheckJQuery(0, resolve);
        }
    });
}

let checkSetting = setInterval(function () {
    BiliBiliTagsBlocker = blockObj.getConfig();
    if(BiliBiliTagsBlocker.tagsArray != null){
        //console.log(BiliBiliTagsBlocker.tagsArray);
        clearInterval(checkSetting);
    }
}, 500);
function ILog() {
    this.prefix = '';

    this.v = function (value) {
        if (level <= this.LogLevel.Verbose) {
            console.log(this.prefix + value);
        }
    }

    this.i = function (info) {
        if (level <= this.LogLevel.Info) {
            console.info(this.prefix + info);
        }
    }

    this.w = function (warning) {
        if (level <= this.LogLevel.Warning) {
            console.warn(this.prefix + warning);
        }
    }

    this.e = function (error) {
        if (level <= this.LogLevel.Error) {
            console.error(this.prefix + error);
        }
    }

    this.d = function (element) {
        if (level <= this.LogLevel.Verbose) {
            console.log(element);
        }
    }

    this.setLogLevel = function (logLevel) {
        level = logLevel;
    }

    this.LogLevel = {
        Verbose: 0,
        Info: 1,
        Warning: 2,
        Error: 3,
    };

    let level = this.LogLevel.Verbose;
}
let inChecking = false;
let jqItv = setInterval(function () {
    if (inChecking) {
        return;
    }
    inChecking = true;
    checkJQuery().then(function (isLoad) {
        if (isLoad)
        {
            initSettingUI()
            if (matchSearch) {
                //initSearchLoading()
                initBodyContainListener();
                initSearchListener();
                initSearchSectionListener();
                initvideoInfo("search").then(function (resolve) {
                    initVideoTagInfo().then(function (resolve) {
                        setRemoveVideo().then(function (resolve) {
                            //console.log(videoInfo);
                            removeVideo("search")
                            //stopSearchLoading()
                        });
                    });
                });
            }
            if (matchPopular) {
                initLoading();
                initPopularListener()
                initvideoInfo("popular").then(function (resolve) {
                    initVideoTagInfo().then(function (resolve) {
                        setRemoveVideo().then(function (resolve) {
                            removeVideo("popular")
                        });
                    });
                });
            }
            clearInterval(jqItv);

        }
        inChecking = false;
    });
}, 1000);
var iLog = new ILog();