如何使用 ffmpeg 记录特定窗口?

Posted

技术标签:

【中文标题】如何使用 ffmpeg 记录特定窗口?【英文标题】:How to record a specific window using ffmpeg? 【发布时间】:2014-10-13 08:13:26 【问题描述】:

我使用 ffmpeg 使用这段代码记录一个窗口:

ffmpeg.exe
-f dshow 
-y 
-i video="screen-capture-recorder":audio="virtual-audio-capturer":audio="Microphone (USB Audio Device)" 
-framerate 15 
-vcodec libx264 
-crf 0 
-preset ultrafast 
-acodec pcm_s16le 
-vf crop=Width:Height:Left:Top 
output.flv

但问题是我可能会移动窗口,这会导致记录一个没有我想要的窗口的区域。

如何捕获可以移动的特定窗口?


编辑:我还使用gdigrab 来捕获我的窗口(例如Skype)而不是dshow

ffmpeg.exe
-y
-f dshow
-i audio="virtual-audio-capturer":audio="Microphone (USB Audio Device)"
-f gdigrab
-draw_mouse 0
-i title="Skype"
-framerate 30
-vcodec libx264
-crf 0
-preset ultrafast
-acodec pcm_s16le
output.flv

但是会议是黑色的……

【问题讨论】:

如果你还想要这个,请提交屏幕截图记录器的问题[我维护它] 您可以使用 dshow 和一种将偏移量动态传递给它的编程语言!您使用了裁剪过滤器,这很好,您可以使用程序创建边框,当您拖动该边框时,它会动态更改过滤器的偏移量。 ***.com/a/43464269/6180077 访问此链接以获取有效的 FFMPEG c++ mp4 格式屏幕录像机应用程序。 【参考方案1】:

这个例子对我有用:

ffmpeg -f gdigrab -framerate 30 -i title="german.avi - VLC media player" -b:v 3M  germ.flv

其中“title”表示目标窗口的实际标题。

希望这会有所帮助。

【讨论】:

当我运行这个命令时,我得到这个错误:未知输入格式:'gdigrab'你能告诉我如何解决这个问题【参考方案2】:

我也在网上寻找解决方案,但对我找到的答案不满意。我现在整理了这个非常简单的 linux 解决方案:

ffmpeg -f x11grab -framerate 25 \
    $(xwininfo | gawk 'match($0, /-geometry ([0-9]+x[0-9]+).([0-9]+).([0-9]+)/, a)\
       print "-video_size " a[1] " -i +" a[2] "," a[3] ') \
    $(date +%Y-%m-%d_%H-%M_%S).mp4

执行此命令后,可以用鼠标指针选择窗口

目标文件名将在当前目录中采用YYYY-mm-dd_hh_mm_ss.mp4 的形式。

那里的 awk 魔法只是解析窗口信息。它很难看,只能与 gnu awk 一起使用,但我还没有找到更好的方法来将窗口几何图形解析为自定义格式。

在屏幕上记录特定矩形的语法是:

-video_size [width]x[height] -i [x],[y]

我相信也应该在 windows 和 dshow 下工作。

【讨论】:

不知道为什么我总是只运行 xwininfo 然后寻找我需要的数据。你在这里使用它的方式很棒。 好像有窗口边框,x,y位置是包含边框的,但是宽、高只是边框内窗口的大小。所以 a[2] 和 a[3] 应该加上边框宽度。不过,这让它变得更加复杂。 我已经运行了你的命令,当我点击一个特定的窗口时,它不会只记录那个特定的窗口,而是记录整个当前屏幕。你能告诉我如何选择一个特定的窗口。【参考方案3】:

ffmpeg -rtbufsize 1500M -f dshow -i audio="virtual-audio-capturer" -f gdigrab -framerate 30 -draw_mouse 1 -i title=RecordWindow -pix_fmt yuv420p -profile:v baseline -y Huangbaohua.mp4

RecordWindow 是指定窗口的标题。

【讨论】:

这对于那些能够自己编译 ffmpeg 的人来说实际上是完美的。我将添加更多晦涩的参数,对于那些下载预编译的 ffmpeg 二进制文件的人来说,这些参数永远不会起作用。对于 nVidia h265 硬件编码,请使用 ffmpeg -rtbufsize 1500M -f dshow -i audio="virtual-audio-capturer" -f gdigrab -framerate 30 -draw_mouse 1 -i title="Record Window" -c:v hevc_nvenc -preset slow -rc vbr_2pass -2pass 1 -qmin 3 -cq 27 -y Huangbaohua.mp4【参考方案4】:

here中提到过:

默认情况下,它会捕获主桌面监视器的“全屏” (所有窗口,重叠,从那里开始,如果 vista+ 则带有 aero,没有 非航空的透明窗户)。

要进行不同的配置,请运行提供的“配置设置” 实用程序/快捷方式”或在开始运行之前调整注册表设置 (仅限高级用户):

HKEY_CURRENT_USER\Software\screen-capture-recorder

