DanmakuRender-4 —— 一个录制带弹幕直播的小工具(版本4)
结合网络上的代码写的一个能录制带弹幕直播流的小工具,主要用来录制包含弹幕的视频流。
- 可以录制纯净直播流和弹幕,并且支持在本地预览带弹幕直播流。
- 可以自动渲染弹幕到视频中,并且渲染速度快。
- 支持同时录制多个直播。
- 支持录播自动上传至B站。
旧版本可以在分支v1-v3找到。
全新的DanmakuRender-5已经推出,欢迎大家试用。
特别注意事项
- Python3.10及以上版本录制斗鱼弹幕失败?
请使用Python3.9版本录制。
- 在主播意外断流恢复之后(例如PK结束和开始的时候)视频出现花屏?
修改下载引擎为streamgears,具体方法见下文示例.
- B站录制失败?
自2023.10.25起,未登录B站账号的用户只能获取最低画质直播流。在录制B站的时候将会要求登录到B站从而录制原画直播,默认情况下,登录信息将保存到.temp/.bili_watch_cookies.json
文件。如果愿意不登录B站录制480P,请参考高级视频录制参数设置修改。
使用说明
如果你是纯萌新建议看我B站的专栏安装:https://www.bilibili.com/read/cv26348023
安装与使用文档
安装文档
使用文档
以下折叠内容为旧版文档,仅供特殊情况下参考
2023.8.11更新:优化程序执行逻辑,提供更多的配置文件选项,提供更多的说明文档,添加自动清理上传完成文件的功能
2023.7.10更新:优化弹幕录制和FFmpeg录制,修改部分参数名称,自动更新优化
2023.6.5更新:多任务并行渲染,抖音弹幕录制
2023.4.30更新:添加新的streamgears下载引擎,修改部分代码逻辑
2023.3.5更新:添加自动上传功能,修改默认分支为v4
2023.1.6更新:更新版本4,优化逻辑
### 前置要求
- Python 3.7+
- Python库 aiohttp,requests,execjs,lxml,yaml
- FFmpeg
- 满足条件的NVIDIA或者AMD显卡(也可以不用,但是渲染弹幕会很卡)
### 安装
- 下载源代码
- 下载ffmpeg,将ffmpeg.exe和ffprobe.exe移动到`tools`文件夹下
- 下载biliup-rs可执行文件(https://github.com/biliup/biliup-rs/releases ),将其放到`tools`文件夹下或者修改配置文件。
### 使用方法
新版本使用yaml配置文件的方法来指定参数,配置文件一共有两个,分别为`default.yml`(默认配置文件)和`replay.yml`(录制配置文件),
一般情况下默认配置文件不需要修改,只需要修改录制配置文件,**程序第一次启动时会自动创建配置文件**。
启动程序可以直接运行`python main.py`,不需要附带参数。
录制配置文件内录制任务应该满足如下格式
```yaml
replay: # 一个数组,每个元素表示一个录制任务
- url: # 第一个任务
<录制参数>: <参数值> # 可选
...
- url: # 第二个任务
...
...
```
录制配置文件示例如下:
- 录制B站13308358直播间
```yaml
replay:
- url: https://live.bilibili.com/13308358
```
- 录制B站13308358直播间,指定分段时间1800秒
```yaml
replay:
- url: https://live.bilibili.com/13308358
segment: 1800
```
- 录制多个直播间,并且指定不同的分段时间,
```yaml
replay:
- url: https://live.bilibili.com/13308358
segment: 1800
- url: https://live.bilibili.com/23197314
segment: 3600
danmaku: false # 指定此任务不需要录制弹幕
```
高阶用例:
- 使用不同的下载引擎
```yaml
replay:
- url: https://live.bilibili.com/13308358
engine: streamgears # 使用streamgears作为下载引擎
vid_format: flv # 使用streamgears作为下载引擎时,录制格式只能是flv
```
注意:使用streamgears作为下载引擎时,录制格式只能是flv,使用其他格式可能会导致意外错误
- 使用其他种类的编码器
```yaml
# replay.yml
render:
hwaccel_args: [-hwaccel,cuda,-noautorotate] # 硬件解码参数,不同平台设置不一样,一般情况下不是N卡都设置为空比较好
vencoder: hevc_nvenc # 使用NVIDIA NVENC H.265编码器
vencoder_args: ['b:v','15M'] # 特殊指定编码器参数,可用参数根据编码器不同而不同
replay:
- url: https://live.bilibili.com/13308358
```
注意:可用编码器根据平台不同而不同,目前比较常用的编码器如下:
| 编码类型 | 编码器 | 注释 |
| :-------: | :-------: | :-------: |
| H.264 | h264_nvenc | N卡使用 |
| H.264 | h264_amf | A卡使用 |
| H.264 | libx264 | 纯CPU编码使用 |
| H.264 | h264_qsv | Intel集成显卡使用 |
| H.265(HEVC) | hevc_nvenc | N卡使用 |
| H.265(HEVC) | hevc_amf | A卡使用 |
| H.265(HEVC) | libx265 | 纯CPU编码使用 |
| H.265(HEVC) | hevc_qsv | Intel集成显卡使用 |
一般情况下不建议使用H.265编码器,因为编码慢很多,除非是自己本地存档需要节省磁盘空间。
- 使用伪4K绕过B站码率限制
```yaml
# replay.yml
render:
output_resize: 3840x2160 # 设置渲染的带弹幕视频的分辨率,3840x2160正好是16:9的4K视频
replay:
- url: https://live.bilibili.com/13308358
```
现在B站的普通1080P视频最高码率一般不超过2Mbps(AV1编码),本地看视频不糊但是传B站就糊就是这个原因。
为了绕开这个限制,需要使用伪4K的功能,简单地说就是把视频缩放到4K,让B站以为是4K视频然后按4K分配码率,最后看的时候就会很清晰。
当然,你愿意的话甚至可以缩放到8K(7680x4320),不过渲染速度的话就不好说了,并且一般情况下4K已经能分到15M的码率了,8K分30M的码率没什么必要。
带自动上传功能的录制
**注意此功能正在测试,可能遇到意料之外的问题,记得拿小号测试!**
上传功能由biliup-rs支持,请先下载biliup.exe可执行文件到tools文件夹,biliup-rs项目地址:https://biliup.github.io/biliup-rs/index.html
简单上传,只上传到b站的一个账号:
```yaml
replay:
- url: https://live.bilibili.com/13308358
upload: # 指定此任务需要自动上传
src_video: bilibili # 指定上传源视频到B站
dm_video: bilibili # 指定上传弹幕视频到B站
```
在此任务中,视频会上传到B站的默认账号,弹幕视频和源视频将会分别上传,上传任务会在直播结束后进行。如果不想上传源视频就删掉src_video那一条。
如果需要复杂的上传,则必须先在录制配置文件中创建一个上传器,然后对不同任务使用不同上传器上传:
```yaml
# replay.yml
upload: # 创建上传器
bzhan-1: # 上传器名称,可以随便写但是不能重复
title: '直播回放1号' # 接下来的参数就是default.yml里面的自动上传参数
# 相当于可以单独设置上传的标题什么的
bzhan-2:
title: '直播回放2号'
replay:
- url: https://live.bilibili.com/13308358
upload: # 指定此任务需要自动上传
src_video: bzhan-1 # 指定上传源视频到第一个上传器
dm_video: bzhan-2 # 指定上传弹幕视频第二个上传器
```
多个上传器之间按照cookies来区分,默认保存cookies到`.temp/<上传器名称>.json`,如果想把多个上传器指定到一个账号则需要手动指定cookies到相同的路径。
**特别提醒:cookies内包含了登录信息,不要将他分享给任何人!**
### 注意事项
- 程序的工作流程是:先录制一小时直播,然后在录制下一小时直播时启动对这一小时直播的渲染。录制完成后可以同时得到直播回放和带弹幕的直播回放(分为两个视频)
- 程序默认使用NVIDIA的硬件编码器渲染,如果用A卡的话需要修改参数。如果不渲染弹幕就不用管。
- 在关闭程序时,如果选择了自动渲染弹幕,则一定要等录制结束并且渲染完成再关闭(由于程序设定是先录制后渲染),否则带弹幕的录播会出问题。
- 如果因为配置比较差,渲染视频比较慢导致渲染比录制慢很多的,可以选择先不渲染弹幕,在录制结束后打开`render_only.py`手动渲染。(这种情况比较少见,因为渲染的速度很快,我1060的显卡都可以同时录两个直播)
- 在录制的过程中弹幕保存为一个字幕文件,因此使用支持字幕的播放器在本地播放录播可以有弹幕的效果(**就算是没渲染弹幕也可以!**),拿VLC播放器为例,在播放录像时选择字幕-添加字幕文件,然后选择对应的ass文件就可以预览弹幕了。
### 默认参数说明
#### 关键字替换说明
一些名称可以使用关键字替换,{xxx}这样的说明把这个东西在程序运行时动态换成指定的内容。例如:
`{STREAMER}-{YEAR}年{MONTH}月{DAY}日{HOUR}点{MINUTE}分` 在执行时大概会是这个样子:
`飞天狙想要努力变胖-2023年3月1日20点30分`。
可用关键字:
{STREAMER}主播名称,{TITLE}标题,{HAS_DANMU}“带弹幕版”这几个字,{URL}直播间链接
{YEAR}年,{MONTH}月,{DAY}日,{HOUR}点,{MINUTE}分,{SECOND}秒
**注意:具体参数以default.yml为准.**
```yaml
# ######################
# 此文件非必要不用修改!
# ######################
# FFprobe 可执行程序地址,为空自动搜索
ffprobe: ~
# FFmpeg 可执行程序地址,为空自动搜索
ffmpeg: ~
# biliup-rs可执行文件地址,为空自动搜索
biliup: ~
# 录制参数
downloader:
# 录制输出文件夹,设置为空则使用主播名称作为文件夹
output_dir: ./直播回放
# 录制文件名称格式,可使用关键字替换,默认效果:飞天狙想要努力变胖-2023年3月1日20点30分,注意这里不能含有冒号,斜杠等非法字符!!
output_name: '{STREAMER}-{YEAR}年{MONTH}月{DAY}日{HOUR}点{MINUTE}分'
# 录制程序引擎,可选ffmpeg(由ffmpeg提供拉流服务)或者streamgears(使用streamgears提供拉流服务,此功能正在测试)
# 在使用streamgears作为录制引擎时,录制视频格式只能是flv
engine: ffmpeg
# 录播分段时间(秒),默认一个小时
segment: 3600
# 是否录制弹幕
danmaku: True
# 是否录制直播流
video: True
# 启动自动渲染
auto_render: True
# 延迟下播计时(分钟)
end_cnt: 1
# 默认分辨率,如果程序无法正常判断流的分辨率可以使用以下参数强行指定
resolution: [1920,1080]
# 录制视频的格式,默认flv
# 使用streamgears作为录制引擎应该使用flv
vid_format: flv
# 直播流CDN选项
# 对于虎牙直播,此项可选al, tx, hw等cdn服务器的缩写,默认al
# 对于B站,此项可选0-n表示不同的cdn服务器,默认为0,也可以输入特定的CDN域名前缀,例如 c1--cn-gotcha208
# 斗鱼和抖音暂时没用
flow_cdn: ~
# ffmpeg http参数
# 使用streamgears作为录制引擎时不生效
ffmpeg_stream_args: [-fflags,+discardcorrupt,-reconnect,'1',-rw_timeout,'10000000',
'-analyzeduration','15000000',
'-probesize','50000000',
'-thread_queue_size', '16']
# 关闭下载过慢自动重启功能,默认false
# 使用streamgears作为录制引擎时不生效
disable_lowspeed_interrupt: False
# 检测流变化,在推流信息变化时立即分段,建议录制手机直播时开启,PC直播时关闭,默认false
# 使用streamgears作为录制引擎时不生效
check_stream_changes: False
# 以下是弹幕录制参数
# 弹幕录制格式,只能选择ass
dm_format: ass
# 弹幕上下间距(行距),设置为0-1的表示为视频宽度的倍数,设置为大于1的数表示像素,默认6
margin_h: 6
# 弹幕左右间距,设置为-1表示允许弹幕叠加,设置为0-1的表示间距为视频宽度的倍数,设置为大于1的数表示像素,默认0.05
margin_w: 0.05
# 指定弹幕占屏幕的最大比例(即屏幕上半部分有多少可以用来显示弹幕),默认为0.4
dmrate: 0.4
# 指定弹幕字体,默认为微软雅黑字体(Microsoft YaHei)
font: Microsoft YaHei
# 指定弹幕字体大小,默认为36
fontsize: 36
# Distance from Screen Top 弹幕距离屏幕顶端的距离(像素,例如20,表示距离屏幕顶端20px)
dst: 20
# 指定单条弹幕持续时间(秒),默认为16
dmduration: 16
# 指定弹幕不透明度,默认为0.8
opacity: 0.8
# 使用自适应弹幕大小(会让把设置的弹幕大小按1080P标准缩放)
auto_fontsize: True
# 弹幕描边颜色(6位十六进制)
outlinecolor: 000000
# 弹幕描边宽度
outlinesize: 1.0
# 弹幕延迟补偿(秒),一般情况下弹幕比视频慢,设置这个强行把弹幕提前,不同直播间不一样
dm_delay_fixed: 3.0
# 弹幕录制程序自动重启间隔(在没人发弹幕的时候会定时重启,保证录制正常,默认300秒,0关闭)
dm_auto_restart: 300
# 弹幕过滤规则,一个正则表达式,符合此条件的弹幕将被过滤,默认为空(不过滤弹幕)
dm_filter: ~
# 渲染参数
render:
# 渲染输出文件夹,默认为空(在录制输出文件夹后面加上“带弹幕版”)
output_dir: ~
# 生成的视频文件格式,默认mp4
format: mp4
# 渲染引擎,可选ffmpeg(纯ffmpeg渲染)或者python(Python PIL作为弹幕的图像渲染器,ffmpeg作为视频编码器,此功能正在测试,请勿使用)
engine: ffmpeg
# 同时执行的渲染任务数,默认1,若渲染时CPU和GPU使用都低于80%可以调高这个,一般情况下设置应该小于5
# 特别提示:如果渲染一个CPU或者显卡占用都很高,调高这个反而有副作用!
nrenders: 1
# 硬件解码参数,默认由FFmpeg自动判断,如果出现问题可以设为空
hwaccel_args: [-hwaccel, auto]
# 视频编码器,NVIDIA设置为h264_nvenc,AMD设置为h264_amf,CPU设置为libx264
vencoder: h264_nvenc
# 视频编码器参数,默认恒定码率15Mbps
vencoder_args: [-b:v, 15M]
# 音频编码器
aencoder: aac
# 音频编码器参数,默认恒定码率320Kbps
aencoder_args: [-b:a, 320K]
# 输出重缩放,会把输出重缩放到指定分辨率,可以设置为'3840x2160'用于在B站传伪4K保证清晰度
output_resize: ~
# 以下参数只适用于python渲染器
# 渲染线程数(单个渲染器使用的进程数量),默认2
nproc: 2
# 渲染管道缓冲区大小(MB)
bufsize: 100
# 弹幕重排序
danmaku_resort: False
# 自动上传参数
uploader:
# 最大并行任务数,在录制多个主播时允许同时上传的最大视频数量,设置为-1表示不限制,默认1
nuploaders: 1
# 上传目标(目前只有B站)
bilibili:
# 上传引擎,目前只能选biliuprs
engine: biliuprs
# 上传账号名称,程序依靠这个来识别不同的账号,如果打算传不同账号就要设置不同的名称
account: bilibili
# (此功能暂不生效)重试次数,如果上传遇到错误将会重试,设置为0表示不重试
retry: 0
# (此功能暂不生效)实时上传,每录制一个分段上传一次,同一场直播的不同分P仍然会在一个视频下,默认关闭
realtime: False
# 登录信息保存的cookies路径,默认为空(由程序自动生成".temp/<上传账号名称>.json"的文件)
# 如果同时指定上传账号和cookies,那么程序会优先使用cookies路径
cookies: ~
# 上传的视频最短长度,小于此长度的视频会被自动过滤,默认五分钟
min_length: 300
# 以下参数来自biliuprs,详细内容可以参考 https://biliup.github.io/biliup-rs/index.html
# 上传线路
line: bda2
# 上传线程数
limit: 3
# 是否为转载视频 1-自制 2-转载
copyright: 1
# 转载来源
source: ''
# 分区号,分区参考 https://biliup.github.io/tid-ref.html
tid: 65
# 封面,指向本地文件地址
cover: ''
# 标题,可以使用关键字替换
# {STREAMER}主播名称,{TITLE}标题,{YEAR}年,{MONTH}月,{DAY}日,{HAS_DANMU}“带弹幕版”这几个字,{URL}直播间链接
# 默认的例子:[飞天狙想要努力变胖/直播回放] 晚上七点半比赛 2023年2月24日 (带弹幕版)
title: '[{STREAMER}/直播回放] {TITLE} {YEAR}年{MONTH}月{DAY}日 {HAS_DANMU}'
# 简介,可以使用关键字替换
desc: "{STREAMER} 的直播回放{HAS_DANMU} \n直播地址:{URL} \n标题:{TITLE} \n时间:{YEAR}年{MONTH}月{DAY}日 \n\n————————————\n由DanmakuRender录制: \nhttps://github.com/SmallPeaches/DanmakuRender"
# 动态内容,可以使用关键字替换
dynamic: '{STREAMER} 的直播回放,{YEAR}年{MONTH}月{DAY}日'
# 互动视频
interactive: 0
# 标签(一定要有!多个标签逗号分割)
tag: '直播回放'
# 延迟发布,单位秒
dtime: 0
# 是否开启杜比音效? 0-关闭 1-开启
dolby: 0
# 允许转载? 0-允许转载,1-禁止转载
no_reprint: 1
# 是否开启充电? 0-关闭 1-开启
open_elec: 1
# 自动清理参数
cleaner:
# 移动文件
move:
# 目标文件夹,可以使用关键字替换,文件夹不存在会自动创建
# 如果设置为空或者"*TRASHBIN*",那么文件将会被移动至回收站
dest: ~
# 清理延迟(秒),在上传完成后会过一段时间再清理
delay: 86400
# (此功能暂不生效)只清理此次运行中上传成功的文件
strict: True
# (此功能暂不生效)是否等待执行完成
wait: True
# 复制文件
copy:
# 目标文件夹,可以使用关键字替换,文件夹不存在会自动创建
dest: ~
# 复制延迟(秒),在上传完成后会过一段时间再复制
delay: 0
# (此功能暂不生效)只复制此次运行中上传成功的文件
strict: True
# (此功能暂不生效)是否等待执行完成
wait: True
# 删除文件
delete:
# 删除延迟(秒),在上传完成后会过一段时间再复制
delay: 172800
# (此功能暂不生效)只复制此次运行中上传成功的文件
strict: True
# (此功能暂不生效)是否等待执行完成
wait: True
```
可选参数
程序运行时可以指定以下参数
-c
指定录制配置文件位置,默认replay.yml
--version
查看版本号
--skip_update
跳过版本检查
更多
感谢 THMonster/danmaku, wbt5/real-url, ForgQi/biliup, ForgQi/stream-gears 的工作。
出现问题欢迎大家提issue讨论。
本程序仅供研究学习使用!