基于弹幕识别的跳过B站内置广告(v0.1)

识别多种时间格式,UI简化。

作者
能代
日安装量
2
总安装量
35
评分
2 0 0
版本
0.1.4
创建于
2025-08-13
更新于
2025-09-23
大小
36.0 KB
许可证
MIT
适用于

基于弹幕识别的跳过B站内置广告(v0.1)

Tampermonkey Bilibili License

这是一个UserScript脚本,用于在Bilibili(B站)视频页面中,通过分析弹幕(danmu)自动识别并跳过内置广告。脚本基于弹幕中的时间指令(如“快进到X分”)来检测可能的广告起始点(A)和结束点(B),并在视频播放到A时自动跳转到B。版本0.1新增了“快进指令提权”(优先保留并提升“快进到”等指令的权重)和“发布时长剔除”(排除视频开头表示“发布X分钟”的无关弹幕)功能。

功能概述

  • 自动跳过广告:基于弹幕识别广告段落(如开头广告),自动快进。
  • 时间格式识别:支持多种格式,如“X:Y”、“X分Y秒”、“X点Y”、“连续数字”(如“1234”解析为12:34)、“向右X下”等。
  • 过滤机制:排除打分类弹幕(e.g., “打X分”)、测量数据(e.g., “X米/Y秒”)、禁止标记(e.g., “+”、“%”)、以及视频开头“发布时长”弹幕(e.g., “发布一分钟”)。
  • 权重计算:优先考虑带有关键词的弹幕(如“快进到”、“广告跳过”),并通过聚类和支持弹幕提升权重。
  • UI面板:右上角mini面板显示状态,展开后显示详细日志、候选列表和匹配弹幕。
  • 配置灵活:通过CONFIG对象调整参数,如最大弹幕加载数、权重阈值、跳过时长限制等。