使用 start_XXX 等的 DWORD 键...​(请参阅包含的文件 安装目录\configuration_setup_utility\setup_screen_tracker_params.rb 有关可用注册表项值的完整列表,或请参阅 https://github.com/rdp/screen-capture-recorder-to-video-windows-free/blob/master/configuration_setup_utility/setup_screen_tracker_params.rb#L9 )

ex:请参阅 configuration_setup_utility\incoming.reg 文件(尽管请注意 这些值是十六进制的,所以编辑那个文件有点乏味——我 始终只使用 regedit 或随附的脚本实用程序,不要 手动编辑)。

要“重置”一个值,删除它的键。

您可以在here 中看到这些注册选项:

capture_height capture_width start_x start_y default_max_fps stretch_to_width stretch_to_height stretch_mode_high_quality_if_1 hwnd_to_track disable_aero_for_vista_plus_if_1 track_new_x_y_coords_each_frame_if_1 capture_mouse_default_1 capture_foreground_window_if_1 dedup_if_1 millis_to_sleep_between_poll_for_dedupe_changes capture_transparent_windows_including_mouse_in_non_aero_if_1_causes_annoying_mouse_flicker hwnd_to_track_with_window_decoration

【讨论】:

【参考方案5】:

我从 MaxC 的回答中改进了命令。

该命令的一个问题是区域位置不考虑多显示器布局。 geometry 行中的 x 和 y 是相对于当前监视器的,所以它不能在其他监视器中记录窗口。

信息从单独的行中解析。并且考虑了窗口边框。还添加了倒计时让用户做好准备。这是脚本:

#!/bin/sh
xwininfo | 
    while IFS=: read -r k v; do
        case "$k" in
        *"Absolute upper-left X"*) x=$v;;
        *"Absolute upper-left Y"*) y=$v;;
        *"Border width"*) bw=$v ;;
        *"Width"*) w=$v;;
        *"Height"*) h=$v;;
        esac
    done
    for i in 3 2 1; do echo "$i"; sleep 1; done
    ffmpeg -y -f x11grab -framerate 30 \
           -video_size "$((w))x$((h))" \
           -i "+$((x+bw)),$((y+bw))" screenrecord.mp4

有两件事我不确定:

绝对或相对左上角 X/Y 坐标(见xwininfo 的输出)? 是否所有 WM/DE 都一致地提供窗口边框信息,即 x 和 y 是否始终指代窗口边框外的点?

【讨论】:

【参考方案6】:

我用这个来记录提示

ffmpeg -rtbufsize 1500M -f dshow -i audio="Microfono (8- Logitech USB Headset)" -f gdigrab -framerate 30 -draw_mouse 1 -i title="Prompt dei comandi" -pix_fmt yuv420p -profile:v baseline -y output\output3_xp.mp4
pause

但它仅适用于提示或其他可分割屏幕尺寸的 100x20 (colxrow),否则它会给我一个错误,这个:

[libx264 @ 0000027c7ed66200] width not divisible by 2 (269x432)
Error initializing output stream 0:0 -- Error while opening encoder for output stream #0:0 - maybe incorrect parameters such as bit_rate, rate, width or height
Conversion failed!

P.S.:我也有这个问题,其他窗口没有宽度或高度。我在 Python 中使用 tkinter 创建了一个窗口,但出现了错误,然后我给了窗口一些几何图形(300x500)并且它工作了......

奇怪的是,鼠标有点偏移……

【讨论】:

[libx264 @ 0000027c7ed66200] 宽度不能被 2 整除 (269x432) 初始化输出流 0:0 时出错 - 打开输出流 #0:0 的编码器时出错 - 可能参数不正确,例如 bit_rate、rate , 宽度或高度转换失败! libx264 在输出 yuv420p 时要求宽度和高度都可以被 2 整除。这里有很多答案展示了如何使用比例过滤器自动处理。【参考方案7】:

ffmpeg -f x11grab -framerate 25 $(xwininfo | gawk 'match($0, /-geometry ([0-9]+x[0-9]+).([0-9]+).([0-9]+)/, a) print "-video_size " a[1] " -i +" a[2] "," a[3] ') $(日期+%Y-%m-%d_%H-%M_%S).mp4

这不适用于 xwininfo 在字符单元格中返回几何的“大小”部分而不是像素的窗口(例如终端窗口)。为了解决这个问题,需要从 xwininfo 响应的 Width: 和 Height: 字段中提取大小。

【讨论】:

【参考方案8】:

我无法发表评论,所以在这里写下。 Brian Huang 的回答给了我这个错误:

width not divisible by 2 (603x585)
Error initializing output stream 0:0 -- Error while opening encoder for output stream #0:0 - maybe incorrect parameters such as bit_rate, rate, width or height

但是在添加具有所需分辨率的-vf scale=1280:720 之后,即使高度和宽度都是如此,这个错误也会消失并且屏幕录制将起作用。即使被其他窗口覆盖也不会出现在录制文件中。

【讨论】:

【参考方案9】:

为了录制一个窗口的节目,“gdigrab”元素和它的“title”补语是必要的,这是窗口的名称,因为它显示在 --> 任务管理器 >> 详细信息中,这在 windows 中。

ffmpeg -f gdigrab -rtbufsize 150M -i title="VisorATSC1" -s 480x360 -r 15 -b 2000k -minrate 2000k -maxrate 2000k -vcodec h264_nvenc -gpu 0 -f flv rtmp://170.239.148.120:1935/live/YASV

【讨论】:

以上是关于如何使用 ffmpeg 记录特定窗口?的主要内容,如果未能解决你的问题,请参考以下文章

FFMPEG 没有记录整个窗口

如何使用 ffmpeg 从视频中删除特定持续时间

如何在ffmpeg中指定nvenc要使用的GPU [关闭]

如何使用ffmpeg提取视频中的第一帧?

如何在ffmpeg中指定nvenc使用的GPU [关闭]

在 ffmpeg 中从单个图像创建特定持续时间的视频