如何通过管道传输到 ffmpeg RGB 值 10?

How to pipe to ffmpeg RGB value 10?

我正在尝试使用 ffmpeg 创建视频文件。我有每一帧的所有 RGB 像素数据,在 this 博文之后,我有代码通过管道逐帧发送数据。它主要起作用。但是,如果任何像素在 3 个通道(例如#00000A、#0AFFFF 等)中的任何一个中的值为 10,则会产生以下错误:

[rawvideo @ 0000020c3787f040] Packet corrupt (stream = 0, dts = 170) 
pipe:: corrupt input packet in stream 0
[rawvideo @ 0000020c3789f100] Invalid buffer size, packet size 32768 < expected frame_size 49152
Error while decoding stream #0:0: Invalid argument

并且输出的视频是乱码。 现在我怀疑因为 ASCII 中的 10 是换行符,所以这会以某种方式混淆管道。 这里到底发生了什么,我该如何修复它以便我可以使用像 #00000a 这样的 RGB 值?

下面是 C 代码,它是一个例子

    #include <stdio.h>

    unsigned char frame[128][128][3];

    int main() {
    
        int x, y, i;
        FILE *pipeout = popen("ffmpeg -y -f rawvideo -vcodec rawvideo -pix_fmt rgb24 -s 128x128 -r 24 -i - -f mp4 -q:v 1 -an -vcodec mpeg4 output.mp4", "w");
    
        for (i = 0; i < 128; i++) {
            for (x = 0; x < 128; ++x) {
                for (y = 0; y < 128; ++y) {
                    frame[y][x][0] = 0;
                    frame[y][x][1] = 0;
                    frame[y][x][2] = 10;
                } 
            }
            fwrite(frame, 1, 128*128*3, pipeout);
        } 
    
        fflush(pipeout);
        pclose(pipeout);
        return 0;
    }

编辑:为清楚起见,我使用 Windows

我刚刚在 Linux 中尝试了您的代码,它对我有用。我认为@Craig Estey 的建议可能就是答案。

如果它不起作用,您可以尝试使用 write 而不是 fwrite 写入数据(如果可用)。 (我在过去使用 fread/fwrite 系列函数将二进制数据写入管道时遇到过问题。)

因此您可以尝试更改此行:

fwrite(frame, 1, 128*128*3, pipeout);

类似于:

int fd = fileno(pipeout);
write(fd, frame, sizeof(frame));

并删除以下行:

fflush(pipeout);

编辑:您链接的博客 post 的评论部分有一些故障排除提示。特别是关于此程序的 Windows 版本。