脚本不修改视频内容,仅监控播放时间并调整currentTime。适用于B站视频页面(https://www.bilibili.com/video/*)。

安装方法

  1. 安装Tampermonkey或其他UserScript管理器

    • Chrome/Firefox:安装Tampermonkey扩展。
    • Edge:安装Tampermonkey或类似扩展。
  2. 安装脚本

  3. 权限

    • 脚本需要GM_xmlhttpRequestGM_addStyle权限,用于获取弹幕XML和添加UI样式。

安装后,访问B站视频页面,脚本会自动运行。

使用方法

  1. 自动运行

    • 打开B站视频页面(e.g., https://www.bilibili.com/video/BVxxxxxxxx)。
    • 脚本会自动检测视频元素、解析CID(视频ID)、获取弹幕,并分析跳点。
    • 右上角出现mini面板,显示“跳点: 等待”/“分析中”/“跳点: 有”/“跳点: 无”。
  2. UI交互

    • 点击mini面板的“打开”按钮,展开详细面板。
    • 面板显示:
      • 弹幕匹配:列出匹配的弹幕(A → B)。
      • 候选时间对:所有候选跳点,按权重排序。
      • 日志:详细过程记录,包括剔除原因、权重计算等。
    • 点击“关闭”隐藏面板,返回mini模式。
  3. 跳过触发

    • 当视频播放到检测到的A点(±1秒窗口)时,自动跳转到B点。
    • 日志会记录跳转事件。
  4. 手动干预

    • 无需手动操作,但如果跳点不准,可刷新页面重试(弹幕可能因缓存或权限变化)。
    • 如果视频无弹幕或弹幕少,脚本可能无法检测跳点。
  5. 调试

    • 控制台(F12)会输出日志。
    • 修改CONFIG参数自定义行为(e.g., 增加maxDanmuLoad加载更多弹幕)。

注意:脚本依赖弹幕质量。如果视频弹幕少/无关/被屏蔽,检测准确率降低。B站可能更新API导致CID/弹幕获取失败,请报告issue。

配置参数解释

脚本的CONFIG对象定义了核心参数,可在脚本开头修改:

  • maxDanmuLoad: 最大加载弹幕数(默认6000,避免性能问题)。
  • fetchRetries: 弹幕请求重试次数(默认3)。
  • triggerWindow: 触发时间聚类窗口(秒,默认2)。
  • minDeltaSeconds: 最小跳过时长(默认5秒)。
  • maxDeltaSeconds: 最大跳过时长(默认300秒)。
  • weightWindowSeconds: 权重支持弹幕窗口(默认20秒)。
  • minSkipDuration: 最小有效跳过时长(默认5秒)。
  • maxSkipFraction: 最大跳过比例(默认视频长度的0.5)。
  • baseWeight: 基础权重(默认0.6)。
  • timeKwExtra: 时间关键词额外权重(默认2.0)。
  • targetKwExtra: 目标关键词额外权重(默认2.0)。
  • weightDanmuBoost: 支持弹幕权重提升(默认2.5)。
  • clusterBoostFactor: 聚类大小提升因子(默认0.5)。
  • forbiddenTokens: 禁止标记列表(e.g., '+', '%', 用于排除无关弹幕)。
  • measurementTokens: 测量标记列表(用于排除数据类弹幕)。
  • maxNonTimeCharsAllowed: 最大非时间字符数(默认3,超过则降权)。
  • nonTimeCharsPenaltyFactor: 非时间字符惩罚因子(默认0.2)。
  • acceptWeightThreshold: 接受权重阈值(默认0.75)。
  • fastForwardBoost: 快进指令权重提升(默认1.2)。
  • POSTAGE_WINDOW_SECONDS: 发布时长窗口(默认25秒,视频开头内检查)。
  • POSTAGE_TARGET_SECONDS: 发布时长目标(默认60秒,主要针对“1分钟”)。

关键词列表:

  • TIME_KEYWORDS: 时间指令关键词(e.g., '快进', '跳到')。
  • WEIGHT_A_KEYWORDS: A点权重关键词(e.g., '广告', '起手')。
  • WEIGHT_B_KEYWORDS: B点权重关键词(e.g., '欢迎回来')。

脚本逻辑详细解释

脚本逻辑分为初始化、数据获取、分析处理和应用跳过四个阶段。以下逐一分解:

1. 初始化(runOnce函数)

  • 创建UI:添加右上角mini面板和展开面板,使用DOM元素和CSS样式。
  • 监听视频元素:使用MutationObserver等待<video>加载,绑定timeupdate事件监听当前时间。
  • 解析CID:从页面脚本、meta标签或API获取视频CID(用于弹幕请求)。
  • 获取弹幕:使用GM_xmlhttpRequest请求XML弹幕(https://api.bilibili.com/x/v1/dm/list.so?oid={cid}),重试机制。

2. 弹幕解析(parseDanmuAndAnalyze函数)

  • 解析XML:使用DOMParser提取<d>标签的时间(p属性)和文本。
  • 标准化文本:替换全角数字、冒号、逗号等为半角,移除空格。
  • 中文数字解析:将“一”、“十”等转换为数字(chineseToNumber函数)。

3. 分析处理(analyzeItems函数)

  • 上下文判断

    • isMeasurementContext: 检查是否为测量数据(e.g., “100米/秒”),排除。
    • isScoreContext: 检查是否为打分(e.g., “打8分”),排除。
    • isFastForwardInstruction: 检查是否为快进指令(e.g., “快进到X分”),保留并提权(+fastForwardBoost)。
    • isPostAgeContext: 检查是否为发布时长(e.g., “发布一分钟”),结合A时间 <= POSTAGE_WINDOW_SECONDS 排除。
  • 时间格式识别:使用正则匹配多种格式,提取目标时间B(target),触发时间A为弹幕出现时间。

    • 冒号:X:Y
    • 分秒:X分Y秒
    • 只有分钟:X分(特殊处理:打分/发布时长剔除,快进提权)
    • 空格/点号:X Y / X.Y
    • 连续数字:XYZ(3位)或WXYZ(4位)解析为分钟:秒
    • 向右:向右X / 右X下(计算B = A + 5*X)
    • 点钟:X点Y分Z秒
  • 过滤候选

    • 排除delta(B-A)太小/太大、后跳、B超出视频时长。
    • 排除含禁止标记、非时间字符过多(降权)。
    • 计数非时间字符(countNonTimeChars),超过阈值降权。
  • 权重计算

    • 基础权重 + 关键词额外(时间/目标/A点/B点)。
    • 聚类:触发时间在窗口内聚类,提升大簇权重。
    • 支持弹幕:A/B附近无数字的权重弹幕(e.g., “广告跳过”近A,提升权重)。
    • 排序:按权重 > 数量 > 最早时间。
  • 选择跳点

    • 从排序候选中选第一个满足条件(权重 >= threshold, 簇大小 >= min, 或有支持弹幕)的。
    • 验证跳过时长(minSkipDuration ~ maxSkipFraction)。
  • 更新UI:显示候选列表、匹配弹幕、日志。

4. 应用跳过(timeupdate事件)

  • 监控currentTime,如果在A ±1秒内,设置currentTime = B。
  • 清空已触发规则。

流程图

以下使用Mermaid语法生成流程图(在GitHub Markdown中渲染)。如果无法渲染,可复制到Mermaid Live Editor查看。

flowchart TD
    A[初始化: 创建UI, 监听视频元素] --> B[解析CID: 从页面/API获取]
    B --> C{获取成功?}
    C -->|否| D[日志: 无法获取CID, 终止]
    C -->|是| E[获取弹幕: 请求XML, 重试3次]
    E --> F{弹幕数量 >0?}
    F -->|否| G[日志: 无弹幕, 终止]
    F -->|是| H[解析弹幕: 提取时间A和文本]
    H --> I[标准化文本 & 中文数字转换]
    I --> J[识别时间格式: 正则匹配多种格式, 提取B]
    J --> K[上下文判断: 排除打分/测量/发布时长, 提权快进指令]
    K --> L[过滤候选: delta范围, 禁止标记, 非时间字符降权]
    L --> M{候选 >0?}
    M -->|否| N[日志: 无有效候选, 终止]
    M -->|是| O[权重计算: 基础 + 关键词 + 聚类 + 支持弹幕]
    O --> P[排序候选: 权重 > 数量 > 最早A]
    P --> Q[选择跳点: 验证阈值/簇/支持, 选最高权重]
    Q --> R[更新UI: 显示候选/匹配/日志]
    R --> S[监听timeupdate: 当前时间 ≈ A 时跳转到B]
    S --> T[日志: 跳转成功, 清空规则]

注意事项

  • 隐私:脚本仅读取公开弹幕,不上传数据。
  • 兼容性:测试于Chrome + Tampermonkey,可能不兼容旧浏览器或B站更新。
  • 限制:依赖弹幕API,如果B站屏蔽或无弹幕,失效。跳过可能误判(e.g., 剧情时间点)。
  • 开发:欢迎PR改进,如添加更多格式或AI辅助识别。
  • 许可证:MIT,开源免费。

如果有问题,打开issue讨论!